Docker 與 K8S學習筆記(十八)—— Pod的使用


Pod 是一組緊密關聯的容器集合,它們共享IPC、Network和UTS namespace,是 Kubernetes 調度的基本單元。Pod 的設計理念是支持多個容器在一個 Pod 中共享網絡和文件系統,可以通過進程間通信和文件共享這種簡單高效的方式組合完成服務。

一、Pod的定義

這里還是以我們之前做的webapp為例定義一個Pod,這是一個最簡單的Pod定義

apiVersion: v1
kind: Pod
metadata:
  name: webapp
  labels:
    app: webapp
spec:
  containers:
  - name: webapp
    image: 172.16.194.135:5000/webapp:latest
    ports:
    - containerPort: 5000

關於Pod的定義比較重要的就是kind、spec.containers,kind就是定義資源類型、在spec.containers中主要定義容器所使用的鏡像,這里可以定義多個容器。

 

二、Pod的基本使用

在使用Pod前我們需要注意,在Kubernetes中對於長時間運行的容器的要求是:其主程序需要一直在前台運行。如果主程序運行在后台,則Kubernetes會認為Pod執行結束,將會銷毀Pod。以webapp鏡像為例,它的Dockerfile如下:

FROM java:8
WORKDIR /opt/soft/
EXPOSE 4567
COPY webapp-1.0-SNAPSHOT.jar /opt/soft/webapp.jar
ENTRYPOINT ["java", "-jar", "/opt/soft/webapp.jar"]

接下來,我們嘗試一下Pod中多容器的場景,我們的Pod包含兩個容器:webapp和busybox,Pod定義如下:

apiVersion: v1
kind: Pod
metadata:
  name: webapp
  labels:
    app: webapp
spec:
  containers:
  - name: webapp
    image: 172.16.194.135:5000/webapp:1.0
    ports:
    - containerPort: 5000
  - name: busybox
    image: busybox
    command: ["sh", "-c", "top"]

注意:busybox容器中我們定義了啟動命令top,這樣做就是為了確保busybox容器始終在前台運行top命令,避免容器直接被銷毀。

我們創建Pod,並通過describe可以清楚看到這兩個容器的創建過程:

$ sudo kubectl create -f webapp_pod.yaml
pod/webapp created
$ sudo kubectl describe pod webapp
Name:         webapp
Namespace:    default
Priority:     0
Node:         ayato/172.16.194.135
Start Time:   Sat, 08 Jan 2022 05:49:38 +0000
Labels:       app=webapp
Annotations:  <none>
Status:       Running
IP:           172.17.0.6
IPs:
  IP:  172.17.0.6
Containers:
  webapp:
    Container ID:   docker://9c68ef7019126b65e2feba5d4d69e55997a9e573ce585b0bbb6a7cfe2fe20b31
    Image:          172.16.194.135:5000/webapp:1.0
    Image ID:       docker-pullable://172.16.194.135:5000/webapp@sha256:df3a447a013ada0642dec67bb31976f42f1a0699a68873d0452f514fa24e5c77
    Port:           5000/TCP
    Host Port:      0/TCP
    State:          Running
      Started:      Sat, 08 Jan 2022 05:49:40 +0000
    Ready:          True
    Restart Count:  0
    Environment:    <none>
    Mounts:
      /var/run/secrets/kubernetes.io/serviceaccount from default-token-pcr2h (ro)
  busybox:
    Container ID:  docker://0dfd00b5fa8e419bfe0b4a43595c83cb1d4986980914865ae3371e1724c7f568
    Image:         busybox
    Image ID:      docker-pullable://busybox@sha256:5acba83a746c7608ed544dc1533b87c737a0b0fb730301639a0179f9344b1678
    Port:          <none>
    Host Port:     <none>
    Command:
      sh
      -c
      top
    State:          Running
      Started:      Sat, 08 Jan 2022 05:49:45 +0000
    Ready:          True
    Restart Count:  0
    Environment:    <none>
    Mounts:
      /var/run/secrets/kubernetes.io/serviceaccount from default-token-pcr2h (ro)
Conditions:
  Type              Status
  Initialized       True
  Ready             True
  ContainersReady   True
  PodScheduled      True
Volumes:
  default-token-pcr2h:
    Type:        Secret (a volume populated by a Secret)
    SecretName:  default-token-pcr2h
    Optional:    false
QoS Class:       BestEffort
Node-Selectors:  <none>
Tolerations:     node.kubernetes.io/not-ready:NoExecute op=Exists for 300s
                 node.kubernetes.io/unreachable:NoExecute op=Exists for 300s
Events:
  Type    Reason     Age    From               Message
  ----    ------     ----   ----               -------
  Normal  Scheduled  3m50s  default-scheduler  Successfully assigned default/webapp to ayato
  Normal  Pulled     3m49s  kubelet            Container image "172.16.194.135:5000/webapp:1.0" already present on machine
  Normal  Created    3m48s  kubelet            Created container webapp
  Normal  Started    3m48s  kubelet            Started container webapp
  Normal  Pulling    3m48s  kubelet            Pulling image "busybox"
  Normal  Pulled     3m44s  kubelet            Successfully pulled image "busybox" in 4.516692787s
  Normal  Created    3m44s  kubelet            Created container busybox
  Normal  Started    3m43s  kubelet            Started container busybox

我們之前說過同一個Pod中的容器共享網絡,也就是說我們在busybox容器中可以通過localhost訪問webapp的接口,我們嘗試一下:

$ sudo kubectl exec -it webapp -c busybox /bin/sh
kubectl exec [POD] [COMMAND] is DEPRECATED and will be removed in a future version. Use kubectl exec [POD] -- [COMMAND] instead.
/ # wget http://localhost:4567/api/hello
Connecting to localhost:4567 (127.0.0.1:4567)
saving to 'hello'
hello                100% |******************************************************************************************|    15  0:00:00 ETA
'hello' saved
/ # cat hello
Hello my friend/ #

 

三、Pod容器共享Volume

同一個Pod中的容器能夠共享Pod級別的Volume,Volume可以被定義為各種類型,多個容器分別進行掛載操作。我們還是以webapp和busybox為例,webapp向volume中寫log,busybox通過tail命令讀log,Pod定義如下:

apiVersion: v1
kind: Pod
metadata:
  name: webapp
  labels:
    app: webapp
spec:
  containers:
  - name: webapp
    image: 172.16.194.135:5000/webapp:1.0
    ports:
    - containerPort: 5000
    volumeMounts:
    - name: webapp-logs
      mountPath: /tmp
  - name: busybox
    image: busybox
    command: ["sh", "-c", "tail -f /logs/log.out"]
    volumeMounts:
    - name: webapp-logs
      mountPath: /logs
  volumes:
  - name: webapp-logs
    emptyDir: {}

我們通過Pod定義中可以看到:我們設置了一個Volume,名稱為webapp-logs,type為emptyDir。容器webapp將Volume掛載到/tmp目錄,因為webapp配置了logback並會向/tmp中寫日志。容器busybox將Volume掛載到/logs目錄,並通過tail命令持續讀日志。我們啟動Pod,並使用kubectl logs命令從busybox中讀取tail的輸出:

$ sudo kubectl create -f webapp_pod.yaml
pod/webapp created
$ sudo kubectl logs webapp -c busybox
06:30:27.810 [INFO ] [main] [org.demo.webapp.todolist.TodoListApplication] Starting TodoListApplication v1.0-SNAPSHOT using Java 1.8.0_111 on webapp with PID 1 (/opt/soft/webapp.jar started by root in /opt/soft)
06:30:27.821 [INFO ] [main] [org.demo.webapp.todolist.TodoListApplication] No active profile set, falling back to default profiles: default
06:30:30.060 [INFO ] [main] [org.springframework.boot.web.embedded.tomcat.TomcatWebServer] Tomcat initialized with port(s): 4567 (http)
06:30:30.079 [INFO ] [main] [org.apache.coyote.http11.Http11NioProtocol] Initializing ProtocolHandler ["http-nio-4567"]
06:30:30.088 [INFO ] [main] [org.apache.catalina.core.StandardService] Starting service [Tomcat]
06:30:30.089 [INFO ] [main] [org.apache.catalina.core.StandardEngine] Starting Servlet engine: [Apache Tomcat/9.0.41]
06:30:30.359 [INFO ] [main] [org.apache.catalina.core.ContainerBase.[Tomcat].[localhost].[/]] Initializing Spring embedded WebApplicationContext
06:30:30.359 [INFO ] [main] [org.springframework.boot.web.servlet.context.ServletWebServerApplicationContext] Root WebApplicationContext: initialization completed in 2407 ms
06:30:30.913 [INFO ] [main] [org.springframework.scheduling.concurrent.ThreadPoolTaskExecutor] Initializing ExecutorService 'applicationTaskExecutor'
06:30:32.634 [WARN ] [main] [org.springframework.boot.autoconfigure.thymeleaf.ThymeleafAutoConfiguration$DefaultTemplateResolverConfiguration] Cannot find template location: classpath:/templates/ (please add some templates or check your Thymeleaf configuration)
06:30:32.956 [INFO ] [main] [org.apache.coyote.http11.Http11NioProtocol] Starting ProtocolHandler ["http-nio-4567"]
06:30:33.096 [INFO ] [main] [org.springframework.boot.web.embedded.tomcat.TomcatWebServer] Tomcat started on port(s): 4567 (http) with context path ''
06:30:33.131 [INFO ] [main] [org.demo.webapp.todolist.TodoListApplication] Started TodoListApplication in 6.387 seconds (JVM running for 7.205)

關於Volume的類型,有如下幾種:

1)emptyDir:emptyDir是在Pod分配到Node時創建的,它的初始內容為空,並且無須指定host上對應的目錄文件,它是由Kubernetes自動分配的目錄,當Pod銷毀后,emptyDir中的數據也會被刪除。一般可用作臨時空間,存放應用程序臨時數據。

2)hostPath:將宿主機中的文件或目錄掛載到Pod中。通常用於應用永久數據的存儲。

3)iscsi:將iSCSI存儲設備上的目錄掛載到Pod中。

4)nfs:將NFS上的目錄掛載到Pod中。

5)glusterfs:將GlusterFS網絡文件系統的目錄掛載到Pod中。

6)rbd:將Ceph塊設備共享存儲掛載到Pod中。

7)gitRepo:通過掛載一個空目錄,並從Git中克隆一個git倉庫供Pod使用。

8)configmap:將配置數據掛載為容器中的文件。

9)secret:將Secret數據掛載為容器中的文件。


免責聲明!

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



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