概述
Pod是Kubernetes的最小单元,也是最重要和最基本的概念。每一个Pod包含一个或多个容器,Pod的容器会作为
一个整体被Master调度到一个Node上运行。
Kubenetes为每个Pod都分配了唯一的IP地址,称为PodIP,一个Pod里的多个容器共享PodIP地址。在Kubernetes里,一个Pod里的容器与另外主机上的Pod容器能够直接通信。
应用在每个Node上运行的其实是一个Pod。Pod也只能运行在Node上。一个pod的所有容器都运行在同一个节点上;一个pod绝不跨越两个节点,如下图:

Pod容器组是一个k8s中一个抽象的概念,用于存放一组 container(可包含一个或多个 container 容器,即图上正方体),以及这些 container (容器)的一些共享资源。这些资源包括:
- 共享存储,称为卷(Volumes),即图上紫色圆柱
 - 网络,每个 Pod(容器组)在集群中有个唯一的 IP,pod(容器组)中的 container(容器)共享该IP地址
 - container(容器)的基本信息,例如容器的镜像版本,对外暴露的端口等
 
POD 资源配置清单
pod一级字段查看 kubectl explain pods
$ kubectl explain podsKIND: PodVERSION: v1DESCRIPTION:Pod is a collection of containers that can run on a host. This resource iscreated by clients and scheduled onto hosts.FIELDS:apiVersion <string>APIVersion defines the versioned schema of this representation of anobject. Servers should convert recognized schemas to the latest internalvalue, and may reject unrecognized values. More info:https://git.k8s.io/community/contributors/devel/api-conventions.md#resourceskind <string>Kind is a string value representing the REST resource this objectrepresents. Servers may infer this from the endpoint the client submitsrequests to. Cannot be updated. In CamelCase. More info:https://git.k8s.io/community/contributors/devel/api-conventions.md#types-kindsmetadata <Object>Standard object's metadata. More info:https://git.k8s.io/community/contributors/devel/api-conventions.md#metadataspec <Object>Specification of the desired behavior of the pod. More info:https://git.k8s.io/community/contributors/devel/api-conventions.md#spec-and-statusstatus <Object>Most recently observed status of the pod. This data may not be up to date.Populated by the system. Read-only. More info:https://git.k8s.io/community/contributors/devel/api-conventions.md#spec-and-status
pod具体配置文件
apiVersion: v1kind: Podmetadata:name: stringnamaspace: stringlabels:- name: stringannotations:- name: stringspec:containers:- name: stringimages: stringimagePullPolice: [Always | Never | IfNotPresent]command: [string]args: [string]workingDir: stringvolumeMounts:- name: stringmountPath: stringreadOnly: booleanports:- name: stringcontainerPort: inthostPort: intprotocol: stringenv:- name: stringvalue: stringresources:limits:cpu: stringmemory: stringrequests:cpu: stringmemory: stringlivenessProbe:exec:command: [string]httpGet:path: stringport: inthost: stringscheme: stringhttpHeaders:- name: stringvalue: stringtcpSocket:port: numberinitialDelaySeconds: 0timeoutSeconds: 0periodSeconds: 0successThreshold: 0failureThreshold: 0securityContext:privileged: falserestartPolicy: [Always | Never | OnFailure]nodeSelector: objectimagePullSecrets:- name: stringhostNetwork: falsevolumes:- name: stringemptyDir: {}hostPath:path: stringsecret:secretName: stringitems:- key: stringpath: stringconfigMap:name: stringitems:- key: stringpath: string
含义如下
| 属性名称 | 取值类型 | 取值说明 | 
|---|---|---|
| apiVersion | String | 版本号,例如v1,版本号必须可以用 kubectl api-versions 查询到 | 
| kind | String | Pod | 
| metadata | Object | 元数据 | 
| metadata.name | String | Pod名称,需符合RFC 1035规范 | 
| metadata.namespace | String | Pod所属的命名空间,默认为”default” | 
| metadata.labels[] | List | 自定义标签 | 
| metadata.annotations[] | List | 自定义注释列表 | 
| spec: | Object | Pod中容器的详细定义 | 
| containers: | List | Pod中容器列表 | 
| - name: string | String | 容器名称,需符合RFC 1035规范 | 
| image: string | String | 容器的镜像名称 | 
| imagePullPolicy: [ Always|Never|IfNotPresent ] | String | 获取镜像的策略,默认值为Alawys,Alawys表示每次都尝试下载镜像,IfnotPresent表示优先使用本地镜像,否则下载镜像,Nerver表示仅使用本地镜像 | 
| command: [string] | List | 容器的启动命令列表,如不指定,使用打包时使用的启动命令 | 
| args: [string] | List | 容器的启动命令参数列表 | 
| workingDir: string | String | 容器的工作目录 | 
| volumeMounts: | List | 挂载到容器内部的存储卷配置 | 
| - name: string | String | 引用pod定义的共享存储卷的名称,需用volumes[]部分定义的的卷名 | 
| mountPath: string | String | 存储卷在容器内mount的绝对路径,应少于512字符 | 
| readOnly: boolean | Boolean | 是否为只读模式,默认为读写模式 | 
| ports: | List | 需要暴露的端口库号列表 | 
| - name: string | String | 端口的名称 | 
| containerPort: int | Int | 容器需要监听的端口号 | 
| hostPort: int | Int | 容器所在主机需要监听的端口号,默认与Container相同 | 
| protocol: string | String | 端口协议,支持TCP和UDP,默认TCP | 
| env: | List | 容器运行前需设置的环境变量列表 | 
| - name: string | String | 环境变量名称 | 
| value: string | String | 环境变量的值 | 
| resources: | Object | 资源限制和请求的设置 | 
| limits: | Object | 资源限制的设置 | 
| cpu: string | String | CPU的限制,单位为core数,将用于docker run —cpu-shares参数 | 
| memory: string | String | 内存限制,单位可以为Mib/Gib,将用于docker run —memory参数 | 
| requests: | Object | 资源限制的设置 | 
| cpu: string | String | CPU请求,容器启动的初始可用数量 | 
| memory: string | String | 内存请求,容器启动的初始可用数量 | 
| livenessProbe: | Object | 对Pod内各容器健康检查的设置,当探测无响应几次后将自动重启该容器,可设置的方法包括exec、httpGet和tcpSocket,对一个容器仅需设置其中一种健康检查方法 | 
| exec: | Object | 对Pod容器内检查方式设置为exec方式 | 
| command: [string] | String | exec方式需要制定的命令或脚本 | 
| httpGet: | Object | 对Pod内个容器健康检查方法设置为HttpGet,需要制定Path、port | 
| path: string | ||
| port: number | ||
| host: string | ||
| scheme: string | ||
| HttpHeaders: | ||
| - name: string | ||
| value: string | ||
| tcpSocket: | Object | 对Pod内个容器健康检查方式设置为tcpSocket方式 | 
| port: number | ||
| initialDelaySeconds: 0 | Number | 容器启动完成后首次探测的时间,单位为秒 | 
| timeoutSeconds: 0 | Number | 对容器健康检查探测等待响应的超时时间,单位秒,默认1秒,若超过该超时时间设置,则认为该容器不健康,会重启该容器 | 
| periodSeconds: 0 | Number | 对容器监控检查的定期探测时间设置,单位秒,默认10秒一次 | 
| successThreshold: 0 | ||
| failureThreshold: 0 | ||
| securityContext: | ||
| privileged: false | ||
| restartPolicy: [Always | Never | OnFailure] | String | Pod的重启策略,(1)Always表示一旦不管以何种方式终止运行,kubelet都将重启它,(2)OnFailure表示只有Pod以非0退出码退出才重启,如果容器正常结束(退出码为0)kubelet将不会重启它,(3)Nerver:Pod终止后,kubelet将退出码报告给Master,不会再重启该Pod。 | 
| nodeSelector: obeject | Object | 设置NodeSelector表示将该Pod调度到包含这个label的node上,以key:value的格式指定 | 
| imagePullSecrets: | Object | Pull镜像时使用的secret名称,以name:secretkey格式指定 | 
| - name: string | ||
| hostNetwork: false | Boolean | 是否使用主机网络模式,默认为false,如果设置为true,表示使用宿主机网络,不再使用Docker网桥,该Pod将无法在同一宿主机上启动第2哥副本 | 
| volumes: | List | 在该pod上定义共享存储卷列表 | 
| - name: string | String | 共享存储卷名称 ,在一个Pod中每个存储卷定义一个名称,应符合RFC 1035规范。容器定义部分的containers[].volumeMounts[].name将引用该共享存储卷的名称。 Volume的类型包括:emptyDir、hostPath、gcePersistentDisk、awsElasticBlockStore、gitRepo、secret、nfs、iscsi、glusterfs、persistentVolumeClaim、rbd、flexVolume、cinder、cephfs、flocker、downwardAPI、fc、azureFile、configMap、vsphereVolume,可以定义多个Volume,每个Volume的name保持唯一。  | 
| emptyDir: {} | Object | 类型为emtyDir的存储卷,与Pod同生命周期的一个临时目录。为空值 | 
| hostPath: string | Object | 类型为hostPath的存储卷,表示挂载Pod所在宿主机的目录 | 
| path: string | String | Pod所在宿主机的目录,将被用于同期中mount的目录 | 
| secret: | Object | 类型为secret的存储卷,挂载集群与定义的secre对象到容器内部 | 
| scretname: string | ||
| items: | ||
| - key: string | ||
| path: string | ||
| configMap: | Object | 类型为configMap的存储卷,挂载预定义的configMap对象到容器内部 | 
| name: string | ||
| items: | ||
| - key: string | ||
| path: string | 
HelloWorld
创建 nginx-pod.yaml 文件
apiVersion: v1 # 定义版本(资源类型不同,其版本可能不同)kind: Pod #(定义资源类型)metadata: #(定义元数据)name: demo-nginx #(定义pod名称)namespace: default #(定义pod隶属的名称空间)spec:containers:- name: demo-nginx #(定义容器名称,一个POD中可包含多个容器)image: nginx:1.14 #(定义容器镜像名称)ports: #(定义容器暴露端口)- name: http #(暴露端口名称)containerPort: 80 #(暴露端口)- name: demo-tomcatimage: tomcat:8.5.35ports:- name: tomcatcontainerPort: 8080
2 构建
kubectl apply -f demo.yaml
查看结果
$ kubectl get pods -o wideNAME READY STATUS RESTARTS AGE IP NODE NOMINATED NODE READINESS GATESniginx-pod 2/2 Running 0 4h39m 10.1.0.147 docker-desktop <none> <none>
创建POD
#[root@master all]# cat nginx.yamlapiVersion: v1kind: Podmetadata:name: nginx1namespace: web1spec:containers:- name: nginx-webimage: nginx:1.14ports:- name: httpcontainerPort: 80
运行pod
kubectl apply -f nginx.yaml
查看pod
#[root@master all]# kubectl get pods -n web1NAME READY STATUS RESTARTS AGEnginx1 1/1 Running 0 8s
指定输出格式
[root@master all]# kubectl get pods -n web1 -o yaml[root@master all]# kubectl get pods -n web1 -o json
更新pod
对于活动对象,并非每个属性值都支持修改,如pod资源的metadata.name字段不支持修改,处分先delete删除后重新创建。
更新
kubectl get pods -n web1 -o yaml > nginx.yaml
修改重新部署
kubectl replace -f nginx.yaml --force
删除POD
kubectl delete -f nginx.yaml
查看
[root@master all]# kubectl get pods -n web1No resources found.
更新
[root@master all]# cat nginx.yamlapiVersion: v1kind: Podmetadata:name: nginx1namespace: web1spec:containers:- name: nginx-webimage: nginx:1.12ports:- name: httpcontainerPort: 80[root@master all]# kubectl apply -f nginx.yamlpod/nginx1 configured[root@master all]# kubectl get pods -n web1NAME READY STATUS RESTARTS AGEnginx1 1/1 Running 1 19s
日志
kubectl logs nginx-pod
$ kubectl logs nginx-pod/docker-entrypoint.sh: /docker-entrypoint.d/ is not empty, will attempt to perform configuration/docker-entrypoint.sh: Looking for shell scripts in /docker-entrypoint.d//docker-entrypoint.sh: Launching /docker-entrypoint.d/10-listen-on-ipv6-by-default.sh10-listen-on-ipv6-by-default.sh: Getting the checksum of /etc/nginx/conf.d/default.conf10-listen-on-ipv6-by-default.sh: Enabled listen on IPv6 in /etc/nginx/conf.d/default.conf/docker-entrypoint.sh: Launching /docker-entrypoint.d/20-envsubst-on-templates.sh/docker-entrypoint.sh: Configuration complete; ready for start up
如果 Pod 上包含多个容器,在查询具体容器的日志时,需要指定参数 -c 容器名 进行查询
删除 pod
$ kubectl delete pod nginx-podpod "nginx-pod" deleted
imagePullPolicy
各工作节点负责运行POD对象,而POD的核心功能用在运行容器,因此工作节点上必须配置运行引擎,如docker,启动容器时,容器引擎将自动拉取镜像。拉取镜像的方式
[root@master all]# kubectl explain pods.spec.containers.imagePullPolicyKIND: PodVERSION: v1FIELD: imagePullPolicy <string>DESCRIPTION:Image pull policy. One of Always, Never, IfNotPresent. Defaults to Alwaysif :latest tag is specified, or IfNotPresent otherwise. Cannot be updated.More info:https://kubernetes.io/docs/concepts/containers/images#updating-images
Always: 镜像标签为”latest”或镜像不存在时总是从指定仓库获取镜像
IfNotPresent: 仅当本地镜像缺失时才从目标仓库下载镜像
Never: 禁止从仓库下载,仅使用本地镜像
注:对于镜像标签为latest的镜像,其默认策略为”Always”,而对于其他标签,其默认策略为”IfNotPresent”,如果使用私有仓库需要认证,则可通过imagePullSecretes 字段调用此认证信息完成。
**
端口
kubectl explain pods.spec.containers.portsFIELDS:containerPort <integer> -required- #必选字段,指定在POD对象的IP地址上暴露的容器端口,其有效范围是(0,65536),使用时,应该总是指定容器应用正常监听者的端口Number of port to expose on the pod's IP address. This must be a valid portnumber, 0 < x < 65536.hostIP <string>#What host IP to bind the external port to.hostPort <integer> # 主机端口,他将接受到的请求通过NAT机制转发至由containerPort字段指定的容器端口Number of port to expose on the host. If specified, this must be a validport number, 0 < x < 65536. If HostNetwork is specified, this must matchContainerPort. Most containers do not need this.name <string> # 当前端口的名称,必须符合IANA_SVC_NAME规范且在当前POD内必须是唯一的,此端口名可被service资源调用If specified, this must be an IANA_SVC_NAME and unique within the pod. Eachnamed port in a pod must have a unique name. Name for the port that can bereferred to by services.protocol <string> # 端口相关协议,其值仅可为TCP或UDP,默认是TCPProtocol for port. Must be UDP, TCP, or SCTP. Defaults to "TCP".
通过端口转发使用 kubectl port-forward 命令来执行端口转发,将本地的 8080 端口转发到 nginx-manual 的 80 端口
$ kubectl port-forward nginx-pod 8000:80
自定义运行容器化应用
容器的command字段能够指定不同于镜像默认运行的应用程序,并且可以同时为使用args字段进行参数传递,它们将覆盖镜像中默认定义,如果仅为容器定义了args字段,那么他将作为参数传递给镜像中默认指定运行的应用程序,如果仅指定了command字段,那么他将覆盖镜像中定义的程序及参数,并以无参数方式运行应用程序。
apiVersion: v1kind: Podmetadata:name: demospec:containers:- name: demoimage: alpine:latestcommand: ["/bin/sh"]args: ["-c","while true; do sleep 30; done"]
环境变量/env
非容器化的传统管理方式中,复杂的应用程序的配置信息多数由配置文件进行指定,用户可借助文本完成配置,对于容器隔离出的环境中的应用程序,用户就需要穿透容器边界在容器内进行配置编辑并进行重载,这种方式复杂,环境变量的方式传递便成为一种潮流。 这种方式依赖于应用程序支持通过环境表示变量进行配置的能力,否则,用户在制作docker镜像时需要通过entrypoint脚本完成变量到程序配置文件的同步。
需要在容器配置端中嵌套使用env字段,他的值是一个由环境变
量构成的列表,通常包含name和value字段构成
[root@master1 ~]# kubectl explain pod.spec.containers.envKIND: PodVERSION: v1RESOURCE: env <[]Object>DESCRIPTION:List of environment variables to set in the container. Cannot be updated.EnvVar represents an environment variable present in a Container.FIELDS:name <string> -required- #环境变量名称,必选字段Name of the environment variable. Must be a C_IDENTIFIER.value <string> #传递给环境变量的值,通过$(VAR_NAME)引用,逃逸格式为"$$(VAR_NAME)",默认为空Variable references $(VAR_NAME) are expanded using the previous definedenvironment variables in the container and any service environmentvariables. If a variable cannot be resolved, the reference in the inputstring will be unchanged. The $(VAR_NAME) syntax can be escaped with adouble $$, ie: $$(VAR_NAME). Escaped references will never be expanded,regardless of whether the variable exists or not. Defaults to "".valueFrom <Object>Source for the environment variable's value. Cannot be used if value is notempty.
实例
apiVersion: v1kind: Podmetadata:name: demo-envspec:containers:- name: demo-envimage: ikubernetes/filebeat:5.6.5-alpineenv:- name: REDIS_HOSTvalue: redis.com- name: LOG_LEVELvalue: info
此处传递主机名称和日志级别
查看,通过printenv即可获取环境变量和列表及其对应的值
共享节点的网络名称空间
kubectl explain pods.spec.hostNetwork 同一个POD对象的各个容器均运行在一个独立的、隔离的Network名称空间中,共享同一个网络协议栈及相关的网络设备,也有一些特殊的POD对象需要运行与所在节点的名称空间中,执行系统级的管理任务,如查看和操作节点的网络资源甚至是网络设备等,事实上,仅需要设置HostNetwork的属性位true即可创建共享节点网络名称空间的Pod对象
如下
配置配置结果
#[root@master1 all]# cat demohostnet.yamlapiVersion: v1kind: Podmetadata:name: demo-hostnetspec:containers:- name: demo-hostnetimage: nginx:1.14hostNetwork: true
Pod对象的安全上下文
pod 对象的安全上下文用于设定Pod或容器的权限和访问控制功能,其支持的常用属性有: 1 基于用户ID和组ID访问控制对象时的权限 2 以特权或非特权的方式运行 3 通过Linux capabities为其提供部分特权 4 基于seccomp过滤进程的系统调用 5 基于SELinux的安全标签 6 是否能够进行权限升级
POD 对象的安全上下文定义在spec.securityContext字段中,而容器的安全上下文则定义在spec.containers.securityContext字段中,且二者可嵌套使用的字段有所不同,
[root@master1 all]# cat demosecu.yamlapiVersion: v1kind: Podmetadata:name: demo-secspec:containers:- name: demo-secimage: busyboxcommand: ["/bin/sh","-c","sleep 86400"]securityContext:runAsNonRoot: true # 非特权模式运行runAsUser: 1000 #设置其运行的UID为1000的可以访问allowPrivilegeEscalation: false #设置其权限升级不允许
注意
在生产环境中,很少会单独启动一个Pod直接使用,经常会用Deployment、DaemonSet、StatefulSet等方式调度并管理Pod,定义Pod的参数同时适应于Deployment、DaemonSet、StatefulSet等方式。



