问题描述
docker中有的时候需要从容器内向外网环境进行访问,这个时候我边出现了一个诡异的问题,从容器的宿主机直接通过curl命令使用域名可以正常的访问并返回正确的解决,但是从容器中向外调用外网环境的这个域名的时候,curl命令会被卡住,一直到超时都没有任何返回数据,,并且出现了x509:certificate signed by unknown authority的错误,但是一个很神奇的事情是,如果将该域名换成对应的IP的时候,从容器内向外调用外网环境的这个IP的时候,这个时候就可以正确的返回结果
问题解析:
通过查看调用命令返回的结果,发现出现该问题的主要原因是由于在域名调用的过程中会出现在容器内域名无法解析的问题.这个问题就是分为--1.无法访问外步资源,2.无法解析https对应资源和域名分析
解决过程
第一步,使容器能访问到外部资源
第二步,使容器内能解析域名,能访问https类型资源(解决证书问题),解决x509:certificate signed by unknown authority的错误,解决地址--》》https://www.jianshu.com/p/97471c082b2f
本文章的解决第一步问题以及解释容器交互情况,选择一种讲解使用,还有其他几种请自行选用
如果是通过run命令来启动容器的话,只需要增加 --net=host这个参数,具体命令如下所示:
docker run -d --net=host --name nginx-1 nginx:latest
下面我们来讲解一下上面的这个启动命令中增加 –net=host这个配置参数的作用,该配置的作用主要是表明该容器不会虚拟自己的网卡,配置自己的IP,而是使用宿主机的IP和端口,所以使用这个命令的时候,docker run命令中的 -p也会失效,因为它本来就使用的是宿主机的IP和端口,根本无需进行端口映射
相关拓展
通过上面碰到的这个问题,我们知道了docker容器网络模式相关的一些东西,接下来我们就来拓展一下docker网络模式的详细内容。
docker自身有四种网络模式,还有一些自定义的网络模式,我们今天主要来了解一下自身的四种网络模式
Host:容器使用宿主机的网卡是IP端口,不会虚拟自己的网卡,也不会配置自己的IP;设置命令如下:
docker run --net=host
Container:容器不会虚拟自己的网卡,也不会配置自己的IP,而是和一个指定容器共享IP和端口范围。
docker run --net=container:containerName/containerId
None:关闭容器网络功能。
docker run --net=none
Bridge(默认):
docker run --net=bridge
该模式会为每一个容器虚拟网卡并设置IP,并将容器连接到宿主机中创建好的docker0虚拟网桥,通过docker0网桥以及Iptables nat表配置与宿主机通信,默认的就是这种,需要注意的几点。
一、连接地址切记不能用localhost和127.0.0.1
这些地址代表的都是容器内的系统,根本没有访问到宿主机,会一直报连接mysql/redis异常。
二、用docker的虚拟网卡地址
在宿主机查询网卡情况------ifconfig
docker0这块虚拟网卡的 inet 地址就是正确的本地ip(如172.17.0.1
),一般都是这个。
在我们安装docker的过程中,docker会自动创建三个网络模式,通过下面的命令即可看到:
docker network ls
输出结果如下所示:
NETWORK ID NAME DRIVER SCOPE
1c175577e460 bridge bridge local
2b90b47781d5 host host local
8469af2f3d91 none null local
在启动容器的时候,我们可以通过 –net 参数来指定使用哪种网络模式,默认docker容器会使用 bridge 网络模式
通过下面的几个命令,我们可以查看每一种网络往事的详细信息:
查看 bridge 网络模式详情
docker network inspect bridge
查看 host 网络模式详情
docker network inspect host
查看 none 网络模式详情
docker network inspect none