Kubernetes Pod 資源共享實現機制
Pod基本概念
Pod是Kubernetes建立和管理的最小單元,一個Pod由一個容器或多個容器組成,這些容器共享儲存、網路。
Pod特點
• 一個Pod可以理解為是一個應用例項,提供服務
• Pod中容器始終部署在一個Node上 • Pod中容器共享網路、儲存資源
• Kubernetes直接管理Pod,而不是容器
Pod就是豌豆莢,裡面的豆子可以理解為容器,一個pod可以理解為一個應用提供具體的某個服務。
Pod主要用法:
• 執行單個容器:最常見的用法,在這種情況下,可以將Pod看做是單個容器的抽象封裝
• 執行多個容器:封裝多個緊密耦合且需要共享資源的應用程式(這就是引入Pod的意義了)
如果有這些需求,你可以執行多個容器:
• 兩個應用之間發生檔案互動
• 兩個應用需要通過127.0.0.1或者socket通訊
• 兩個應用需要發生頻繁的呼叫
Pod資源共享實現機制
容器之間是通過namespace之間去隔離的,之間的網路是隔離的,檔案系統是隔離的,難道在pod當中兩個容器也不能相互通訊了嗎?彷彿又回到了docker各個容器之間都是隔離的。
Pod要解決網路和檔案系統的問題其實就要打破namespace的隔離。
怎麼解決兩個容器之間通訊的問題呢?也即是容器之間看到的網路協議棧是一樣的,在建立pod的時候會先建立infra container這個容器,啟動好之後然後再將實際建立的pod加入到infra container容器當中,這個容器實現的主要目的是維護了pod的網路,沒有跑任何的業務邏輯,只是啟動了一個容器罷了。其他容器的建立都讓其連線至該容器的網路名稱空間當中。這樣一來其他容器看到的網路檢視就是infra container的網路檢視了。一個pod當中所有的容器看到的網路裝置,網絡卡,ip,mac地址都看到的是同一個了,因為在一個網路名稱空間。這樣就解決了網路共享的問題。實際上pod的ip就是infra container的ip。(加入infra container名稱空間實現網路共享,同一個網路協議棧)
兩個容器的檔案系統也是隔離的,k8s引入了資料卷volume,通過pod當中的不同容器去掛載這個捲來實現共享某些資料。
[root@k8s-master ~]# cat pod-network.yml apiVersion: v1 kind: Pod metadata: labels: app: test name: pod-network-test namespace: default spec: containers: - image: busybox name: busybox command: ["/bin/sh","-c","sleep 3600"] - image: nginx name: nginx [root@k8s-master ~]# kubectl get pod NAME READY STATUS RESTARTS AGE pod-network-test 2/2 Running 0 117s [root@k8s-master ~]# kubectl describe pod pod-network-test 如果啟動不了使用該命令檢視Pod具體資訊
正常情況busybox和nginx是網路隔離的,也就是在busybox裡面訪問127.0.0.1裡面訪問nginx是訪問不到的。
如果pod當中包含有多個容器需要使用-c指定進入哪個容器
[root@k8s-master ~]# kubectl exec -it pod-network-test -c busybox -- sh / # netstat -tpln Active Internet connections (only servers) Proto Recv-Q Send-Q Local Address Foreign Address State PID/Program name tcp 0 0 0.0.0.0:80 0.0.0.0:* LISTEN - tcp 0 0 :::80 :::* LISTEN
busybox是一個純淨的容器,裡面怎麼多出了一個80埠?實際上這就是nginx的監聽埠。其實看到的就是infra container的網路協議棧。即nginx和busybox看到的網路協議棧是一樣的。
可以看到網路是共享的,如果網路不是共享的通過127.0.0.1就訪問自己的協議棧了,就不會獲取到index.html頁面
/ # wget 127.0.0.1:80 Connecting to 127.0.0.1:80 (127.0.0.1:80) saving to 'index.html' index.html 100% |******************************************************************| 612 0:00:00 ETA 'index.html' saved / # cat index.html | grep nginx <title>Welcome to nginx!</title>
提供volume實現資料共享
[root@k8s-master ~]# cat pod-volume.yml apiVersion: v1 kind: Pod metadata: labels: app: test name: pod-volume-test namespace: default spec: containers: - image: busybox name: busybox command: ["/bin/sh","-c","sleep 3600"] volumeMounts: - name: data mountPath: /data - image: nginx name: nginx volumeMounts: - name: data mountPath: /data volumes: - name: data emptyDir: {}
[root@k8s-master ~]# kubectl get pod NAME READY STATUS RESTARTS AGE pod-network-test 2/2 Running 0 23m pod-volume-test 2/2 Running 0 42s [root@k8s-master ~]# kubectl exec -it pod-volume-test -c nginx -- bash root@pod-volume-test:/# cd /data root@pod-volume-test:/data# echo "volume test" > a.txt root@pod-volume-test:/data# exit exit
[root@k8s-master ~]# kubectl exec -it pod-volume-test -c busybox -- sh / # cat /data/a.txt volume test / #
可以看busybox看到Nginx修改的檔案到檔案共享了,通過資料卷實現的檔案的共享
Pod管理命令
建立Pod:
kubectl apply -f pod.yaml
或者使用命令 kubectl run nginx --image=nginx
檢視Pod:
kubectl get pods
kubectl describe pod <Pod名稱>
檢視日誌:如果pod裡面包含多個容器,需要指定容器名字來檢視指定容器的日誌
kubectl logs <Pod名稱> [-c CONTAINER]
kubectl logs <Pod名稱> [-c CONTAINER] -f
進入容器終端:
kubectl exec <Pod名稱> [-c CONTAINER] -- bash
刪除Pod:
kubectl delete <Pod名稱>
如果需要採集nginx日誌,那麼可能就需要共享儲存這個機制,跑一個獨立的採集日誌的容器採集共享儲存裡面的日誌。這就會用到一個pod執行多個容器。一個業務容器,一個業務日誌採集容器
pod幾種狀態:
Pending Pod未排程,或者pod已排程正在拉取映象
Running Pod已經執行
Failed Pod內容器執行停止
Success Pod內容器執行成功結束
Unknown Master與Node失聯,Pod狀態無法正常獲取到
作者:傑巨集唯一 出處:http://www.cnblogs.com/wuxinchun/ 本文版權歸作者和部落格園共有,歡迎轉載,但未經作者同意必須保留此段宣告,且在文章頁面明顯位置給出原文連線,否則保留追究法律責任的權利.