Kubernetes網絡組件之Calico策略實踐(BGP、RR、IPIP)


Pod 1 訪問 Pod 2大致流程如下:
數據包從容器1出到達Veth Pair另一端(宿主機上,以cali前綴開頭);
宿主機根據路由規則,將數據包轉發給下一跳(網關);
到達Node2,根據路由規則將數據包轉發給cali設備,從而到達容器2。

其中,這里最核心的“下一跳”路由規則,就是由 Calico 的 Felix 進程負責維護的。這些路由規則信息,則是通過 BGP Client 也就是 BIRD 組件,使用 BGP 協議傳輸而來的。
不難發現,Calico 項目實際上將集群里的所有節點,都當作是邊界路由器來處理,它們一起組成了一個全連通的網絡,互相之間通過 BGP 協議交換路由規則。這些節點,我們稱為 BGP Peer。

而host-gw和calico的唯一不一樣的地方就是當數據包下一跳到達node2節點的容器的時候發生變化了,並且出數據包也發生變化了,我們知道它是從veth的設備對讓容器里面的數據包到達宿主機上數據包,這個數據包到達node2之后,它又根據一個特殊的路由規則,這個會記錄目的通信地址的cni網絡,然后通過cali的設備進去容器,這個就跟網線一樣,數據包通過這個網線發到容器中,這也是一個二層的網絡互通才能實現,如果二層不通的就可以使用IPIP模式了,

calico沒有網橋數據包是怎么出去的?
pod1的數據包從veth的設備對到到宿主機的一段eth0上,之前的數據包其實是走的默認宿主機的網關將流量轉發到calico的cali的設備上的,通過路由表信息下一跳地址到宿主機然后轉發到對應的容器中

6、Route Reflector 模式(RR)(路由反射)
https://docs.projectcalico.org/master/networking/bgp
Calico 維護的網絡在默認是(Node-to-Node Mesh)全互聯模式,Calico集群中的節點之間都會相互建立連接,用於路由交換。但是隨着集群規模的擴大,mesh模式將形成一個巨大服務網格,連接數成倍增加。
這時就需要使用 Route Reflector(路由器反射)模式解決這個問題。
確定一個或多個Calico節點充當路由反射器,讓其他節點從這個RR節點獲取路由信息。

在BGP中可以通過calicoctl node status看到啟動是node-to-node mesh網格的形式,這種形式是一個全互聯的模式,默認的BGP在k8s的每個節點擔任了一個BGP的一個喇叭,一直吆喝着擴散到其他節點,隨着集群節點的數量的增加,那么上百台節點就要構建上百台鏈接,就是全互聯的方式,都要來回建立連接來保證網絡的互通性,那么增加一個節點就要成倍的增加這種鏈接保證網絡的互通性,這樣的話就會使用大量的網絡消耗,所以這時就需要使用Route reflector,也就是找幾個大的節點,讓他們去這個大的節點建立連接,也叫RR,也就是公司的員工沒有微信群的時候,找每個人溝通都很麻煩,那么建個群,里面的人都能收到,所以要找節點或着多個節點充當路由反射器,建議至少是2到3個,一個做備用,一個在維護的時候不影響其他的使用。

具體步驟如下:
1、關閉 node-to-node BGP網格
添加 default BGP配置,調整 nodeToNodeMeshEnabled和asNumber:

[root@k8s-master1 calico]# cat bgp.yaml 
 apiVersion: projectcalico.org/v3
 kind: BGPConfiguration
 metadata:
   name: default
 spec:
   logSeverityScreen: Info
   nodeToNodeMeshEnabled: false  
   asNumber: 63400

直接應用一下,當我們禁用node-to-node mesh的時候,網絡立馬就會斷,所以斷的話要提前做好影響的范圍,也就是切換這個網絡是需要斷網的,使用node-to-node BGP這種也是建議100個節點以下,當超過100台節點一定要使用路由反射RR模式

[root@k8s-master1 calico]# calicoctl apply -f bgp.yaml 
Successfully applied 1 'BGPConfiguration' resource(s)

查看bgp網絡配置情況,false為關閉

[root@k8s-master1 calico]# calicoctl get bgpconfig
NAME      LOGSEVERITY   MESHENABLED   ASNUMBER   
default   Info          false         63400 

去查看pod的網絡測試已經斷開了,這里是因為我們使用caclico的配置禁用了node-to-node mesh了

[root@k8s-master1 calico]# ping 10.244.245.2
PING 10.244.245.2 (10.244.245.2) 56(84) bytes of data.

ASN號可以通過獲取 # calicoctl get nodes --output=wide
這里有個編號,ASN64300,一個編號就是一個自治系統

[root@k8s-master1 calico]# calicoctl get nodes --output=wide
NAME                ASN       IPV4           IPV6   
k8s-master1   (63400)   10.4.7.11/24          
k8s-node1   (63400)   10.4.7.12/24          
k8s-node2   (63400)   10.4.7.21/24 

2、配置指定節點充當路由反射器
為方便讓BGPPeer輕松選擇節點,通過標簽選擇器匹配,也就是可以去調用k8s里面的標簽進行關聯,我們可以給哪個節點作為路由發射器打個標簽
給路由器反射器節點打標簽,我這將node1打上標簽
[root@k8s-master1 calico]# kubectl label node k8s-node1 route-reflector=true

查看node BJP的節點狀態,因為禁用了網格,所以這里都關閉了,所以也就不通了。

[root@k8s-master1 calico]# calicoctl node status
Calico process is running.

IPv4 BGP status
No IPv4 peers found.

IPv6 BGP status
No IPv6 peers found.

然后配置路由器反射器節點routeReflectorClusterID,增加一個集群節點的ID
下面的可以通過-o yaml輸出出來

[root@k8s-master1 calico]# calicoctl get node k8s-node2 -o yaml > node.yaml

apiVersion: projectcalico.org/v3
kind: Node
metadata:
  annotations:
    projectcalico.org/kube-labels: '{"beta.kubernetes.io/arch":"amd64","beta.kubernetes.io/os":"linux","kubernetes.io/arch":"amd64","kubernetes.io/hostname":"k8s-node2","kubernetes.io/os":"linux"}'
  creationTimestamp: null
  labels:
    beta.kubernetes.io/arch: amd64
    beta.kubernetes.io/os: linux
    kubernetes.io/arch: amd64
    kubernetes.io/hostname: k8s-node2
    kubernetes.io/os: linux
  name: k8s-node2
spec:
  bgp:
    ipv4Address: 10.4.7.12/24
    routeReflectorClusterID: 244.0.0.1   # 集群ID
  orchRefs:
  - nodeName: k8s-node2
    orchestrator: k8s

應用一下
[root@k8s-master1 calico]# calicoctl apply -f node.yaml
現在,很容易使用標簽選擇器將路由反射器節點與其他非路由反射器節點配置為對等:現在也就是將其他的節點去連接這個k8s-node1打標簽的路由發射器

[root@k8s-master1 calico]# cat bgp1.yaml 
apiVersion: projectcalico.org/v3
kind: BGPPeer
metadata:
  name: peer-with-route-reflectors
spec:
  nodeSelector: all()    #所以的節點
  peerSelector: route-reflector == 'true' 

#就是帶route-reflector的都去連接匹配這個,剛才我們不是打上標簽了嘛,所以需要我們去連接這個路由反射器
查看節點的BGP規則與連接狀態,這樣的話就顯示一個路由反射器的節點

[root@k8s-master1 calico]# calicoctl apply -f bgp1.yaml 
Successfully applied 1 'BGPPeer' resource(s)
[root@k8s-master1 calico]# calicoctl get bgppeer
NAME                         PEERIP   NODE    ASN   
peer-with-route-reflectors            all()   0     
[root@k8s-master1 calico]# calicoctl node status
Calico process is running.

IPv4 BGP status
+--------------+---------------+-------+----------+-------------+
| PEER ADDRESS |   PEER TYPE   | STATE |  SINCE   |    INFO     |
+--------------+---------------+-------+----------+-------------+
| 10.4.7.12    | node specific | up    | 08:22:22 | Established |
+--------------+---------------+-------+----------+-------------+

IPv6 BGP status
No IPv6 peers found.

查看容器網絡聯通性

[root@k8s-master1 calico]# ping 10.244.203.80
PING 10.244.203.80 (10.244.203.80) 56(84) bytes of data.
64 bytes from 10.244.203.80: icmp_seq=1 ttl=63 time=1.71 ms

添加多個路由反射器
現在進行對路由反射器添加多個,100個節點以內建議2-3個路由反射器
1)進行對集群節點打標簽

[root@k8s-master1 calico]# kubectl label node k8s-node2 route-reflector=true
node/k8s-node2 labeled

2)對k8s-node2添加然后配置路由器反射器節點
[root@k8s-master1 calico]# calicoctl get node k8s-node2 -o yaml
3)查看節點狀態

[root@k8s-master1 calico]# calicoctl node status
Calico process is running.

IPv4 BGP status
+--------------+---------------+-------+----------+-------------+
| PEER ADDRESS |   PEER TYPE   | STATE |  SINCE   |    INFO     |
+--------------+---------------+-------+----------+-------------+
| 10.4.7.12    | node specific | up    | 08:22:22 | Established |
| 10.4.7.21    | node specific | up    | 08:44:44 | Established |
+--------------+---------------+-------+----------+-------------+

IPv6 BGP status
No IPv6 peers found.

4)測試網絡連通性

[root@k8s-master1 calico]# ping 10.244.203.81
PING 10.244.203.81 (10.244.203.81) 56(84) bytes of data.
64 bytes from 10.244.203.81: icmp_seq=1 ttl=63 time=12.7 ms
64 bytes from 10.244.203.81: icmp_seq=2 ttl=63 time=1.40 ms

所以這是使用路由反射器來解決節點增多BGP帶來的消耗
7、IPIP模式

ipip模式與flannel的vxlan模式類似,這個也是對數據包的一個封裝
在前面提到過,Flannel host-gw 模式最主要的限制,就是要求集群宿主機之間是二層連通的。而這個限制對於 Calico 來說,也同樣存在,也是不能跨vlan的,主要局限就是數據包主要封裝的是容器,源IP和目的IP,因為它們工作都是使用的二層,所以二層它不會考慮容器之間進行數據包轉發的,但如果添加路由表,將目的的IP通過靜態路由的方式也能實現,不同vlan的數據的通信,不過這種方式目前沒有測試。

另外還有一個弊端,會發現calico的路由表比flannel的多一些,因為它里面還要加一些傳入過來的到設備的路由表信息,就是每個pod都加一個路由表,所以它的路由表的量也比flannel大不少。
修改為IPIP模式:

calicoctl get ippool -o yaml > ipip.yaml
vi ipip.yaml
apiVersion: projectcalico.org/v3
kind: IPPool
metadata:
  name: default-ipv4-ippool
spec:
  blockSize: 26
  cidr: 10.244.0.0/16
  ipipMode: Always
  natOutgoing: true

calicoctl apply -f ipip.yaml

創建好之后查看詳細信息,已經開啟ippool

[root@k8s-master1 calico]# calicoctl get ippool -o wide
NAME                  CIDR            NAT    IPIPMODE   VXLANMODE   DISABLED   SELECTOR   
default-ipv4-ippool   10.244.0.0/16   true   Always     Never       false      all() 

查看網絡設備會增加一個tunl0,增加了一個隧道的網卡

 tunl0@NONE: <NOARP,UP,LOWER_UP> mtu 1440 qdisc noqueue state UNKNOWN group default qlen 1000
    link/ipip 0.0.0.0 brd 0.0.0.0
    inet 10.244.113.131/32 brd 10.244.113.131 scope global tunl0
       valid_lft forever preferred_lft forever

IPIP示意圖:
Kubernetes網絡組件之Calico策略實踐(BGP、RR、IPIP)

那么有這么一個需求,有兩個不同vlan,因為需要突破2層,現在有兩個vlan,這兩個vlan它本身是三層可達的,三層可達就必須要借助路由器,也就是這兩個節點,部署k8s集群可能是兩個vlan里面的,但是它們網絡是通的,你也可以組建成一個集群,但是要使用calico的BGP,如果只讓它們三層可達的話,與BJP也是不可以用的,因為BJP使用的二層,因為數據源IP和目的IP都是pod的IP,而這個路由器並不知道這個源IP和目的IP應該發給誰,因為這沒有寫這個路由表信息,如果寫了,理論上來講節點不同網段也是可以通信的,那么不添加這個路由表的話,這個BGP是過不去的,那么這種情況下就得去啟用ipip模式了,IPIP是linux內核的驅動程序,可以對數據包進行隧道,那么它看到兩個不同的網絡vlan1和vlan2,啟動ipip模式也有個前提,它是屬於4層的,因為它是基於現有的以太網的網絡將你原來包里的原始IP,也是進行一次封裝,因為現有的網絡已經通了,三層的路由現實不同的vlan進行通信,所以通過tunl0解包,這個tunl0類似於ipip模塊,這個就跟vxlan的veth類似,所以這個模式跟vxlan的模式大致是一樣的

Pod 1 訪問 Pod 2大致流程如下:
數據包從容器1出到達Veth Pair另一端(宿主機上,以cali前綴開頭);
進入IP隧道設備(tunl0),由Linux內核IPIP驅動封裝在宿主機網絡的IP包中(新的IP包目的地之是原IP包的下一跳地址,即192.168.31.63),這樣,就成了Node1 到Node2的數據包;

     此時包的類型:
       原始IP包:
       源IP:10.244.1.10
       目的IP:10.244.2.10

        TCP:
        源IP: 192.168.31.62
        目的iP:192.168.32.63

那么這個IPIP本身和vxlan一樣,工作在三層的,因為它用現在的以太網進行傳輸的,現在物理機傳輸的,路由器這個方面達到另一個vlan2,這個網絡之間肯定是可以訪問的,那么IPIP之間就能和三層的路由到目的另一個vlan中
數據包經過路由器三層轉發到Node2;
Node2收到數據包后,網絡協議棧會使用IPIP驅動進行解包,從中拿到原始IP包;
然后根據路由規則,根據路由規則將數據包轉發給cali設備,從而到達容器2。
路由表:

[root@k8s-node1 ~]# ip route
default via 10.4.7.1 dev eth0 proto static metric 100 
10.4.7.0/24 dev eth0 proto kernel scope link src 10.4.7.12 metric 100 
10.244.113.128/26 via 10.4.7.11 dev tunl0 proto bird onlink 
10.244.203.64/26 via 10.4.7.21 dev tunl0 proto bird onlink 
blackhole 10.244.245.0/26 proto bird 
10.244.245.1 dev calie1d6cd79d22 scope link 
10.244.245.2 dev calid6a1fb2294e scope link 
172.17.0.0/16 dev docker0 proto kernel scope link src 172.17.0.1 

不難看到,當 Calico 使用 IPIP 模式的時候,集群的網絡性能會因為額外的封包和解包工作而下降。所以建議你將所有宿主機節點放在一個子網里,避免使用 IPIP。
8、CNI 網絡方案優缺點及最終選擇
先考慮幾個問題:
需要細粒度網絡訪問控制?這個flannel是不支持的,calico支持,所以做多租戶網絡方面的控制ACL,那么要選擇calico
追求網絡性能?這兩個方案無疑是flannel和calico的路由方案是最高的,也就是flannel的host-gw和calico的BGP。
服務器之前是否可以跑BGP協議?很多的公有雲是不支持跑BGP協議的,那么使用calico的BGP模式自然是不行的。
集群規模多大?如果規模不大,100節點以下維護起來比較方面之間可以使用flannel就可以
是否有維護能力?calico的路由表很多,而且走BGP協議,一旦出現問題排查起來也比較困難,上百台的,路由表去排查也是很麻煩,這個具體的需求也是跟自己餓的情況而定。

小話題:辦公網絡與k8s網絡如何互通
現在架構也是微服務也比較流行,測試環境是在k8s集群中,開發人員是在辦公網絡中,網絡顯然是不同的,微服務是使用pod去通信的,辦公網絡訪問pod自然是不同的,那么就需要將這個網絡打通。

比如開發開發了一個微服務,不想啟動整套,注冊中心,服務發現了等等,但是它只想跑一個模塊,直接調用測試環境中注冊中心數據庫了直接去用,那么就要考慮將這個網絡打通了
比如一塊是辦公網絡,然后開發人家使用的開發電腦,另一塊是k8s集群跑着很多的微服務,那么pod的ip是10.244.0.0/16這個網段,那么service是10.0.0.10/24,宿主機是172.17.0.0/24,那么辦公網絡是192.168.1.0/24

----------------------------------                
|   「pc」      「pc」         |
|   「pc」      「pc」         |                     辦公網絡:192.168.1.0/24
|             辦公                    |
----------------------------------
----------------------------------
|   「pod」      「pod」     |                    pod IP     10.244.0.0/16
|   「pod」      「pod」     |                    service IP 10.0.0.10/24
|             k8s集群               |                    宿主機 IP  172.17.0.0/24
----------------------------------

那么辦公網絡去訪問pod的IP肯定是不通的,除非做了路由,即使辦公網絡和k8s的宿主機網絡能通,但是也需要做一些特殊的轉發策略,現在解決的問題是辦公網絡可以訪問pod的IP,訪問service的IP,也就是讓k8s內部的網絡暴露出來,辦公網絡就像之間訪問虛擬機一樣去訪問,所以去解決這個問題,分為兩種情況。

第一種情況,k8s集群測試環境在辦公網絡的子網里面,那么這個實現就比較簡單了,只需要在子網中上層的路由器添加一個規則就行了,ip route add,目的IP為10.244.0.0/16,到達的下一跳via為其中的k8s節點,比如k8s-node1 dev 接口A
ip route add 10.244.0.0/16 via <k8s-node1> dev A
添加這么一個規則,辦公網絡就能直接訪問k8s的節點,直接就能訪問pod IP,也就是下一跳地址之后,就能直接訪問都podIP了。

第二種情況,k8s集群與辦公網絡在不同VLAN中,不同機房
前提是k8s集群與辦公網絡是互通的,三層可達
有兩種方案1)在路由器上添加路由表,10.244.0.0/16 <k8s-node1>
2) 采用BGP,如果三層的路由支持BGP協議的話,直接就可以讓路由器BGP與路由反射器BGP建立連接,這樣的話路由器上的BGP就能獲取到了k8s上的路由表信息了,然后經過下一跳來轉發到目的的node的pod中。
總結:只要是不同vlan,必須是三層可達,能在上層的路由器上,訪問集群的網段,pod網段還是service網段,一定要告知它,幫它轉發到下一跳是誰,下一跳如果是目的的節點,那就直接轉發數據包。

4.5 網絡策略
1、為什么需要網絡隔離?
CNI插件插件解決了不同Node節點Pod互通問題,從而形成一個扁平化網絡,默認情況下,Kubernetes 網絡允許所有 Pod 到 Pod 的流量,也就是在k8s網絡中都是相互ping通,都是可以訪問傳輸數據包的,在一些場景中,我們不希望Pod之間默認相互訪問,例如:
應用程序間的訪問控制。例如微服務A允許訪問微服務B,微服務C不能訪問微服務A
開發環境命名空間不能訪問測試環境命名空間Pod
當Pod暴露到外部時,需要做Pod白名單
多租戶網絡環境隔離

比如這個命名空間與其他的命名空間進行互通,將你的pod暴露在外面了暴露在辦公網絡中了,為了方便,但是提高一些安全性,那么誰能訪問,誰不能訪問,直接做白名單也可以,然后微服務部署的也比較多,也希望做一些隔離,那么也可以使用網絡隔離,那么就可以使用network policy進行pod網絡的隔離。

既然說到了網絡的限制也就是ACP訪問控制,自然是有兩個方向,一個是入口方向,一個是出口方向
一個用戶去訪問虛擬機,客戶端訪問這是入方向,對於客戶端來說這是出方向,虛擬機訪問外網自然是出方向,做ACL一個是入方向,一個是出方向,我們針對pod做誰能訪問pod,pod能訪問誰。

所以,我們需要使用network policy對Pod網絡進行隔離。支持對Pod級別和Namespace級別網絡訪問控制。
Pod網絡入口方向隔離
基於Pod級網絡隔離:只允許特定對象訪問Pod(使用標簽定義),允許白名單上的IP地址或者IP段訪問Pod
基於Namespace級網絡隔離:多個命名空間,A和B命名空間Pod完全隔離。
Pod網絡出口方向隔離
拒絕某個Namespace上所有Pod訪問外部
基於目的IP的網絡隔離:只允許Pod訪問白名單上的IP地址或者IP段
基於目標端口的網絡隔離:只允許Pod訪問白名單上的端口
2、網絡策略概述
一個NetworkPolicy例子:

apiVersion: networking.k8s.io/v1
kind: NetworkPolicy
metadata:
  name: test-network-policy
  namespace: default
spec:
  podSelector:
    matchLabels:
      role: db
  policyTypes:
  - Ingress
  - Egress
  ingress:
  - from:
    - ipBlock:
        cidr: 172.17.0.0/16
        except:
        - 172.17.1.0/24
    - namespaceSelector:
        matchLabels:
          project: myproject
    - podSelector:
        matchLabels:
          role: frontend
    ports:
    - protocol: TCP
      port: 6379
  egress:
  - to:
    - ipBlock:
        cidr: 10.0.0.0/24
    ports:
    - protocol: TCP
      port: 5978

配置解析:
podSelector:用於選擇策略應用到的Pod組,也就是對哪個pod進行網絡隔離
policyTypes:其可以包括任一Ingress,Egress或兩者。該policyTypes字段指示給定的策略用於Pod的入站流量、還是出站流量,或者兩者都應用。如果未指定任何值,則默認值為Ingress,如果網絡策略有出口規則,則設置egress,這個也就是入口方向和出口方向,限制入口或者限制出口方向
Ingress:from是可以訪問的白名單,可以來自於IP段、命名空間、Pod標簽等,ports是可以訪問的端口。入口的策略是什么,入口的策略是這么限制的,
Egress:這個Pod組可以訪問外部的IP段和端口。出的策略是這么限制的,pod出去是這么限制的,是訪問百度的ip,還是訪問其他的ip,是哪個ip段還是哪個命名空間。
在172.17.0.0/16這個大子網里面除了這個172.17.1.0/24這個不能訪問,其他的都能訪問,命名空間也是可以哪個可以訪問,哪個不可以訪問。
cidr: 172.17.0.0/16
except:

  • 172.17.1.0/24
    pod還能定義你可以訪問我哪個端口,這是出口策略的定義,就是出去可以訪問誰,訪問哪個ip段的端口
    ports:
    • protocol: TCP
      port: 6379

根據上面的yaml的規則來說,結構是這樣的,對pod命名空間的攜帶標簽role:db的pod進行網絡隔離,只有172.17.0.0/16子網下除了172.17.1.0/24其他的都可以訪問我,

  • namespaceSelector:
    matchLabels:
    project: myproject
    • podSelector:
      matchLabels:
      role: frontend
      這個命名空間可以訪問我,攜帶role:frontend的也可以訪問我,這些只能訪問我6379的端口,本身自己只能訪問10.0.0.0/24IP段的ip的5978端口。
      3、入站、出站網絡流量訪問控制案例
      現在做對pod的訪問限制
      Pod訪問限制
      准備測試環境,一個web pod,兩個client pod
      kubectl create deployment nginx --image=nginx
      kubectl run client1 --generator=run-pod/v1 --image=busybox --command -- sleep 36000
      kubectl run client2 --generator=run-pod/v1 --image=busybox --command -- sleep 36000
      kubectl get pods --show-labels

      需求:將default命名空間攜帶run=nginx標簽的Pod隔離,只允許default命名空間攜帶run=client1標簽的Pod訪問80端口

apiVersion: networking.k8s.io/v1
kind: NetworkPolicy
metadata:
  name: test-network-policy
  namespace: default
spec:
  podSelector:
    matchLabels:
      app: nginx
  policyTypes:
  - Ingress
  ingress:
  - from:
    - namespaceSelector:
        matchLabels:
          project: default 
    - podSelector:
        matchLabels:
          run: client1
    ports:
    - protocol: TCP
      port: 80

隔離策略配置:
Pod對象:default命名空間攜帶run=nginx標簽的Pod
允許訪問端口:80
允許訪問對象:default命名空間攜帶run=client1標簽的Pod
拒絕訪問對象:除允許訪問對象外的所有對象

測試查看現在client的網絡是不能通信的,而這個組件calico支持,像其他的flannel組件是不支持的
命名空間隔離
需求:default命名空間下所有pod可以互相訪問,但不能訪問其他命名空間Pod,其他命名空間也不能訪問default命名空間Pod。

[root@k8s-master1 ~]# kubectl run client3 --generator=run-pod/v1 --image=busybox -n kube-system --command -- sleep 36000
default的pod都能互通,kube-system的pod不能與default的pod互通,default也不能訪問kube-system的pod,也就是自己隔離到了自己網絡命名空間下了
現在我們實現一下這個需求,創建好之后因為我們沒有限制網絡的隔離,所以默認情況下不同命名空間的網絡也是互通的
創建一個default下的pod名字為nginx的pod

[root@k8s-master1 ~]# kubectl get pod -o wide
NAME                                      READY   STATUS    RESTARTS   AGE     IP               NODE          NOMINATED NODE   READINESS GATES
nginx-86c57db685-cv627                    1/1     Running   0          5m57s   10.244.113.132   k8s-master1   <none>           <none
[root@k8s-master1 ~]# kubectl exec -it client3 -n kube-system /bin/sh
/ # ping 10.244.113.132
PING 10.244.113.132 (10.244.113.132): 56 data bytes
64 bytes from 10.244.113.132: seq=0 ttl=62 time=3.105 ms
64 bytes from 10.244.113.132: seq=1 ttl=62 time=13.029 ms

創建網絡隔離yaml,實現default和kube-system下的pod不能互通

[root@k8s-master1 ~]# cat ns.yaml
apiVersion: networking.k8s.io/v1
kind: NetworkPolicy
metadata:
  name: deny-from-other-namespaces 
  namespace: default
spec:
  podSelector: {}
  policyTypes:
  - Ingress
  ingress:
  - from:
    - podSelector: {}

[root@k8s-master1 ~]# kubectl apply -f ns.yaml 
networkpolicy.networking.k8s.io/deny-from-other-namespaces created

測試之后現在已經無法訪問default下的pod了,這也就實現的網絡隔離,相反反過來也不通

[root@k8s-master1 ~]# kubectl exec -it client3 -n kube-system /bin/sh
/ # ping 10.244.113.132
PING 10.244.113.132 (10.244.113.132): 56 data bytes

podSelector: {}:default命名空間下所有Pod
from.podSelector: {} : 如果未配置具體的規則,默認不允許

 

參考

https://blog.csdn.net/cichaohuai7500/article/details/100984497

https://blog.51cto.com/u_14143894/2463392


免責聲明!

本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



 
粵ICP備18138465號   © 2018-2025 CODEPRJ.COM