Kubernetes in action-Kubernetes的pod
Kubernetes的pod
- 1、什么是pod
- 2、pod的yaml描述文件
- 3、K8s的标签功能
- 3.1 使用标签描述pod
- 3.2 将指定的pod调度到指定的工作节点
- 3.3 命名空间
- 4、停止和移除pod
- 5、保持pod健康
- 5.1 容器探活和重启-kubelet功能
- 5.2 pod协调- replication controller功能
- 6、replicaSet
- 7、DaemonSet
如有侵权,请联系~
如有错误,也欢迎批评指正~
本篇文章大部分是来自学习《Kubernetes in action》的笔记
1、什么是pod
pod是一组并置的容器,它是k8s最基本的构建模块,一个pod的上会有多个容器【很多时候也是只有一个容器】。当一个pod的有多个容器的时候也都是运行在一个工作节点上,即不会一个pod上的多个容器运行在多个节点上。
同一个pod中的容器之间是部分隔离的
虽然容器之间通过Linux的命名空间是隔离的,但是有时候我们并不希望单个容器之间是完全隔离的,而是让一个容器组内的容器之间可以共享一部分资源。
同一个pod中的容器是在相同的network和UTS命名空间中运行的,即他们共享相同的主机名和网络ip,最新的k8s也能共享PID命名空间,但是默认是关闭的。但是文件系统是相互隔离的,也可以使用名为volume的k8s资源来共享文件目录。
通过推荐是一个pod里面只有一个容器,一个容器里面只有一个进程,除非是有相关的进程。
2、pod的yaml描述文件
Pod 的配置通常通过 YAML 文件来描述。yaml的实例:
apiVersion: v1 # 指定 API 版本(Pod 属于核心 API)
kind: Pod # 定义资源类型为 Pod
metadata: # 元数据部分name: my-pod # Pod 的名称labels: # 标签,用于标识和选择 Podapp: my-appenvironment: dev
spec: # Pod 的规格定义containers: # 容器列表- name: my-container # 容器的名称image: nginx:latest # 使用的镜像ports: # 暴露的端口- containerPort: 80 # 容器内部监听的端口env: # 环境变量- name: ENV_VAR_NAME # 环境变量名称value: "value" # 环境变量值resources: # 资源限制requests: # 请求的资源memory: "64Mi" # 请求内存大小cpu: "250m" # 请求 CPU 大小limits: # 最大资源限制memory: "128Mi" # 最大内存限制cpu: "500m" # 最大 CPU 限制restartPolicy: Always # 重启策略
使用yaml文件就可以创建pod实例:
// 创建pod
kubectl create -f pod.yaml// 查看pod的yaml描述文件
kubectl get po my-pod -o yaml
3、K8s的标签功能
3.1 使用标签描述pod
随着服务数量越来越多,pod的数量也会越来越多,如果操作pod的时候有时候需要批量的操作一类pod。那么就需要标签功能。标签是一种简单却功能强大的Kubemetes特性,不仅可以组织pod, 也可以组织所有其他的Kubemetes资源。
一个资源便可以拥有多个标签。通常在我们创建资源时就会将标签附加到资源上,但之后我们也可以再添加其他标签,或者修改现有标签的值, 而无须重新创建资源。
上述yaml文件中的metadata.labels就表示的是这个pod的标签。
标签要和标签选择器一起使用。标签选择器可以选择具有特定标签的pod子集,并对子集进行操作。标签选择器可以根据如下条件进行选择资源:
- 包含(不包含)某个键的资源
- 包含特定键和值的资源
- 包含特定键,但是值和指定不同的资源
3.2 将指定的pod调度到指定的工作节点
不只是pod可以使用标签功能,k8s的其他资源也可以使用标签,例如节点。可以对每个工作节点设置相应的标签,然后就可以将pod调度上指定的某一列工作节点上。
设置node的标签:
kubectl label node <nodeName> gpu=true
将pod指定到node上:
apiVersion: v1
kind: Pod
metadata:name: my-pod
spec:nodeSelector: # 匹配节点标签gpu: true # 标签键值对containers:- name: my-containerimage: nginx
当然也可以将pod调度到指定的某一个特定的节点。但是如果这个节点处于离线状态,可能导致调度失败。所以不应该对pod调度到某一个特定的工作节点上,而是一个工作节点组。
apiVersion: v1
kind: Pod
metadata:name: my-pod
spec:nodeName: node-01 # 直接指定节点名称containers:- name: my-containerimage: nginx
3.3 命名空间
通过上述标签可以知道,资源是相互叠加的,一个资源存在多个标签,一个标签对应多个资源。如果不想让这些资源叠加,可以使用k8s的命名空间【和linux的命名空间不一样】。命名空间为资源名称提供了作用域,针对于不同的命名空间可以使用相同的资源名。
如果不同的用户都在一个命名空间中,那么可能存在一个用户误删了其他用户的资源。那么此时就可以使用命名空间隔离不同用户的资源。或者根据不同业务类型区分不同的命名空间。
创建命名空间
使用YAML 文件或者命令:
1、YAML 文件(namespace.yaml)
apiVersion: v1
kind: Namespace
metadata:name: dev
应用YAML文件:
kubectl apply -f namespace.yaml
2、直接使用命令
kubectl create namespace <namespace-name>
4、停止和移除pod
在删除pod的过程中,其实K8s会终止pod中的所有容器。删除pod的方式有很多:
1、通过名字进行删除:
kubectl delete pod <pod-name1> <pod-name2>
2、通过标签进行删除
kubectl delete pod -l app=myApp
3、通过命名空间进行删除,这样命名空间也删除了
kubectl delete ns custome-namespace
4、通过命名空间进行删除,保留命名空间,只删除pod
kubectl delete pods --all -n <namespace>
5、通过命名空间进行删除,删除所有资源,包括这个命名空间中的pod、 service、 replication Controller等等
kubectl delete all --all -n <namespace>
5、保持pod健康
5.1 容器探活和重启-kubelet功能
在 Kubernetes 中,Pod 的保活(Liveness)是指通过健康检查机制来确保 Pod 中的容器处于正常运行状态。如果健康检查失败,Kubernetes 会根据配置采取措施(如重启容器或重新调度 Pod),以确保服务的高可用性。
探针可以通过以下三种方式实现:
- HTTP 请求:
Kubernetes 会向指定的路径发送 HTTP 请求,如果返回状态码为 200-399,则认为探针成功。 - TCP Socket:
Kubernetes 会尝试与指定端口建立 TCP 连接,如果连接成功,则认为探针成功。 - 命令执行:
Kubernetes 会在容器内执行指定的命令,如果命令退出状态码为 0,则认为探针成功。
如果探测失败则会重启容器,而不是重启pod。重启pod根据restart policy策略和容器是否为正常退出决定。探活和重启都是kubelet实现的。
使用 HTTP 请求进行存活检查:
apiVersion: v1
kind: Pod
metadata:name: liveness-http
spec:containers:- name: liveness-containerimage: nginxlivenessProbe:httpGet:path: /healthzport: 80initialDelaySeconds: 5 # 容器启动后延迟 5 秒开始检查periodSeconds: 10 # 每 10 秒检查一次timeoutSeconds: 1 # 超时时间为 1 秒failureThreshold: 3 # 允许连续失败 3 次后重启容器
使用 TCP Socket 进行存活检查
apiVersion: v1
kind: Pod
metadata:name: liveness-tcp
spec:containers:- name: liveness-containerimage: nginxlivenessProbe:tcpSocket:port: 80initialDelaySeconds: 10periodSeconds: 20
5.2 pod协调- replication controller功能
kubelet负责单个node中pod的管理,而replication controller是负责整个所有的pod的管理和协调。例如某个pod下了,他会在别的节点重新创建一个新的pod。
replication controller的yaml:
apiVersion: v1
kind: ReplicationController
metadata:name: my-rc # ReplicationController 的名称
spec:replicas: 3 # 确保始终有 3 个 Pod 副本selector:app: my-app # 标签选择器,用于匹配管理的 Podtemplate: # 下面的配置是该replication controller控制的pod配置,创建新pod使用metadata:labels:app: my-app # Pod 的标签必须与 selector 匹配spec:containers:- name: nginx-container # 容器名称image: nginx:latest # 容器镜像ports:- containerPort: 80 # 容器监听的端口
service - replication controller - pod的关系:
replication controller协调管理pod:
6、replicaSet
replicaSet已经慢慢的替代replication controller。replicaSet功能更加强大,它不仅可以匹配标签等于某个值的pod,而且还可以匹配缺少某个标签、两个标签的同时存在、只要存在某个标签就行不需要关心标签的值等等,对标签的匹配能力更加强大。
replicaSet的yaml文件:
apiVersion: apps/v1
kind: ReplicaSet
metadata:name: my-replicaset # ReplicaSet 的名称
spec:replicas: 3 # 确保始终有 3 个 Pod 副本selector: #标签选择器提供了强大的标签匹配能力:matchLabels、matchExpressionsmatchLabels:app: my-app # 标签选择器,用于匹配管理的 Podtemplate:metadata:labels:app: my-app # Pod 的标签必须与 selector 匹配spec:containers:- name: nginx-container # 容器名称image: nginx:latest # 容器镜像ports:- containerPort: 80 # 容器监听的端口
上述yaml给的标签选择器是使用的matchLabels,也可以替换给功能更强大的matchExpressions。
apiVersion: apps/v1
kind: ReplicaSet
metadata:name: my-replicaset
spec:replicas: 3selector:matchExpressions:- key: appoperator: Invalues:- my-app- another-app- key: environmentoperator: NotInvalues:- production- key: debugoperator: Existstemplate:metadata:labels:app: my-appenvironment: stagingdebug: "true"spec:containers:- name: nginx-containerimage: nginx:latestports:- containerPort: 80
operator支持 in、 not in【这两种需要给value属性】,Exists、not Exists【不能存在value属性】。如果存在多个matchExpressions或者matchLabel,需要同时满足才能匹配pod。
7、DaemonSet
DaemonSet和replication controller、replicaSet很像,也是控制管理pod。不同点就是:replicaSet是将期望的pod随机的分配到工作节点node上;而DaemonSet是对每一个工作节点node都会创建一个pod。
例如日志管理器和资源管理器就会希望在每个节点上运行,这就可以通过DaemonSet进行管理。另一个例子就是kube-proxy进程。他会在节点启动添加到集群的时候就创建pod,DaemonSet不需要指定期望的pod数。因为新增工作节点就会创建一个新的pod,删除工作节点也不会新建代替。
apiVersion: apps/v1
kind: DaemonSet
metadata:name: my-daemonset # DaemonSet 的名称labels:app: my-app
spec:selector:matchLabels:app: my-app # 标签选择器,用于匹配管理的 Podtemplate:metadata:labels:app: my-app # Pod 的标签必须与 selector 匹配spec:nodeSelector: # 也可以指定只对那些node进行部署disk:ssdcontainers:- name: nginx-container # 容器名称image: nginx:latest # 容器镜像ports:- containerPort: 80 # 容器监听的端口resources:limits:memory: "128Mi"cpu: "500m"tolerations: # 可选:容忍污点,确保 DaemonSet 在所有节点上运行- key: "node-role.kubernetes.io/master"operator: "Exists"effect: "NoSchedule"