淺談k8s網絡模型及不同node上Pod如何互訪

k8s網絡模型

接上一篇文章: Overlay和Underlay網絡協議區別及概述講解
Kubernetes 對容器技術做了更多的抽象,其中最重要的一點是提出 pod 的概念,pod 是 Kubernetes 資源調度的基本單元,我們可以簡單地認爲 pod 是容器的一種延伸擴展,從網絡的角度來看,pod 必須滿足以下條件:

  1. 每一個 pod 都有獨特的 IP 地址,所有 pod 都在一個可以直接連通的、扁平的網絡空間中;
  2. 同一個 pod 內的所有容器共享同一個網絡命名空間;
    image

基於這樣的基本要求,我們可以知道:

  1. 同一個 pod 內的所有容器之間共享端口,可直接通過 localhost + port 來訪問;
  2. 由於每個 pod 有單獨的 IP,所以不需要考慮容器端口與主機端口映射以及端口衝突問題;

事實上,Kubernetes 進一步確定了對一個合格集羣網絡的基本要求:

  1. 任意兩個 pod 之間其實是可以直接通信的,無需顯式地使用 NAT 進行地址的轉換;
  2. 任意集羣節點與任意 pod 之間是可以直接通信的,無需使用明顯的地址轉換,反之亦然;
  3. 任意 pod 看到自己的 IP 跟別人看見它所用的 IP 是一樣的,中間不能經過地址轉換;

也就是說,必須同時滿足以上三點的網絡模型才能適用於 Kubernetes,事實上,在早期的 Kubernetes 中,並沒有什麼網絡標準,只是提出了以上基本要求,只有滿足這些要求的網絡纔可以部署 Kubernetes,基於這樣的底層網絡假設,Kubernetes 設計了pod-deployment-service 的經典三層服務訪問機制。直到1.1發佈,Kubernetes 纔開始採用全新的 CNI(Container Network Interface) 網絡標準。

CNI

其實,我們在前面介紹容器網絡的時候,就提到了 CNI 網絡規範,CNI 相對於 CNM(Container Network Model) 對開發者的約束更少、更開放,不依賴於容器運行時。事實上,CNI 規範確實非常簡單,詳情可以參考github資料:https://github.com/containernetworking/cni/blob/master/SPEC.md
image

實現一個 CNI 網絡插件只需要一個配置文件和一個可執行文件:

  • 配置文件描述插件的版本、名稱、描述等基本信息;
  • 可執行文件會被上層的容器管理平臺調用,一個 CNI 可執行文件需要實現將容器加入到網絡的 ADD 操作以及將容器從網絡中刪除的 DEL 操作(以及一個可選的 VERSION 查看版本操作);

Kubernetes 使用 CNI 網絡插件的基本工作流程:

  1. kubelet 先創建 pause 容器創建對應的網絡命名空間;
  2. 根據配置調用具體的 CNI 插件,可以配置成 CNI 插件鏈來進行鏈式調用;
  3. 當 CNI 插件被調用時,它根據環境變量以及命令行參數來獲得網絡命名空間、容器的網絡設備等必要信息,然後執行 ADD 操作;
  4. CNI 插件給 pause 容器配置正確的網絡,pod 中其他的容器都是複用 pause 容器的網絡;

如果不清楚什麼是 pause 容器,它在pod中處於什麼樣的位置,請查看從 container 到 pod。

通常來說,CNI 插件可以分爲三種:Overlay、路由及 Underlay。
image

  • Overlay 模式的典型特徵是容器獨立於主機的 IP 段,這個 IP 段進行跨主機網絡通信時是通過在主機之間創建隧道的方式,將整個容器網段的包全都封裝成底層的物理網絡中主機之間的包。該方式的好處在於它不依賴於底層網絡;

  • 路由模式中主機和容器也分屬不同的網段,它與 Overlay 模式的主要區別在於它的跨主機通信是通過路由打通,無需在不同主機之間做一個隧道封包。但路由打通就需要部分依賴於底層網絡,比如說要求底層網絡有二層可達的一個能力;

  • Underlay 模式中容器和宿主機位於同一層網絡,兩者擁有相同的地位。容器之間網絡的打通主要依靠於底層網絡。因此該模式是強依賴於底層能力的。

瞭解了以上三種常用的實現模式之後,再根據自己的環境、需求判斷可由哪一種模式進行實現,再在對應的模式中去找 CNI 插件。不過社區中有那麼多插件,它們又都屬於哪種模式?如何進行選擇呢?怎麼挑選適合自己的呢?我們可以從以下 3 個方面來考慮。

pod 網絡模型

要了解 Kubernetes 網絡模型的實現原理,我們就要從單個 pod 入手,事實上,一旦熟悉了單個 pod 的網絡模型,就會發現 Kubernetes 網絡模型基本遵循和容器網絡模型一樣的原理。

通過前面的筆記從 container 到 pod,我們知道 pod 啓動的時候先創建 pause 容器創建對應的網絡命名空間,然後與其他容器共享此網絡命名空間。而對於單個容器的網絡模型我們之前也介紹過,主要就是通過 docker0 網橋設備與 veth 設備對連接不同的容器網絡命名空間,由此,我們可以得到如下圖所示的單個 pod 網絡模型:
image

主流 Kubernetes 網絡實現方案

上一小節我們知道單個 pod 的網絡模型是容器網絡模型的擴展,但是 pod 與 pod 之間的是怎麼相互通信的呢?這其實與容器之間相互通信非常類似,也分爲同一個主機上的 pod 之間與跨主機的 pod 之間兩種情況。

如容器網絡模型一樣,對於同一主機上的 pod 之間,通過 docker0 網橋設備直接二層(數據鏈路層)網絡上通過 MAC 地址直接通信:
image

而跨主機的 pod 之間的相互通信也主要有以下兩個思路:

  1. 修改底層網絡設備配置,加入容器網絡 IP 地址的管理,修改路由器網關等,該方式主要和 SDN(Software define networking) 結合。

  2. 完全不修改底層網絡設備配置,複用原有的 underlay 網絡平面,解決容器跨主機通信,主要有如下兩種方式:

  • 隧道傳輸(overlay):將容器的數據包封裝到原主機網絡的三層或者四層數據包中,然後使用主機網絡的 IP 或者 TCP/UDP 傳輸到目標主機,目標主機拆包後再轉發給目標容器。overlay 隧道傳輸常見方案包括 Vxlan、ipip 等,目前使用 overlay 隧道傳輸技術的主流容器網絡有 Flannel 等;
    image

  • 修改主機路由:把容器網絡加到主機路由表中,把主機網絡設備當作容器網關,通過路由規則轉發到指定的主機,實現容器的三層互通。目前通過路由技術實現容器跨主機通信的網絡如 Flannel host-gw、Calico 等;
    image

下面簡單介紹幾種主流的方案:

  • **Flannel **是目前使用最爲普遍的方案,提供了多種網絡後端,它支持多種數據路徑,也適合於 overlay/underlay 等多種場景。對於 overlay 的數據包封裝,可以使用用戶態的 UDP,內核態的 Vxlan(性能相對較好),甚至在集羣規模不大,且處於同一個二層域時可以採用 host-gw 的方式修改主機路由表;

  • **Weave **工作模式與 Flannel 很相似的,它最早只提供了 UDP(稱爲 sleeve 模式)的網絡方式,後來又加上了 fastpass 方式(基於 VxLAN),不過 Weave 消除了 Flannel 中用來存儲網絡地址的額外組件,自己集成了高可用的數據存儲功能;

  • **Calico ** 主要是採用了修改主機路由,節點之間採用 BGP 的協議去進行路由的同步,但是現實中的網絡並不總是支持 BGP 路由的,因此 Calico 也支持內核中的 IPIP 模式,使用 overlay 的方式來傳輸數據;

可以看到,同一個 pod 裏面的其他容器共享 pause 容器創建的網絡命名空間,也就是說,所有的容器共享相同的網絡設備、路由表設置、服務端口等信息,彷彿是在同一臺機器上運行的不同進程,所以這些容器之間可以直接通過 localhost + port 通信;對於集羣外部的請求,則通過 docker0 網橋設備充當的網關,同時通過 iptables 做地址轉換。到這裏我們就會發現,這其實就是對單個容器的 bridge 網絡模型的擴展。

Pod間如何互訪

容器到容器的通信

同一個Pod內的容器可以用localhost地址訪問彼此的端口。
image

Pod之間的通信
同一個Node內Pod之間的通信
image

不同Node上Pod之間的通信
image

總結
今天的數據中心包含多個集羣以及海量的物理機,Overlay 網絡是虛擬機和底層網絡設備之間的中間層,通過 Overlay 網絡這一個中間層,我們可以解決虛擬機的遷移問題、降低二層核心網絡設備的壓力並提供更大規模的虛擬網絡數量:

  • 在使用 VxLAN 構成二層網絡中,虛擬機在不同集羣、不同可用區和不同數據中心遷移後,仍然可以保證二層網絡的可達性,這能夠幫助我們保證線上業務的可用性、提升集羣的資源利用率、容忍虛擬機和節點的故障;

  • 集羣中虛擬機的規模可能是物理機是幾十倍,與物理機構成的傳統集羣相比,虛擬機構成的集羣包含的 MAC 地址數量可能多一兩個數量級,網絡設備很難承擔如此大規模的二層網絡請求,Overlay 網絡通過 IP 封包和控制平面可以減少集羣中的 MAC 地址表項和 ARP 請求;

  • VxLAN 的協議頭使用 24 位的 VNI 表示虛擬網絡,總共可以表示 1600 萬的虛擬網絡,我們可以爲不同的虛擬網絡單獨分配網絡帶寬,滿足多租戶的網絡隔離需求;

需要注意的是,Overlay 網絡只是一種在物理網絡上的虛擬網絡,使用該技術並不能直接解決集羣中的規模性等問題,而 VxLAN 也不是組建 Overlay 網絡的唯一方法,在不同場景中我們可以考慮使用不同的技術,例如:NVGRE、GRE 等。

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章