linux模拟pod并配置上外网
- 2021 年 1 月 19 日
- AI
- TensorFlow
前言
这篇文章我们将完成以下几件事情:
用docker模拟一个POD
将这个POD和主机连接起来,在主机中能访问POD的网站
让这个POD能上外网
模拟一个POD
POD是一个K8S的逻辑概念,POD里会有一个或多个容器,他们之间共享一个网络命名空间,可以用localhost相互访问,下面我们将脱离开K8S,直接用docker来模拟这种情况:
首先创建一个network=none的容器:
这时候pause容器会新建一个网络命名空间,但不会加入docker0网桥中,我们用下面的命令来查看:
我们再运行一个nginx容器,加入上面的pause容器的网络命名空间,命令如下:
这时候我们试一下在pause容器中用localhost访问nginx:
也可以这样验证:
把容器的网络命名空间映射出来,让我们用ip netns可以更方便地操作到:
好了,到这一步为止,我们已经把一个pause容器模拟出来了,而且已经加了一个nginx在这个pause容器的网络命名空间中,把这个网络命名空间挂到了/var/run/netns/ns99下面,我们现在可以用:
来操作这个Pod的网络了,接下来的事情就是前面已经完成过的内容了,这里直接把命令列出,不再一一解释了。
POD连接节点
接下来,我们会在主机的网络命名空间创建一对veth网卡对,然后把一端转到POD的网络中,并且设置IP地址:
接下来进入pod中配置默认网关和邻居表:
这时候退出来主机的网络空间中,然后试着curl 10.2.2.4
已经成功了。
POD连接外网
现在POD已经连到了主机上,我们现在要把主机当成NAT网关来上外网,首先要开启主机的转发功能
然后要加两条iptables规则:
第一条是说放过所有转发的数据包,第二条是说为来源为10.2.2.4的数据进行SNAT,做完这两步后,再进去POD中PING 8.8.8.8已经通了。
为什么加了个snat,就能正常出外网了呢?实际上,不加snat,流量也能正常出的,关键是,回不来
仔细想一下,源地址为10.2.2.4,目标为8.8.8.8,在主机出外网的出口上肯定要做一次nat,假设主机所在网络的出口的ip是7.7.7.7,那么从7.7.7.7到8.8.8.8是没的问题的,从8.8.8.8回7.7.7.7也是没有问题的,关键是7.7.7.7的这个出口路由上再要把包再回给10.2.2.4就有问题了,因为这个ip是我们在主机上虚拟出来的,除了这台主机外其它人根本不认识,所以snat在这里就很关键了。
作者:刘海峰,IT行业资深码农,从事.net/Java/go语言开发十余年,长期关注springcloud/k8s/linux网络相关的技术,现为滴普科技容器产品首席架构师。
了解更多详情请登录://www.deepexi.com/