欢迎来到尧图网

客户服务 关于我们

您的位置:首页 > 文旅 > 旅游 > 【Kubernetes基础--Pod深入理解】--查阅笔记2

【Kubernetes基础--Pod深入理解】--查阅笔记2

2025/4/19 8:58:11 来源:https://blog.csdn.net/liu888663/article/details/147251375  浏览:    关键词:【Kubernetes基础--Pod深入理解】--查阅笔记2

深入理解Pod

  • 为什么要有个Pod
    • 1. 容器协作与资源共享
    • 2. 简化调度和资源管理
    • 3. 设计模式支持
  • Pod 基本用法
  • Pod 容器共享 Volume
  • Pod 的配置管理
    • ConfigMap 概述
    • 创建 ConfigMap 资源对象
    • 在 Pod 中使用 ConfigMap
    • 使用 ConfigMap 的限制条件

为什么要有个Pod

Pod 的引入并非技术冗余,而是 k8s 为应对容器编排复杂性的关键设计。它提供的是一种编排思想,而非具体的技术方案。

Pod 作为 k8s 最小的调度和管理单元,解决了容器化环境中的多个关键问题:

1. 容器协作与资源共享

  • 亲密关系容器组:Pod 允许同一组容器共享 Network Namespace 和 Volume,这些容器需要紧密协作(如共享网络、存储或进程空间)。例如,日志收集容器与应用容器共享日志目录,或 Sidecar 模式下的代理容器与主应用容器通过本地 Socket 通信
  • 统一网络和存储:Pod 内容器共享 同一个 IP 和端口范围,可以通过 localhost 直接通信;共享 Volume 可以实现文件交换(配置文件、临时数据等)

2. 简化调度和资源管理

  • 成组调度:需要共同运行的容器(比如 Web 服务与缓存服务)必须部署在同一个节点。Pod 作为整体调度单位,避免因分散部署导致资源不足或依赖失效。例如,k8s 直接以 Pod 为粒度分配 CPU、内存资源,而非逐个容器计算
  • 统一生命周期:Pod 内的容器具有一致的生命周期。若某个容器异常退出,K8S 可基于 Pod 的重启策略(如 Always、OnFailure)统一处理,而非单独管理每个容器。
  • 统一运维:扩缩容、滚动升级等操作以 Pod 为单位,当节点故障时,K8S 可直接重建整个 Pod,而非逐个恢复容器,提升系统健壮性

3. 设计模式支持

  • Infra 容器:每个 Pod 默认有一个 Infra 容器(pause 容器),负责创建共享的 Network Namespace 和 Volume。用户容器通过加入 Infra 容器的命名空间实现资源共享,解决了容器启动顺序依赖问题
  • 扩展设计:Pod 支持 Init 容器(初始化任务)、Sidecar 容器(辅助功能如日志转发)等模式,增强了应用的可维护性。例如,通过 Sidecar 实现服务网格的流量代理

Pod 基本用法

使用 Docker 时,我们使用 docker run 来创建并启动一个容器。但是,在 k8s 中对长时间运行容器的要求是:其主程序需要一直在前台执行

比如,我们使用 ./start.sh & 在后台执行程序,则在 k8s 创建包含这个容器的 Pod 之后运行完该命令,即认为 Pod 执行结束,将立刻销毁。如果为该 Pod 定义了 RC,则系统会监控到该 Pod 已经终止,之后根据 RC 定义中 Pod 的 replicas 副本数量生成一个新的 Pod。一旦创建新的 Pod,就在执行完启动命令后陷入无限循环的过程中。这就是Kubernetes需要我们自己创建的 Docker 镜像并以一个前台命令作为启动命令的原因。

以一种场景举例,frontend 和 redis 两个容器应用为紧耦合的关系,并组合成一个整体对外提供服务时,应将这两个容器打包为一个Pod,配置文件 frontend-localredis-pod.yaml:

apiVersion: v1
kind: Pod
metadata:name: redis-phplabels:name: redis-php
spec: containers:- name: frontendimage: kubeguide/guestbook-php-frontend:localredisports:- containerPort: 80- name: redisimage: kubeguide/redis-masterports:- containerPort: 6379

属于同一个 Pod 的多个容器应用之间相互访问时仅需要通过 localhost 就可以通信,使得这一组容器被“绑定”在了一个环境中。

kubectl create -f frontend-localredis-pod.yaml
# pod "redis-php" createdkubectl get pods   # READAY 2/2 表示两个容器都成功运行了
kubectl describe pod redis-php # 显示 pod 详细信息

Pod 容器共享 Volume

同一个 Pod 中的多个容器能够共享 Pod 级别的存储卷 Volume。Volume 可以被定义为各种类型,多个容器各自进行挂载操作,将一个 Volume 挂载为容器内部需要的目录。

看个例子:在 Pod 内包含两个容器:tomcat 和 busybox,在 Pod 级别设置 Volume “app-logs”​,用于tomcat向其中写日志文件,busybox 读日志文件,配置文件 pod-volume-applogs.yaml:

apiVersion: v1
kind: Pod
metadata:name: volume-pod
spec:containers:- name: tomcatimage: tomcatports:- containerPort: 8080volumeMounts:- name: app-logsmountPath: /usr/local/tomcat/logs- name: busyboximage: busyboxcommand: ["sh", "-c", "tail -f /logs/catalina*.log"]volumeMounts:- name: app-logsmountPath: /logsvolumes:- name: app-logsemptyDir: {}

Volume 名为 app-logs,类型为 emptyDir(还可设置其他类型,如 hostPath,configMap等),挂载到 tomcat 容器内的/usr/local/tomcat/logs 目录,同时挂载到 busybox 容器内的 /logs 目录。tomcat 容器在启动后会向 /usr/local/tomcat/logs 目录写文件,busybox 容器就可以读取其中的文件了。

# busybox 容器的启动命令为tail -f /logs/catalina*.log,我们可以通过 kubectl logs 命令查看 busybox 容器的输出内容:
kubectl logs volume-pod -c busybox
# 登录 tomcat 容器进行查看
kubectl exec -ti volume-pod -c tomcat -- ls /usr/local/tomcat/logs
kubectl exec -ti volume-pod -c tomcat -- tail /usr/local/tomcat/logs/catalina*.log

Pod 的配置管理

将应用所需的配置信息与程序进行分离,可以使应用程序被更好地复用,通过不同的配置也能实现更灵活的功能。
将应用打包为容器镜像后,可以通过环境变量或者外挂文件的方式在创建容器时进行配置注入。k8s 1.2开始提供统一的应用配置管理–ConfigMap,实现多个容器的配置。

ConfigMap 概述

  • 生成为容器内的环境变量
  • 设置容器启动命令的启动参数(需设置为环境变量)​
  • 以 Volume 的形式挂载为容器内部的文件或目录

ConfigMap 以 key:value 的形式保存在 k8s 系统中供应用使用,既可以用于表示一个变量的值(例如 apploglevel=info)​,也可以用于表示一个完整配置文件的内容(例如server.xml=<?xml…>…)。

可以通过 YAML 配置文件或者直接使用 kubectl create configmap 命令行的方式来创建 ConfigMap。

创建 ConfigMap 资源对象

  1. 通过 YAML 配置文件方式创建
    举例 cm-appvars.yaml 将几个应用所需的变量定义为 ConfigMap 的用法:
apiVersion: v1
kind: ConfigMap
metadata:name: cm-appvars
data:apploglevel: infoappdatadir: /var/data

执行 create 命令创建

kubectl create -f cm-appvars.yaml  # ConfigMap "cm-appvars" createdkubectl get configmapkubectl describe configmap cm-appvarskubectl get configmap cm-appvars -o yaml

cm-appconfigfiles.yaml 描述了将两个配置文件 server.xml 和 logging.properties 定义为 ConfigMap 的用法,设置 key 为配置文件的别名,value 则是配置文件的全部文本内容:

apiVersion: v1
kind: ConfigMap
metadata:name: cm-appconfigfiles
data:key-serverxml: |<?xml version='1.0' encoding='utf-8' ?><Server port="8080" shutdown="SHUTDOWN"><Listener className="xxx" />...</Server>key-loggingproperties: "handles=filehanlder\r\n\r\nformatter=simpleformater\r\n\r\nlevel=info\r\n\r\n"
  1. 通过 kubectl 命令创建
  • 通过 --from-file 参数从文件中进行创建,可以指定 key 的名称,也可以在一个命令行中创建包含多个 key 的 ConfigMap:
kubectl create configmap NAME --from-file=[key=]source --from-file=[key=]sourcekubectl create configmap cm-server.xml --from-file=server.xml # ConfigMap "cm-server.xml" created
kubectl describe configmap cm-server.xml
  • 通过 --from-file 参数从目录中进行创建,该目录下的每个配置文件名都被设置为 key,文件的内容被设置为 value:
kubectl create configmap NAME --from-file=config-files-dirkubectl create configmap cm-appconf --from-file=configfiles
kubectl describe configmap cm-appconf
  • 使用 --from-literal 时会从文本中进行创建,直接将指定的 key=value创建为 ConfigMap 的内容:
kubectl create configmap NAME --from-literal=key1=value1 --from-literal=key2=value2kubectl create configmap cm-appenv --from-literal=loglevel=info --from-literal=appdatadir=/var/data
kubectl describe configmap cm-appenv

在 Pod 中使用 ConfigMap

  1. 通过环境变量使用 ConfigMap
    以前面的 ConfigMap “cm-appvars” 为例,在 Pod “cm-test-pod” 中,将 ConfigMap “cm-appvars” 中的内容以环境变量方式设置为容器内部的环境变量,容器的启动命令将显示这两个环境变量
apiVersion: v1
kind: Pod
metadata:name: cm-test-pod
spec:containers:- name: cm-testimage: busyboxcommand: [ "/bin/sh", "-c", "env | grep APP" ]env:- name: APPLOGLEVEL             # 定义环境变量的名称valueFrom:                     # key“apploglevel”对应的值configMapKeyRef:name: cm-appvars          # 环境变量的值取自cm-appvars:key: apploglevel          # key为apploglevel- name: APPDATADIR              # 定义环境变量的名称valueFrom:                     # key“appdatadir”对应的值configMapKeyRef:name: cm-appvars          # 环境变量的值取自cm-appvarskey: appdatadir           # key为appdatadirrestartPolicy: Never            # 不会自动重启

使用 kubectl create -f 命令创建该 Pod,由于是测试 Pod,所以该 Pod 在执行完启动命令后将会退出,并且不会被系统自动重启(restartPolicy=Never)​:

kubectl create -f cm-test-pod.yaml  # pod "cm-test-pod" createdkubectl get pods --show-all # 使用kubectl get pods --show-all查看已经停止的 Pod
# 查看该Pod的日志,可以看到启动命令“env | grep APP”的执行结果
kubectl logs cm-test-pod
# APPDATADIR=/var/data
# APPLOGLEVEL=info

k8s 1.6版本开始,引入新的字段 envFrom,实现了在 Pod 环境中将 ConfigMap(也可用于 Secret 资源对象)中所有定义的 key=value 自动生成为环境变量:

apiVersion: v1
kind: Pod
metadata:name: cm-test-pod
spec:containers:- name: cm-testimage: busyboxcommand: [ "/bin/sh", "-c", "env" ]envFrom:- configMapRefname: cm-appvars      # 根据cm-appvars中的 key=value 自动生成环境变量restartPolicy: Never

注意:环境变量的名称受POSIX命名规范(​[a-zA-Z_]​[a-zA-Z0-9_]*)约束,不能以数字开头。如果包含非法字符,则系统将跳过该条环境变量的创建,并记录一个Event来提示环境变量无法生成,但并不阻止Pod的启动

  1. 通过 volumeMount 使用 ConfigMap
    在Pod “cm-test-app” 的定义中,将 ConfigMap “cm-appconfigfiles” 中的内容以文件的形式 mount 到容器内部的 /configfiles 目录下。Pod 配置文件cm-test-app.yaml:
apiVersion: v1
kind: Pod
metadata:name: cm-test-app
spec:containers:- name: cm-test-appimage: tomcat-app:v1ports:- containerPort: 8080volumeMounts:- name: serverxml                    # 引用Volume的名称mountPath: /configfiles            # 挂载到容器内的目录volumes:- name: serverxml                      # 定义Volume的名称configMap:name: cm-appconfigfiles            # 使用ConfigMap“cm-appconfigfiles”items:- key: key-serverxml               # key=key-serverxmlpath: server.xml                 # value将server.xml文件名进行挂载- key: key-loggingproperties       # key=key-loggingpropertiespath: logging.properties         # value将logging.properties文件名进行挂载

创建 Pod,进入容器,查看 /configfiles 目录下存在 serverl.xml 和 logging.properties 文件,内容为 ConfigMap “cm-appconfigfiles” 中两个 key 定义的内容:

kubectl create -f cm-test-app.yamlkubectl exec -ti cm-test-app -- bashcat /configfiles/server.xml
cat /configfiles/logging.properties

在引用 ConfigMap 时不指定 items,则使用 volumeMount 方式在容器内的目录下为每个 item 都生成一个文件名为 key 的文件:

apiVersion: v1
kind: Pod
metadata:name: cm-test-app
spec:containers:- name: cm-test-appimage: tomcat-app:v1imagePullPolicy: Neverports:- containerPort: 8080volumeMounts:- name: serverxml               # 引用Volume的名称mountPath: /configfiles      # 挂载到容器内的目录volumes:- name: serverxml                 # 定义Volume的名称configMap:name: cm-appconfigfiles      # 使用ConfigMap“cm-appconfigfiles”

查看到在 /configfiles 目录下存在key-loggingproperties和key-serverxml文件,文件的名称来自在ConfigMap cm-appconfigfiles中定义的两个key的名称,文件的内容则为value的内容

kubectl create -f cm-test-app.yamlls /configfiles  # key-loggingproperties  key-serverxml        

使用 ConfigMap 的限制条件

  • ConfigMap 必须在 Pod 之前创建
  • ConfigMap 受 Namespace 限制,只有处于相同 Namespace 中的 Pod 才可以引用它
  • kubelet 只支持可以被API Server管理的 Pod 使用 ConfigMap。kubelet 在本 Node 上通过–manifest-url 或 --config 自动创建的静态 Pod将无法引用 ConfigMap
  • 在 Pod 对 ConfigMap 进行挂载(volumeMount)操作时,在容器内部只能挂载为“目录”​,无法挂载为“文件”​。

版权声明:

本网仅为发布的内容提供存储空间,不对发表、转载的内容提供任何形式的保证。凡本网注明“来源:XXX网络”的作品,均转载自其它媒体,著作权归作者所有,商业转载请联系作者获得授权,非商业转载请注明出处。

我们尊重并感谢每一位作者,均已注明文章来源和作者。如因作品内容、版权或其它问题,请及时与我们联系,联系邮箱:809451989@qq.com,投稿邮箱:809451989@qq.com

热搜词