文章插图
容器网络发端于 Docker 的网络 。Docker 使用了一个比较简单的网络模型,即内部的网桥加内部的保留 IP 。这种设计的好处在于容器的网络和外部世界是解耦的,无需占用宿主机的 IP 或者宿主机的资源,完全是虚拟的 。
它的设计初衷是:当需要访问外部世界时,会采用 SNAT 这种方法来借用 Node 的 IP 去访问外面的服务 。比如容器需要对外提供服务的时候,所用的是 DNAT 技术,也就是在 Node 上开一个端口,然后通过 iptable 或者别的某些机制,把流导入到容器的进程上以达到目的 。
该模型的问题在于,外部网络无法区分哪些是容器的网络与流量、哪些是宿主机的网络与流量 。比如,如果要做一个高可用的时候,172.16.1.1 和 172.16.1.2 是拥有同样功能的两个容器,此时我们需要将两者绑成一个 Group 对外提供服务,而这个时候我们发现从外部看来两者没有相同之处,它们的 IP 都是借用宿主机的端口,因此很难将两者归拢到一起 。
文章插图
在此基础上,Kubernetes 提出了这样一种机制:即每一个 Pod,也就是一个功能聚集小团伙应有自己的“身份证”,或者说 ID 。在 TCP 协议栈上,这个 ID 就是 IP 。
这个 IP 是真正属于该 Pod 的,外部世界不管通过什么方法一定要给它 。对这个 Pod IP 的访问就是真正对它的服务的访问,中间拒绝任何的变造 。比如以 10.1.1.1 的 IP 去访问 10.1.2.1 的 Pod,结果到了 10.1.2.1 上发现,它实际上借用的是宿主机的 IP,而不是源 IP,这样是不被允许的 。Pod 内部会要求共享这个 IP,从而解决了一些功能内聚的容器如何变成一个部署的原子的问题 。
剩下的问题是我们的部署手段 。Kubernetes 对怎么实现这个模型其实是没有什么限制的,用 underlay 网络来控制外部路由器进行导流是可以的;如果希望解耦,用 overlay 网络在底层网络之上再加一层叠加网,这样也是可以的 。总之,只要达到模型所要求的目的即可 。
Pod 究竟如何上网
容器网络的网络包究竟是怎么传送的?
文章插图
我们可以从以下两个维度来看:
- 协议层次
- 网络拓扑
2. 网络拓扑一个容器的包所要解决的问题分为两步:第一步,如何从容器的空间 (c1) 跳到宿主机的空间 (infra);第二步,如何从宿主机空间到达远端 。
我个人的理解是,容器网络的方案可以通过接入、流控、通道这三个层面来考虑 。
- 第一个是接入,就是说我们的容器和宿主机之间是使用哪一种机制做连接,比如 Veth + bridge、Veth + pair 这样的经典方式,也有利用高版本内核的新机制等其他方式(如 mac/IPvlan 等),来把包送入到宿主机空间;
- 第二个是流控,就是说我的这个方案要不要支持 Network Policy,如果支持的话又要用何种方式去实现 。这里需要注意的是,我们的实现方式一定需要在数据路径必经的一个关节点上 。如果数据路径不通过该 Hook 点,那就不会起作用;
- 第三个是通道,即两个主机之间通过什么方式完成包的传输 。我们有很多种方式,比如以路由的方式,具体又可分为 BGP 路由或者直接路由 。还有各种各样的隧道技术等等 。最终我们实现的目的就是一个容器内的包通过容器,经过接入层传到宿主机,再穿越宿主机的流控模块(如果有)到达通道送到对端 。
文章插图
这个方案的精髓在于 route 表的设置,如上图所示 。接下来为大家一一解读一下 。
推荐阅读
- H3C网络设备环路检测详细说明及配置
- Android中的 eBPF 流量监控
- 网络许可证|10分钟搞定ICP、EDI、SP、IDC、ISP、VPN、呼叫中心
- 如何使用 firewall-cmd 管理网络服务
- 轻松学习http知识让枯燥的内容变得生动有趣:TCP/IP四层模型
- 黑客泄露了暗网网络托管提供商DH的数据库
- 让你的无线wifi网络无人可破!
- 一起了解网络域名的由来
- 初级入门IT网络工程师?收下这份关于NTP网络时间协议解读 纯干货
- 网络知识扫盲,一文搞懂 DNS