05-k8s-Pod

摘要

本文内容转自网络,个人学习记录使用,请勿传播

基本概念

Pod是Kubernets创建和管理的最小单元,一个Pod由一个容器或者多个容器组成,这些容器共享存储、网络资源

Pod的特点

  • 一个Pod是一个应用的最小实例,并对外提供服务
  • 一个Pod中可以有一个容器或者多个容器
  • 一个Pod中的容器始终部署在同一个Node上
  • Pod中的所有容器共享网络和存储资源
  • Kubernets直接管理Pod,而不是容器

Pod存在的意义

Pod主要用法

  • 一个Pod运行一个容器:最常见的用法,这种情况下可以将Pod看成单个容器的抽象封装
  • 一个Pod运行多个容器:封装多个有高度耦合的容器在同一个Pod中,共享Pod资源
    • 如前后端分离服务的前端服务和后端服务
    • 多个容器间有文件交互
    • 多个容器间需要通过localhost或socket进行通信
    • 多个容器的应用需要发生频繁调用

实现资源共享的机制

image-20210902195958056

网络共享

同一个Pod中的多个容器共享网络

1
2
3
4
5
6
7
8
9
10
11
12
13
14
apiVersion: v1
kind: Pod
metadata:
labels:
app: network-pod
name: network-pod
namespace: default
spec:
containers:
- image: nginx:1.17.10
name: nginx
- image: busybox
name: tools
command: ["/bin/sh", "-c", "ping baidu.com"]

共享存储

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
apiVersion: v1
kind: Pod
metadata:
labels:
app: volume-pod
name: volume-pod
namespace: default
spec:
containers:
- image: nginx:1.17.10
name: nginx
volumeMounts:
- name: log
mountPath: /usr/share/nginx/html
- image: busybox
name: tools
command: ["/bin/sh", "-c", "ping baidu.com"]
volumeMounts: # 数据卷挂载
- name: log # 指定挂载的数据卷名称
mountPath: /data # 数据卷挂载到容器中的路径
volumes: # 定义数据卷
- name: log # 数据卷名称
emptyDir: {} # 数据卷类型

测试

1
2
3
4
5
6
7
8
# 通过资源清单创建Pod
kubectl apply -f volume-pod.yaml
# 进入一个容器创建文件
kubectl exec -it volume-pod -c tools -- sh
cd /data && echo "hello" > index.html
# 进入nginx容器查看共享目录中的文件
kubectl exec -it volume-pod -c nginx -- sh
cd /usr/share/nginx/html && cat index.html

Pod管理命令

1
2
3
4
5
6
7
8
9
10
11
12
13
14
# 创建Pod:
kubectl apply -f pod.yaml
# 使用命令创建Pod:
kubectl run nginx --image=nginx
# 查看Pod:
kubectl get pods
kubectl describe pod <Pod名称>
# 查看日志:
kubectl logs <Pod名称> [-c CONTAINER]
kubectl logs <Pod名称> [-c CONTAINER] -f
# 进入容器终端:
kubectl exec <Pod名称> [-c CONTAINER] -- bash
# 删除Pod:
kubectl delete pod <Pod名称>

Pod设计思路

健康检查和重启策略

image-20210903135743711

重启策略(restartPolicy)

  • Always:当容器终止退出后,总是重启容器,默认策略。
  • OnFailure:当容器异常退出(退出状态码非0)时,才重启容器。
  • Never:当容器终止退出,从不重启容器。

健康检查类型

  • livenessProbe(存活检查):如果检查失败,将杀死容器,根据Pod的restartPolicy来操作。
  • readinessProbe(就绪检查):如果检查失败,Kubernetes会把Pod从service endpoints中剔除。

健康检查的三种方式

  • httpGet:发送HTTP请求,返回200-400范围状态码为成功。
  • exec:执行Shell命令返回状态码是0为成功。
  • tcpSocket:发起TCP Socket建立成功。

HTTP请求

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
apiVersion: apps/v1
kind: Deployment
metadata:
labels:
app: nginx
name: nginx
namespace: default
spec:
replicas: 3
selector:
matchLabels:
app: nginx
template:
metadata:
labels:
app: nginx
spec:
restartPolicy: Always
containers:
- image: nginx:1.17.10
imagePullPolicy: IfNotPresent
name: nginx
ports:
- containerPort: 80
livenessProbe:
httpGet:
path: /index.html
port: 80
httpHeaders:
- name: Custom-Header
value: Awesome
# tcpSocket: # 端口探测
# port: 80
initialDelaySeconds: 30 #启动容器后多少秒健康检查
periodSeconds: 10 #以后每间隔多少秒检查一次
readinessProbe:
httpGet:
path: /index.html
port: 80
# tcpSocket:
# port: 80
initialDelaySeconds: 30
periodSeconds: 10

---
apiVersion: v1
kind: Service
metadata:
labels:
app: nginx
name: nginx
spec:
type: NodePort
ports:
- port: 80
protocol: TCP
targetPort: 80
nodePort: 8100
selector:
app: nginx

验证

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
$ kubectl get pod
NAME READY STATUS RESTARTS AGE
nginx-77b7dd78f5-k6ddx 1/1 Running 0 16s
nginx-77b7dd78f5-kh5mw 1/1 Running 0 56s
nginx-77b7dd78f5-wfn7r 1/1 Running 0 97s

$ kubectl logs -f nginx-77b7dd78f5-kh5mw
10.252.32.69 - - [07/Sep/2021:11:38:07 +0000] "GET /index.html HTTP/1.1" 200 612 "-" "kube-probe/1.21" "-"
10.252.32.69 - - [07/Sep/2021:11:38:07 +0000] "GET /index.html HTTP/1.1" 200 612 "-" "kube-probe/1.21" "-"
10.252.32.69 - - [07/Sep/2021:11:38:17 +0000] "GET /index.html HTTP/1.1" 200 612 "-" "kube-probe/1.21" "-"
10.252.32.69 - - [07/Sep/2021:11:38:17 +0000] "GET /index.html HTTP/1.1" 200 612 "-" "kube-probe/1.21" "-"
10.252.32.69 - - [07/Sep/2021:11:38:27 +0000] "GET /index.html HTTP/1.1" 200 612 "-" "kube-probe/1.21" "-"
10.252.32.69 - - [07/Sep/2021:11:38:27 +0000] "GET /index.html HTTP/1.1" 200 612 "-" "kube-probe/1.21" "-"


$ kubectl describe svc nginx
Endpoints: 10.244.115.61:80,10.244.115.62:80,10.244.115.63:80

kubectl exec -it nginx-77b7dd78f5-k6ddx -- sh
cd /usr/share/nginx/html
mv index.html index.html.bak

kubectl describe svc nginx
Endpoints: 10.244.115.61:80,10.244.115.62:80

执行shell命令

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
apiVersion: apps/v1
kind: Deployment
metadata:
labels:
app: nginx
name: nginx
namespace: default
spec:
replicas: 3
selector:
matchLabels:
app: nginx
template:
metadata:
labels:
app: nginx
spec:
restartPolicy: Always
containers:
- image: nginx:1.17.10
imagePullPolicy: IfNotPresent
name: nginx
ports:
- containerPort: 80
livenessProbe:
exec:
command:
- cat
- /usr/share/nginx/html/index.html
initialDelaySeconds: 30 #启动容器后多少秒健康检查
periodSeconds: 10 #以后每间隔多少秒检查一次
readinessProbe:
exec:
command:
- cat
- /usr/share/nginx/html/index.html
initialDelaySeconds: 30
periodSeconds: 10

环境变量

创建 Pod 时,可以为其下的容器设置环境变量。

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
apiVersion: apps/v1
kind: Deployment
metadata:
labels:
app: nginx-env
name: nginx-env
spec:
replicas: 3
selector:
matchLabels:
app: nginx-env
template:
metadata:
labels:
app: nginx-env
spec:
containers:
- image: nginx:1.17.10
name: nginx
env:
- name: MY_NODE_NAME
valueFrom: # 变量值从Pod属性中获取
fieldRef:
fieldPath: spec.nodeName
- name: MY_POD_NAME
valueFrom:
fieldRef:
fieldPath: metadata.name
- name: MY_POD_NAMESPACE
valueFrom:
fieldRef:
fieldPath: metadata.namespace
- name: MY_POD_IP
valueFrom:
fieldRef:
fieldPath: status.podIP
- name: ABC # 自定义变量值
value: "123456"
1
2
3
4
5
6
7
$ kubectl exec -it nginx-env-fd5d86b54-8gp82 sh
$ env
MY_POD_NAMESPACE=default
MY_POD_IP=10.244.115.24
MY_NODE_NAME=kube-0-1.epc.isme.com
MY_POD_NAME=nginx-env-fd5d86b54-8gp82
ABC=123456

应用场景

  • 容器内应用程序获取Pod信息
  • 容器内应用程序通过用户定义的变量改变默认行为

变量值定义的几种方式

  • 自定义变量值

  • 变量值从Pod属性获取

  • 变量值从Secret、ConfigMap获取

Init Container

用于初始化工作的Pod,执行完一次性任务就会结束。

  • 支持大部分应用容器的配置,但是不支持健康检查
  • 优先于应用容器运行

应用场景

  • 环境检查:可以在应用容器运行前检查依赖环境
  • 初始化配置:可以给应用容器准备配置文件,拉取依赖

使用方式

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
apiVersion: apps/v1
kind: Deployment
metadata:
labels:
app: nginx-init
name: nginx-init
spec:
replicas: 1
selector:
matchLabels:
app: nginx-init
template:
metadata:
labels:
app: nginx-init
spec:
initContainers:
- name: download
image: busybox
command:
- wget
- "-O"
- "/opt/index.html"
- http://www.ctnrs.com
volumeMounts:
- name: wwwroot
mountPath: "/opt"
containers:
- image: nginx:1.17.10
name: nginx
ports:
- containerPort: 80
volumeMounts:
- name: wwwroot
mountPath: /usr/share/nginx/html
volumes:
- name: wwwroot
emptyDir: {}

Pod中几种容器类型

  • Infrastructure Container:基础容器
    • 维护整个Pod的网络空间
  • InitContainers:初始化容器
    • 先于应用容器运行
  • Containers:业务容器
    • 多个容器并行启动

静态Pod

1
2
3
4
5
6
7
8
9
10
apiVersion: v1
kind: Pod
metadata:
labels:
run: static-nginx
name: static-nginx
spec:
containers:
- image: nginx:1.17.10
name: static-nginx
1
2
3
4
$ cp static-nginx.yaml /etc/kubernetes/manifests/
$ kubectl get pod
NAME READY STATUS RESTARTS AGE
static-nginx-kube-master 1/1 Running 0 54s

静态Pod特点

  • Pod由特定节点上的kubelet管理
  • 不能使用控制器
  • Pod名称标识当前节点名称
  • kubeadm方式部署的集群可以通过move集群组件yaml文件的方式对组件进行重启

静态pod位置配置参数

1
2
3
4
5
6
7
8
# 在kubelet配置文件启用静态Pod的参数:
vi /var/lib/kubelet/config.yaml

...

staticPodPath: /etc/kubernetes/manifests

...

将部署的pod yaml放到该目录会由kubelet自动创建。