日日操夜夜添-日日操影院-日日草夜夜操-日日干干-精品一区二区三区波多野结衣-精品一区二区三区高清免费不卡

公告:魔扣目錄網為廣大站長提供免費收錄網站服務,提交前請做好本站友鏈:【 網站目錄:http://www.ylptlb.cn 】, 免友鏈快審服務(50元/站),

點擊這里在線咨詢客服
新站提交
  • 網站:51998
  • 待審:31
  • 小程序:12
  • 文章:1030137
  • 會員:747

K8S 網絡設計與實現是在學習 K8S 網絡過程中總結的內容。本文按照 K8S 網絡設計原則、Pod 內部網絡、Pod 之間網絡等幾個步驟講解 K8S 復雜的網絡架構。

K8S 的網絡架構弄清楚了嗎?

 

圖片出自:《你女兒也能看懂的插畫版 Kubernetes 指南》

K8S 網絡設計原則

K8S 網絡設計原則如下:

  • 每個 Pod 都擁有一個獨立 IP 地址,Pod 內所有容器共享該 IP 地址。
  • 集群內所有 Pod 都在一個直接連通的扁平網絡中,可通過 IP 直接訪問。
  • 即:所有容器之間無需 NAT 就可以直接互相訪問;所有 Node 和所有容器之間無需 NAT 就可以直接互相訪問;容器自己看到的 IP 跟其他容器看到的一樣。

K8S 網絡規范

CNI 是由 CoreOS 提出的一個容器網絡規范。已采納規范的包括 Apache Mesos,Cloud Foundry,Kubernetes,Kurma 和 RKT。

另外 Contiv Networking,Project Calico 和 Weave 這些項目也為 CNI 提供插件。

K8S 的網絡架構弄清楚了嗎?

 

CNI 規定了一個容器 Runtime 和網絡插件之間的簡單的契約。這個契約通過 JSON 的語法定義了 CNI 插件所需要提供的輸入和輸出。

CNI 插件提供兩個功能:

  • 一個用來將網絡接口加入到指定網絡。
  • 另一個用來將其移除。

這兩個接口分別在容器被創建和銷毀的時候被調用。容器 Runtime 首先需要獲得一個網絡命名空間以及一個容器 ID,然后連同一些 CNI 配置參數傳給網絡驅動。

接著網絡驅動會將該容器連接到網絡并將分配的 IP 地址以 JSON 的格式返回給容器 Runtime。

K8S 網絡插件要求

K8S 對網絡插件的要求總的來講主要有兩個最基本的,分別是:

  • 要能夠為每一個 Node 上的 Pod 分配互相不沖突的 IP 地址。
  • 要所有 Pod 之間能夠互相訪問。

K8S 網絡實現方案

K8S網絡實現方案有如下幾種:

隧道方案

隧道方案在 IaaS 層的網絡中應用也比較多,將 Pod 分布在一個大二層的網絡規模下。網絡拓撲簡單,但隨著節點規模的增長復雜度會提升。

代表方案:

  • Weave:UDP 廣播,本機建立新的 BR,通過 PCAP 互通。
  • Open vSwitch:基于 VxLan 和 GRE 協議,但是性能方面損失比較嚴重。
  • Flannel:UDP 廣播,VxLan。
  • Racher:IPsec。

路由方案

路由方案一般是從 3 層或者 2 層實現隔離和跨主機容器互通的,出了問題也很容易排查。

代表方案:

  • Calico:基于 BGP 協議的路由方案,支持很細致的 ACL 控制,對混合云親和度比較高。
  • macvlan:從邏輯和 Kernel 層來看隔離性和性能優的方案,基于二層隔離,所以需要二層路由器支持,大多數云服務商不支持,所以混合云上比較難以實現。

K8S Pod 的網絡創建流程

K8S Pod 的網絡創建流程如下:

  • 每個 Pod 除了創建時指定的容器外,都有一個 Kubelet 啟動時指定的基礎容器。
  • Kubelet 創建基礎容器,生成 Network Namespace。
  • Kubelet 調用網絡 CNIdriver,根據配置調用具體的 CNI 插件。
  • CNI 插件給基礎容器配置網絡。
  • Pod 中其他的容器共享基礎容器的網絡。

Pod 中的網絡

Pod 是 K8S 的最小工作單元。每個 Pod 包含一個或多個容器。K8S 管理的也是 Pod 而不是直接管理容器。Pod 中的容器會作為一個整體被 Master 調度到一個 Node 上運行。

Pod 的設計理念是支持多個容器在一個 Pod 中共享網絡地址和文件系統,可以通過進程間通信和文件共享這種簡單高效的方式組合完成服務。

K8S 的網絡架構弄清楚了嗎?

 

一個 Pod 中可以包含多個容器,而一個 Pod 只有一個 IP 地址。那么多個容器之間互相訪問和訪問外網是如何使用這一個 IP 地址呢?

答案是:多個容器共享同一個底層的網絡命名空間 Net(網絡設備、網絡棧、端口等)。

下面以一個小例子說明,創建一個 Pod 包含兩個容器,yaml 文件如下:

apiVersion: Apps/v1beta1
kind: Deployment
metadata:
 name: Pod-two-container
spec:
 replicas: 1
 template:
 metadata:
 labels:
 app: Nginx
 spec:
 containers:
 - name: busybox
 image: busybox
 command:
 - "/bin/sh"
 - "-c"
 - "while true;do echo hello;sleep 1;done"
 - name: nginx
 image: nginx
K8S 的網絡架構弄清楚了嗎?

 

創建 1 個 Pod 中包含 2 個 Container,實際會創建 3 個 Container。多出的一個是“Pause”容器。

該 Container 是 Pod 的基礎容器,為其他容器提供網絡功能。

K8S 的網絡架構弄清楚了嗎?

 

查看 Pause 容器的基礎信息:

K8S 的網絡架構弄清楚了嗎?

 

使用命令 Docker inspect 容器 _ID 查看 Nginx 詳細信息,其網絡命令空間使用了 Pause 容器的命名空間,同樣還有進程間通信的命名空間。

K8S 的網絡架構弄清楚了嗎?

 

再查看 Busybox,可以發現其網絡命令空間使用了 Pause 容器的命名空間,進程通信的命名空間也是 Pause 容器的命名空間。

K8S 的網絡架構弄清楚了嗎?

 

實現方式:Nginx 和 Busybox 之所以能夠和 Pause 的命名空間連通是因為 Docker 有一個特性:能夠在創建時使用指定 Docker 的網絡命名空間。

在 Docker 的官網上有一段描述:

https://docs.docker.com/engine/reference/run/
K8S 的網絡架構弄清楚了嗎?

 

所以如果要手動完成一個上面的 Pod,可以先創建 Pause,再創建 Nginx 和 Busybox,同時將網絡指定為 Pause 的網絡命名空間即可。

docker run --name pause mirrorgooglecontainers/pause-amd64:3.1
docker run --name=nginx --network=container:pause nginx 
docker run --name=busybox --network=container:pause busybox

上述步驟由 K8S 幫助我們完成,所以 Pod 命名空間應該是這樣的:

K8S 的網絡架構弄清楚了嗎?

 

講完了 Pod 內部的網絡實現,我們主要來看 Pod 如何獲取 IP 地址,以及 Pod 與 Pod 之間的通信是怎么樣的過程?

Flannel 網絡

Flannel 簡介

Flannel 是 CoreOS 團隊針對 Kubernetes 設計的一個網絡規劃服務,簡單來說,它的功能是讓集群中的不同節點主機創建的 Docker 容器都具有全集群唯一的虛擬 IP 地址。

在默認的 Docker 配置中,每個節點上的 Docker 服務會分別負責所在節點容器的 IP 分配。這樣導致的一個問題是,不同節點上容器可能獲得相同的 IP 地址。

Flannel 的設計目的就是為集群中的所有節點重新規劃 IP 地址的使用規則,從而使得不同節點上的容器能夠獲得“同屬一個內網”且“不重復的”IP 地址,并讓屬于不同節點上的容器能夠直接通過內網 IP 通信。

Flannel 實質上是一種“覆蓋網絡(overlay network)”,也就是將 TCP 數據包裝在另一種網絡包里面進行路由轉發和通信。

目前已經支持 UDP、Vxlan、Host-gw、Aws-vpc、Gce 和 Alloc 路由等數據轉發方式,默認的節點間數據通信方式是 UDP 轉發。

適用場景:不需要隔離 Pod,集群規模小。

設計思想:為每一個 Node 節點分配 IP 網段,使 Node 之間 IP 不重復,Pod 之間直接使用 IP 訪問。

設計優勢:網絡模型簡單,安裝配置相對容易,成熟度高,適合大多數用例的環境。

Flannel 對網絡要求提出的解決辦法

互相不沖突的 IP:

  • Flannel 利用 Kubernetes API 或者 etcd 用于存儲整個集群的網絡配置,根據配置記錄集群使用的網段。
  • Flannel 在每個主機中運行 Flanneld 作為 Agent,它會為所在主機從集群的網絡地址空間中,獲取一個小的網段 Subnet,本主機內所有容器的 IP 地址都將從中分配。

如測試環境中 IP 分配:

①Master 節點

K8S 的網絡架構弄清楚了嗎?

 

②Node1

K8S 的網絡架構弄清楚了嗎?

 

③Node2

K8S 的網絡架構弄清楚了嗎?

 


K8S 的網絡架構弄清楚了嗎?

 

在 Flannel Network 中,每個 Pod 都會被分配唯一的 IP 地址,且每個 K8S Node 的 Subnet 各不重疊,沒有交集。

Pod 之間互相訪問:

  • Flanneld 將本主機獲取的 Subnet 以及用于主機間通信的 Public IP 通過 etcd 存儲起來,需要時發送給相應模塊。
  • Flannel 利用各種 Backend 機制,例如 UDP,Vxlan 等等,跨主機轉發容器間的網絡流量,完成容器間的跨主機通信。

Flannel 架構原理

Flannel 架構圖:

K8S 的網絡架構弄清楚了嗎?

 

各個組件的解釋如下:

Cni0:網橋設備,每創建一個 Pod 都會創建一對 Veth Pair。其中一端是 Pod 中的 eth0,另一端是 cni0 網橋中的端口(網卡)。

Pod 中從網卡 eth0 發出的流量都會發送到 cni0 網橋設備的端口(網卡)上。

K8S 的網絡架構弄清楚了嗎?

 

注:cni0 設備獲得的 IP 地址是該節點分配到的網段的第一個地址。

Flannel.1:Overlay 網絡的設備,用來進行 Vxlan 報文的處理(封包和解包)。不同 Node 之間的 Pod 數據流量都從 Overlay 設備以隧道的形式發送到對端。

K8S 的網絡架構弄清楚了嗎?

 

Flanneld:Flannel 在每個主機中運行 Flanneld 作為 Agent,它會為所在主機從集群的網絡地址空間中,獲取一個小的網段 Subnet,本主機內所有容器的 IP 地址都將從中分配。

同時 Flanneld 監聽 K8S 集群數據庫,為 Flannel.1 設備提供封裝數據時必要的 Mac,IP 等網絡數據信息。

不同 Node 上的 Pod 的通信流程:

  • Pod 中產生數據,根據 Pod 的路由信息,將數據發送到 cni0。
  • cni0 根據節點的路由表,將數據發送到隧道設備 Flannel.1。
  • Flannel.1 查看數據包的目的 IP,從 Flanneld 獲得對端隧道設備的必要信息,封裝數據包。
  • Flannel.1 將數據包發送到對端設備。節點的網卡接收到數據包,發現數據包為 Overlay 數據包,解開外層封裝,并發送內層封裝到 Flannel.1 設備。
  • Flannel.1 設備查看數據包,根據路由表匹配,將數據發送給 cni0 設備。
  • cni0 匹配路由表,發送數據給網橋上對應的端口。

通信流程

①Pod1 中的容器到 cni0

Pod1 與 Pod3 能夠互相 Ping 通:

K8S 的網絡架構弄清楚了嗎?

 

Ping 包的 Dst IP 為 192.20.1.43,根據路由匹配到最后一條路由表項,去往 192.20.0.0/12 的包都轉發給 192.20.0.1。

K8S 的網絡架構弄清楚了嗎?

 

192.20.0.1 為 cni0 的 IP 地址。

K8S 的網絡架構弄清楚了嗎?

 

②cni0 到 Flannel1.1

當 Icmp 包達到 cni0 之后,cni0 發現 Dst 為 192.20.1.43,CNI 根據主機路由表來查找匹配項。

K8S 的網絡架構弄清楚了嗎?

 

根據最小匹配原則,匹配到圖上的一條路由表項。去往 192.20.1.0/24 網段的包,發送 192.20.1.0 網關,網關設備是 Flannel.1。

③Flannel.1

內層封裝:Flannel.1 為 Vxlan 隧道端點,當數據包來到 Flannel.1 時,需要將數據包封裝起來。此時:

  • 源 IP src ip 為 192.20.0.51。
  • 目的 IP dst ip 為 192.20.1.43。

數據包繼續封裝需要知道目的 IP 192.20.1.43,IP 地址對應的 Mac 地址。此時,Flannel.1 不會發送 ARP 請求去獲得目的 IP 的 Mac 地址,而是將請求發送到用戶空間的 Flanned 程序。

Flanned 程序收到內核的請求事件之后,從 etcd 查找能夠匹配該地址的子網的 Flannel.1 設備的 Mac 地址,即發往的 Pod 所在 Host 中 Flannel.1 設備的 Mac 地址。

Flannel 在為 Node 節點分配 IP 網段時記錄了所有的網段和 Mac 等信息。該過程交互流程如下圖所示:

K8S 的網絡架構弄清楚了嗎?

 

Flanned 將查詢到的信息放入 Master 節點的 ARP Cache 表中:

K8S 的網絡架構弄清楚了嗎?

 

到這里,Vxlan 的內層數據包就完成了封裝。格式是這樣的:

K8S 的網絡架構弄清楚了嗎?

 

簡單總結這個流程:

  • 數據包到達 Flannel.1,通過查找路由表,知道數據包要通過 Flannel.1 發往 192.20.1.0。
  • 通過 ARP Cache 表,知道了目的 IP 192.20.1.0 的 Mac 地址。

外層封裝:此時內層封裝已經準備好,需要找到 Vxlan 的外層封裝。Kernel 需要查看 Node 上的 FDB(forwarding database)以獲得內層封包中目的 Vtep 設備所在的 Node 地址。

因為已經從 ARP Table 中查到目的設備 Mac 地址為 52:77:71:e6:4f:58,同時在 FDB 中存在該 Mac 地址對應的 Node 節點的 IP 地址。

如果 FDB 中沒有這個信息,那么 Kernel 會向用戶空間的 Flanned 程序發起“L2 MISS”事件。Flanneld 收到該事件后,會查詢 etcd,獲取該 Vtep 設備對應的 Node 的“Public IP”,并將信息注冊到 FDB 中。

當內核獲得了發往機器的 IP 地址后,ARP 得到 Mac 地址,之后就能完成 Vxlan 的外層封裝。

K8S 的網絡架構弄清楚了嗎?

 

④對端 Flannel.1

Node 節點的 eth0 網卡接收到 Vxlan 設備包,Kernal 將識別出這是一個 Vxlan 包,將包拆開之后轉給節點上的 Flannel.1 設備。

這樣數據包就從發送節點到達目的節點,Flannel.1 設備將接收到一個如下的數據包:

K8S 的網絡架構弄清楚了嗎?

 

目的地址為 192.20.1.43,Flannel.1 查找自己的路由表,根據路由表完成轉發。

K8S 的網絡架構弄清楚了嗎?

 

根據匹配原則,Flannel.1 將去往 192.20.1.0/24 的流量轉發到 cni0 上去。

⑤cnio 到 Pod

cni0 是一個網橋設備。當 cni0 拿到數據包之后,通過 Veth Pair,將數據包發送給 Pod。查看 Node 節點中的網橋。

K8S 的網絡架構弄清楚了嗎?

 

在 Node 節點上通過 ARP 解析可以開出,192.20.1.43 的 Mac 地址為 66:57:8e:3d:00:85:

K8S 的網絡架構弄清楚了嗎?

 

該地址為 Pod 的網卡 eth0 的地址。

K8S 的網絡架構弄清楚了嗎?

 

同時通過 Veth Pair 的配對關系可以看出,Pod 中的 eth0 是 Veth Pair 的一端,另一端在 Node 節點行上,對應的網卡是 vethd356ffc1@if3:

K8S 的網絡架構弄清楚了嗎?

 

所以,在 cni0 網橋上掛載的 Pod 的 Veth Pair 為 vethd356ffc1,即:

K8S 的網絡架構弄清楚了嗎?

 

eth0@if50 和 vethd356ffc1@if3 組成的一對 Veth Pair。其效果相當于將 Pod 中的 eth0 直接插在到 cni0 上。

簡單總結 cni0 轉發流量的原理:

  • 首先通過 ARP 查找出 IP 地址對應的 Mac 地址。
  • 將流量轉發給 Mac 地址所在 eth0 網的對應的 Veth Pair 端口。
  • Veth Pair 端口接收到流量,直接將流量注入到 Pod 的 eth0 網卡上。

總結 Flannel 的特點:

  • 使集群中的不同 Node 主機創建的 Docker 容器都具有全集群唯一的虛擬 IP 地址。
  • 建立一個覆蓋網絡(overlay network),通過這個覆蓋網絡,將數據包原封不動的傳遞到目標容器。
  • 創建一個新的虛擬網卡 Flannel0 接收 Docker 網橋的數據,通過維護路由表,對接收到的數據進行封包和轉發。
  • etcd 保證了所有 Node 上 Flanned 所看到的配置是一致的。同時每個 Node 上的 Flanned 監聽 etcd 上的數據變化,實時感知集群中 Node 的變化。

不同后端的封裝

Flannel 可以指定不同的轉發后端網絡,常用的有 Hostgw,UDP,Vxlan 等,上述使用的就是 Vxlan 網絡。

①Hostgw:是簡單的 Backend,它的原理非常簡單,直接添加路由,將目的主機當做網關,直接路由原始封包。

例如,我們從 etcd 中監聽到一個 EventAdded 事件 Subnet 為 10.1.15.0/24 被分配給主機 Public IP 192.168.0.100。

Hostgw 要做的工作就是在本主機上添加一條目的地址為 10.1.15.0/24,網關地址為 192.168.0.100,輸出設備為上文中選擇的集群間交互的網卡即可。

優點:簡單,直接,效率高。

缺點:要求所有的 Pod 都在一個子網中,如果跨網段就無法通信。

②UDP:如何應對 Pod 不在一個子網里的場景呢?將 Pod 的網絡包作為一個應用層的數據包,使用 UDP 封裝之后在集群里傳輸,即 Overlay。

K8S 的網絡架構弄清楚了嗎?

 

上圖來自 Flannel 官方,其中右邊 Packer 的封裝格式就是使用 UDP 完成 Overlay 的格式。

K8S 的網絡架構弄清楚了嗎?

 

當容器 10.1.15.2/24 要和容器 10.1.20.2/24 通信時:

  • 因為該封包的目的地不在本主機 Subnet 內,因此封包會首先通過網橋轉發到主機中。
  • 在主機上經過路由匹配,進入網卡 Flannel.1。(需要注意的是 Flannel.1 是一個 Tun 設備,它是一種工作在三層的虛擬網絡設備,而 Flanneld 是一個 Proxy,它會監聽 Flannel.1 并轉發流量。)
  • 當封包進入 Flannel.1 時,Flanneld 就可以從 Flanne.1 中將封包讀出,由于 Flanne.1 是三層設備,所以讀出的封包僅僅包含 IP 層的報頭及其負載。
  • 最后 Flanneld 會將獲取的封包作為負載數據,通過 UDP Socket 發往目的主機。
  • 在目的主機的 Flanneld 會監聽 Public IP 所在的設備,從中讀取 UDP 封包的負載,并將其放入 Flannel.1 設備內。
  • 容器網絡封包到達目的主機,之后就可以通過網橋轉發到目的容器了。

優點:Pod 能夠跨網段訪問。

缺點:隔離性不夠,UDP 不能隔離兩個網段。

③Vxlan:和上文提到的 udpbackend 的封包結構是非常類似的,不同之處是多了一個 vxlanheader,以及原始報文中多了個二層的報頭。

K8S 的網絡架構弄清楚了嗎?

 

當初始化集群里,Vxlan 網絡的初始化工作:主機 B 加入 Flannel 網絡時,它會將自己的三個信息寫入 etcd 中,分別是:Subnet10.1.16.0/24、Public IP 192.168.0.101、Vtep 設備 Flannel.1 的 Mac 地址 MAC B。

之后,主機 A 會得到 EventAdded 事件,并從中獲取上文中 B 添加至 etcd 的各種信息。

這個時候,它會在本機上添加三條信息:

  • 路由信息:所有通往目的地址 10.1.16.0/24 的封包都通過 Vtep 設備 Flannel.1 設備發出,發往的網關地址為 10.1.16.0,即主機 B 中的 Flannel.1 設備。
  • FDB 信息:MAC 地址為 MAC B 的封包,都將通過 Vxlan 發往目的地址 192.168.0.101,即主機 B。
  • ARP 信息:網關地址 10.1.16.0 的地址為 MAC B。

事實上,Flannel 只使用了 Vxlan 的部分功能,由于 VNI 被固定為 1,本質上工作方式和 UDP Backend 是類似的,區別無非是將 UDP 的 Proxy 換成了內核中的 Vxlan 處理模塊。

而原始負載由三層擴展到了二層,但是這對三層網絡方案 Flannel 是沒有意義的,這么做也僅僅只是為了適配 Vxlan 的模型。

存在問題

存在的問題如下:

  • 不支持 Pod 之間的網絡隔離。Flannel 設計思想是將所有的 Pod 都放在一個大的二層網絡中,所以 Pod 之間沒有隔離策略。
  • 設備復雜,效率不高。Flannel 模型下有三種設備,數量經過多種設備的封裝、解析,勢必會造成傳輸效率的下降。

 

Calico 網絡

Calico 簡介

Calico 是一種開源網絡和網絡安全解決方案,適用于容器,虛擬機和基于主機的本機工作負載。

Calico 支持廣泛的平臺,包括 Kubernetes,OpenShift,Docker EE,OpenStack 和裸機服務。

在虛擬化平臺中,比如 OpenStack、Docker 等都需要實現 Workloads 之間互連,但同時也需要對容器做隔離控制,就像在 Internet 中的服務僅開放 80 端口、公有云的多租戶一樣,提供隔離和管控機制。

而在多數的虛擬化平臺實現中,通常都使用二層隔離技術來實現容器的網絡,這些二層的技術有一些弊端,比如需要依賴 VLAN、Bridge 和隧道等技術。

其中 Bridge 帶來了復雜性,Vlan 隔離和 Tunnel 隧道則消耗更多的資源并對物理環境有要求,隨著網絡規模的增大,整體會變得越加復雜。

Calico 是一個純三層的方案,把每個 Node 節點認為是一個路由器,然后把所有的容器認為是連在這個路由器上的網絡終端,在路由器之間跑標準的路由協議——BGP 的協議,然后讓它們自己去學習這個網絡拓撲該如何轉發。

Calico 為每個主機分配了一段子網作為容器可分配的 IP 范圍,這樣就可以根據子網的 CIDR 為每個主機生成比較固定的路由規則,Pod 發送另一個主機的流量能夠根據路由規則匹配而被轉發。

適用場景:集群規模較大,環境中的 Pod 之間需要隔離。

設計思想:Calico 不使用隧道或 NAT 來實現轉發,而是巧妙的把所有二三層流量轉換成三層流量,并通過 Host 上路由配置完成跨 Host 轉發。

設計優勢如下:

①更優的資源利用:二層網絡通訊需要依賴廣播消息機制,廣播消息的開銷與 Host 的數量呈指數級增長,Calico 使用的三層路由方法,則完全抑制了二層廣播,減少了資源開銷。

另外,二層網絡使用 VLAN 隔離技術,天生有 4096 個規格限制,即便可以使用 Vxlan 解決,但 Vxlan 又帶來了隧道開銷的新問題。而 Calico 不使用 Vlan 或 Vxlan 技術,使資源利用率更高。

②可擴展性:Calico 使用與 Internet 類似的方案,Internet 的網絡比任何數據中心都大,Calico 同樣天然具有可擴展性。

③簡單而更容易 Debug:因為沒有隧道,意味著 Workloads 之間路徑更短更簡單,配置更少,在 Host 上更容易進行 Debug 調試。

④更少的依賴:Calico 僅依賴三層路由可達。

⑤可適配性:Calico 較少的依賴性使它能適配所有 VM、Container、白盒或者混合環境場景。

Calico 架構原理

架構圖如下:

K8S 的網絡架構弄清楚了嗎?

 

Calico 網絡模型主要工作組件:

  • Felix:運行在每一臺 Host 的 Agent 進程,主要負責網絡接口管理和監聽、路由、ARP 管理、ACL 管理和同步、狀態上報等。
  • etcd:分布式鍵值存儲,主要負責網絡元數據一致性,確保 Calico 網絡狀態的準確性,可以與 Kubernetes 共用。
  • BGP Client(BIRD):Calico 為每一臺 Host 部署一個 BGP Client,使用 BIRD 實現,BIRD 是一個單獨的持續發展的項目,實現了眾多動態路由協議比如 BGP、OSPF、RIP 等。
  • 在 Calico 的角色是監聽 Host 上由 Felix 注入的路由信息,然后通過 BGP 協議廣播告訴剩余 Host 節點,從而實現網絡互通。
  • BGP Route Reflector(BIRD):在大型網絡規模中,如果僅僅使用 BGP Client 形成 Mesh 全網互聯的方案就會導致規模限制,因為所有節點之間倆倆互聯,需要 N^2 個連接。
  • 為了解決這個規模問題,可以采用 BGP 的 RouterReflector 的方法,使所有 BGPClient 僅與特定 RR 節點互聯并做路由同步,從而大大減少連接數。

Felix:會監聽 ectd 中心的存儲,從它獲取事件,比如說用戶在這臺機器上加了一個 IP,或者是創建了一個容器等。

用戶創建 Pod 后,Felix 負責將其網卡、IP、MAC 都設置好,然后在內核的路由表里面寫一條,注明這個 IP 應該到這張網卡。

同樣如果用戶制定了隔離策略,Felix 同樣會將該策略創建到 ACL 中,以實現隔離。

BIRD:是一個標準的路由程序,它會從內核里面獲取哪一些 IP 的路由發生了變化,然后通過標準 BGP 的路由協議擴散到整個其他的宿主機上,讓其他 Node 節點都知道這個 IP 在這里,生成路由條目就比較方便。

由于 Calico 是一種純三層的實現,因此可以避免與二層方案相關的數據包封裝的操作,中間沒有任何的 NAT,沒有任何的 Overlay。

所以它的轉發效率可能是所有方案中最高的,因為它的包直接走原生 TCP/IP 的協議棧,它的隔離也因為這個棧而變得好做。

因為 TCP/IP 的協議棧提供了一整套的防火墻的規則,所以它可以通過 IPTABLES 的規則達到比較復雜的隔離邏輯。

Calico 網絡 Node 之間兩種網絡

IPIP:是把一個 IP 數據包放在在一個 IP 包里,即把 IP 層封裝到 IP 層的一個 Tunnel。

它的作用基本上就相當于一個基于 IP 的網橋!一般來說,普通的網橋是基于 Mac 的,根本不需 IP。

而 IPIP 則是通過兩端的路由做一個 Tunnel,把兩個本來不通的網絡通過點對點連接起來。

BGP:邊界網關協議(Border Gateway Protocol, BGP)是互聯網上一個核心的去中心化自治路由協議。

它通過維護 IP 路由表或‘前綴’表來實現自治系統(AS)之間的可達性,屬于矢量路由協議。

BGP 不使用傳統的內部網關協議(IGP)的指標,而使用基于路徑、網絡策略或規則集來決定路由。

IPIP 工作模式

①測試環境

一個 Msater 節點,IP 172.171.5.95,一個 Node 節點 IP 172.171.5.96:

K8S 的網絡架構弄清楚了嗎?

 

創建一個 Daemonset 的應用,Pod1 落在 Master 節點上 IP 地址為 192.168.236.3,Pod2 落在 Node 節點上 IP 地址為 192.168.190.203:

K8S 的網絡架構弄清楚了嗎?

 

Pod1 Ping Pod2:

K8S 的網絡架構弄清楚了嗎?

 

②Ping 包旅程

Pod1 上的路由信息:

K8S 的網絡架構弄清楚了嗎?

 

根據路由信息,Ping 192.168.190.203,會匹配到第一條。第一條路由的意思是:去往任何網段的數據包都發往網管 169.254.1.1,然后從 eth0 網卡發送出去。

路由表中 Flags 標志的含義:

  • U:UP 表示當前為啟動狀態。
  • H:Host 表示該路由為一個主機,多為達到數據包的路由。
  • G:Gateway 表示該路由是一個網關,如果沒有說明目的地是直連的。
  • D:Dynamicaly 表示該路由是重定向報文修改。
  • M:表示該路由已被重定向報文修改。

Master 節點上的路由信息:

K8S 的網絡架構弄清楚了嗎?

 

當 Ping 包來到 Master 節點上,會匹配到路由 tunl0。該路由的意思是:去往 192.169.190.192/26 的網段的數據包都發往網關 172.171.5.96。

因為 Pod1 在 5.95,Pod2 在 5.96。所以數據包就通過該路由發往到 Node 節點上。

Node 節點上路由信息:

K8S 的網絡架構弄清楚了嗎?

 

當 Node 節點網卡收到數據包之后,發現發往的目的 IP 為 192.168.190.203,于是匹配到紅線的路由(綠線是 Node 結點對應的發往 Master 的路由)。

該路由的意思是:192.168.190.203 是本機直連設備,去往設備的數據包發往 caliadce112d250。這個設備就是 Pod2 的 Veth Pair 的一端。

在創建 Pod2 時 Calico 會給 Pod2 創建一個 Veth Pair 設備。一端是 Pod2 的網卡,另一端就是我們看到的 caliadce112d250。

可以通過如下方式驗證:在 Pod2 中安裝 ethtool 工具,然后使用 ethtool-S eth0,查看 Veth Pair 另一端的設備號。

K8S 的網絡架構弄清楚了嗎?

 

Pod2 網卡另一端的設備編號是 18,在 Node 上查看編號為 18 的網絡設備,可以發現該網絡設備就是 caliadce112d250。

K8S 的網絡架構弄清楚了嗎?

 

所以,Node 上的路由,發送 caliadce112d250 的數據其實就是發送到 Pod2 的網卡中。Ping 包的旅行到這里就到了目的地。

查看一下 Pod2 中的路由信息,發現該路由信息和 Pod1 中是一樣的。

K8S 的網絡架構弄清楚了嗎?

 

顧名思義,IPIP 網絡就是將 IP 網絡封裝在 IP 網絡里。IPIP 網絡的特點是所有 Pod 的數據流量都從隧道 tunl0 發送,并且在 tunl0 這增加了一層傳輸層的封包。

在 Master 網卡上抓包分析該過程:

K8S 的網絡架構弄清楚了嗎?

 


K8S 的網絡架構弄清楚了嗎?

 

打開 ICMP 285,Pod1 Ping Pod2 的數據包,能夠看到該數據包一共 5 層,其中 IP 所在的網絡層有兩個,分別是 Pod 之間的網絡和主機之間的網絡封裝。

K8S 的網絡架構弄清楚了嗎?

 

根據數據包的封裝順序,應該是在 Pod1 Ping Pod2 的 ICMP 包外面多封裝了一層主機之間的數據包。

K8S 的網絡架構弄清楚了嗎?

 

之所以要這樣做是因為 tunl0 是一個隧道端點設備,在數據到達時要加上一層封裝,便于跨網段訪問。

兩層 IP 封裝的具體內容:

K8S 的網絡架構弄清楚了嗎?

 

IPIP 的連接方式:

K8S 的網絡架構弄清楚了嗎?

 

BGP 工作模式

①修改配置

在安裝 Calico 網絡時,默認安裝是 IPIP 網絡。calico.yaml 文件中,將 CALICO_IPV4POOL_IPIP 的值修改成"off",就能夠替換成 BGP 網絡。

K8S 的網絡架構弄清楚了嗎?

 

②對比

BGP 網絡相比較 IPIP 網絡,最大的不同之處就是沒有了隧道設備 tunl0,且不通過隧道設備發送流量。

前面介紹過 IPIP 網絡 Pod 之間的流量發送 tunl0,然后 tunl0 發送對端設備。BGP 網絡中,Pod 之間的流量直接從網卡發送目的地,減少了 tunl0 這個環境。

Master 節點上路由信息。從路由信息來看,沒有 tunl0 設備。

K8S 的網絡架構弄清楚了嗎?

 

同樣創建一個 Daemonset,Pod1 在 Master 節點上,Pod2 在 Node 節點上。

K8S 的網絡架構弄清楚了嗎?

 

③Ping 包旅程

Pod1 Ping Pod2:

K8S 的網絡架構弄清楚了嗎?

 

根據 Pod1 中的路由信息,Ping 包通過 eth0 網卡發送到 Master 節點上。

Master 節點上路由信息。根據匹配到的 192.168.190.192 路由,該路由的意思是:去往網段 192.168.190.192/26 的數據包,發送網段 172.171.5.96。

而 5.96 就是 Node 節點。所以,該數據包直接發送了 5.96 機器:

K8S 的網絡架構弄清楚了嗎?

 

Node 節點上的路由信息。根據匹配到的 192.168.190.192 的路由,數據將發送給 cali6fcd7d1702e 設備,該設備和上面分析的是一樣,為 Pod2 的 Veth Pair 的一端。數據就直接發送給 Pod2 的網卡。

K8S 的網絡架構弄清楚了嗎?

 

當 Pod2 對 Ping 包做出回應之后,數據到達 Node 節點上,匹配到 192.168.236.0 的路由。

該路由說的是:去往網段 192.168.236.0/26 的數據,發送給網關 172.171.5.95。數據包就直接通過網卡 ens160,發送到 Master 節點上。

K8S 的網絡架構弄清楚了嗎?

 

通過在 Master 節點上抓包,查看經過的流量,篩選出 ICMP,找到 Pod1 Ping Pod2 的數據包。

K8S 的網絡架構弄清楚了嗎?

 

可以看到 BGP 網絡下,沒有使用 IPIP 模式,數據包是正常的封裝。

K8S 的網絡架構弄清楚了嗎?

 

值得注意的是 Mac 地址的封裝。192.168.236.0 是 Pod1 的 IP,192.168.190.198 是 Pod2 的 IP。

而源 Mac 地址是 Master 節點網卡的 Mac,目的 Mac 是 Node 節點的網卡的 Mac。

這說明,在 Master 節點的路由接收到數據,重新構建數據包時,使用 ARP 請求,將 Node 節點的 Mac 拿到,然后封裝到數據鏈路層。

K8S 的網絡架構弄清楚了嗎?

 

BGP 的連接方式如下圖:

K8S 的網絡架構弄清楚了嗎?

 

網絡對比

IPIP 網絡:

  • 流量:tunlo 設備封裝數據,形成隧道,承載流量。
  • 適用網絡類型:適用于互相訪問的 Pod 不在同一個網段中,跨網段訪問的場景。外層封裝的 IP 能夠解決跨網段的路由問題。
  • 效率:流量需要 tunl0 設備封裝,效率略低。

BGP 網絡:

  • 流量:使用路由信息導向流量。
  • 適用網絡類型:適用于互相訪問的 Pod 在同一個網段,跨網段需要上行交換機或路由器支持。適用于大型網絡。
  • 效率:原生 HostGW,效率高。

存在問題

①租戶隔離問題

Calico 的三層方案是直接在 Host 上進行路由尋址,那么對于多租戶如果使用同一個 CIDR 網絡就面臨著地址沖突的問題。

②路由規模問題

通過路由規則可以看出,路由規模和 Pod 分布有關,如果 Pod 離散分布在 Host 集群中,勢必會產生較多的路由項。

③IPtables 規則規模問題

1 臺 Host 上可能虛擬化十幾或幾十個容器實例,過多的 IPtables 規則造成復雜性和不可調試性,同時也存在性能損耗。

④跨子網時的網關路由問題

當對端網絡不為二層可達時,需要通過三層路由時,需要網關支持自定義路由配置,即 Pod 的目的地址為本網段的網關地址,再由網關進行跨三層轉發。

K8S 網絡方案對比

以下對比為摘錄內容:

http://www.sohu.com/a/256113338_764649
K8S 的網絡架構弄清楚了嗎?

 


K8S 的網絡架構弄清楚了嗎?

 

關注微信公眾號:安徽思恒信息科技有限公司,了解更多技術內容……

分享到:
標簽:K8S
用戶無頭像

網友整理

注冊時間:

網站:5 個   小程序:0 個  文章:12 篇

  • 51998

    網站

  • 12

    小程序

  • 1030137

    文章

  • 747

    會員

趕快注冊賬號,推廣您的網站吧!
最新入駐小程序

數獨大挑戰2018-06-03

數獨一種數學游戲,玩家需要根據9

答題星2018-06-03

您可以通過答題星輕松地創建試卷

全階人生考試2018-06-03

各種考試題,題庫,初中,高中,大學四六

運動步數有氧達人2018-06-03

記錄運動步數,積累氧氣值。還可偷

每日養生app2018-06-03

每日養生,天天健康

體育訓練成績評定2018-06-03

通用課目體育訓練成績評定