当前位置: 首页 > news >正文

Kubernetes Service与Pod深度解析

Kubernetes Service与Pod深度解析

一、Service:Pod的统一访问入口

在Kubernetes集群中,Deployment可创建多副本Pod以实现服务高可用,但Pod存在两个关键问题:一是Pod重建时IP会动态变化,二是Pod IP仅集群内部可见,外部无法直接访问。Service作为Pod的抽象访问层,完美解决了这些问题,它为一组同类Pod提供固定访问接口,同时实现服务发现与负载均衡。

(一)Service核心原理

Service通过标签选择器(Selector) 与Pod关联,只要Pod拥有Service指定的标签,就会被自动纳入Service的管理范围。Service会分配一个固定的Cluster IP,该IP在Service生命周期内保持不变,客户端通过Cluster IP访问服务,Service再将请求转发到后端Pod,实现负载均衡。

(二)Service实操案例

1. 创建集群内部可访问的Service(ClusterIP类型)

ClusterIP类型的Service仅在集群内部可见,适用于集群内服务间的通信。

  • 暴露Service:基于已有的Deployment(如名为nginx的Deployment,命名空间为dev)创建Service,指定Service名称为svc-nginx1,类型为ClusterIP,Service对外暴露端口80,并转发到Pod的80端口。
[root@master ~]# kubectl expose deploy nginx --name=svc-nginx1 --type=ClusterIP --port=80 --target-port=80 -n dev
service/svc-nginx1 exposed
  • 查看Service:通过kubectl get svc命令查看Service详情,可获取CLUSTER-IP(如10.109.179.231)、端口、关联的Pod标签选择器(run=nginx)等信息。
[root@master ~]# kubectl get svc svc-nginx1 -n dev -o wide
NAME         TYPE        CLUSTER-IP       EXTERNAL-IP   PORT(S)   AGE     SELECTOR
svc-nginx1   ClusterIP   10.109.179.231   <none>        80/TCP    3m51s   run=nginx
  • 访问Service:在集群内部(如Master节点或其他Pod),通过CLUSTER-IP:端口即可访问Service后端的Pod服务。
[root@master ~]# curl 10.109.179.231:80
<!DOCTYPE html><html><head><title>Welcome to nginx!</title></head><body><h1>Welcome to nginx!</h1>
.......</body></html>
2. 创建集群外部可访问的Service(NodePort类型)

NodePort类型的Service会在集群所有Node节点上开放一个固定端口,外部客户端可通过“Node IP:NodePort”访问服务,适用于需要对外暴露服务的场景。

  • 创建NodePort类型Service:基于nginxDeployment创建Service,名称为svc-nginx2,类型指定为NodePort,其他端口配置与ClusterIP类型一致。
[root@master ~]# kubectl expose deploy nginx --name=svc-nginx2 --type=NodePort --port=80 --target-port=80 -n dev
service/svc-nginx2 exposed
  • 查看NodePort Service:查看结果中PORT(S)列会显示“Service端口:NodePort端口”(如80:31928/TCP),其中31928是Node节点上开放的端口,范围通常为30000-32767
[root@master ~]# kubectl get svc  svc-nginx2  -n dev -o wide
NAME          TYPE        CLUSTER-IP       EXTERNAL-IP   PORT(S)        AGE    SELECTOR
svc-nginx2    NodePort    10.100.94.0      <none>        80:31928/TCP   9s     run=nginx
  • 外部访问Service:在集群外部的主机(如本地电脑),通过浏览器或curl命令访问“Node IP:NodePort”,即可访问服务(假设Node IP为192.168.100.10)。
http://192.168.100.10:31928/
3. 删除Service

当Service不再需要时,可通过名称或配置文件删除。

  • 通过名称删除:
[root@master ~]# kubectl delete svc svc-nginx-1 -n dev
service "svc-nginx-1" deleted
4. 通过配置文件创建Service

除了命令行方式,还可通过YAML配置文件定义Service,便于版本控制和批量部署。

  • 创建配置文件(svc-nginx.yaml):指定Service的API版本、类型、元数据、端口、标签选择器等信息,可手动固定clusterIP(需确保该IP未被占用)。
apiVersion: v1
kind: Service
metadata:name: svc-nginxnamespace: dev
spec:clusterIP: 10.109.179.231  # 固定Service的内网IP(可选)ports:- port: 80protocol: TCPtargetPort: 80selector:run: nginx  # 关联标签为“run=nginx”的Podtype: ClusterIP  # Service类型
  • 通过配置文件创建/删除Service
    • 创建:
kubectl create -f svc-nginx.yaml
  • 删除:
kubectl delete -f svc-nginx.yaml

二、Pod:Kubernetes最小部署单元

Pod是Kubernetes中最小的部署和调度单元,一个Pod可包含一个或多个容器,这些容器共享Pod的网络命名空间、存储卷等资源,在同一节点上协同运行。

(一)Pod资源清单完整解析

Pod的配置通过YAML资源清单定义,包含API版本、资源类型、元数据、规格等核心部分,以下是完整的资源清单结构及说明:

apiVersion: v1  # 必选,API版本(需通过kubectl api-versions查询确认)
kind: Pod       # 必选,资源类型(固定为Pod)
metadata:       # 必选,元数据(用于标识Pod)name: string  # 必选,Pod名称(在命名空间内唯一)namespace: string  # 可选,Pod所属命名空间(默认“default”)labels:       # 可选,自定义标签(键值对形式,用于Service关联、Pod筛选)key1: value1key2: value2
spec:  # 必选,Pod核心规格(定义容器、资源、调度等配置)containers:  # 必选,容器列表(一个Pod可包含多个容器)- name: string  # 必选,容器名称(在Pod内唯一)image: string  # 必选,容器镜像地址(如nginx:1.17.1)imagePullPolicy: [Always|Never|IfNotPresent]  # 可选,镜像拉取策略command: [string]  # 可选,容器启动命令(覆盖Dockerfile中的ENTRYPOINT)args: [string]     # 可选,启动命令参数(配合command使用)workingDir: string  # 可选,容器工作目录(默认容器根目录)volumeMounts:       # 可选,容器挂载存储卷配置- name: string      # 必选,引用spec.volumes中定义的存储卷名称mountPath: string # 必选,存储卷在容器内的挂载路径(绝对路径)readOnly: boolean # 可选,是否为只读模式(默认false)ports:  # 可选,容器暴露端口列表- name: string        # 可选,端口名称(在Pod内唯一)containerPort: int  # 必选,容器监听端口(1-65535)hostPort: int       # 可选,容器在主机上暴露的端口(默认与containerPort一致,不推荐设置,可能导致端口冲突)protocol: string    # 可选,端口协议(TCP/UDP/SCTP,默认TCP)env:  # 可选,容器环境变量列表- name: string  # 必选,环境变量名称value: string # 必选,环境变量值resources:  # 可选,容器资源限制与请求limits:  # 可选,资源上限(超过会导致容器重启)cpu: string     # CPU限制(单位:core,如“1”表示1核,“0.5”表示半核)memory: string  # 内存限制(单位:Gi/Mi,如“1Gi”“512Mi”)requests:  # 可选,资源请求(环境资源不足时Pod无法启动)cpu: string    # CPU请求(最小所需CPU)memory: string # 内存请求(最小所需内存)lifecycle:  # 可选,容器生命周期钩子(在特定阶段执行命令)postStart:  # 容器启动后立即执行(执行失败会触发重启策略)exec:command: [string]  # 执行的命令preStop:    # 容器终止前执行(无论结果如何,容器都会终止)exec:command: [string]livenessProbe:  # 可选,容器健康检查(探测失败多次后重启容器)exec:        # 执行命令检查(命令退出码为0表示健康)command: [string]httpGet:     # HTTP请求检查(返回2xx/3xx表示健康)path: string    # 请求路径port: number    # 请求端口host: string    # 请求主机(默认Pod IP)scheme: string  # 协议(HTTP/HTTPS,默认HTTP)httpHeaders:    # 自定义请求头- name: stringvalue: stringtcpSocket:   # TCP连接检查(连接成功表示健康)port: numberinitialDelaySeconds: 0  # 容器启动后首次探测延迟(单位:秒,默认0)timeoutSeconds: 1       # 探测超时时间(单位:秒,默认1)periodSeconds: 10       # 探测间隔时间(单位:秒,默认10)successThreshold: 1     # 探测成功次数阈值(默认1)failureThreshold: 3     # 探测失败次数阈值(默认3,超过则触发重启)securityContext:  # 可选,容器安全上下文(如特权模式)privileged: false  # 是否开启特权模式(默认false)restartPolicy: [Always|Never|OnFailure]  # 可选,Pod重启策略(默认Always)# Always:无论容器退出码如何,都重启(适用于长期运行服务)# Never:从不重启(适用于一次性任务)# OnFailure:仅当容器退出码非0时重启(适用于批处理任务)nodeName: <string>  # 可选,指定Pod调度到的节点名称(强制调度)nodeSelector: object  # 可选,基于节点标签调度(Pod仅调度到匹配标签的节点)key: valueimagePullSecrets:  # 可选,拉取私有镜像的密钥(引用Secret资源)- name: stringhostNetwork: false  # 可选,是否使用主机网络(默认false,true表示共享主机网络命名空间)volumes:  # 可选,Pod存储卷列表(供容器共享存储)- name: string  # 必选,存储卷名称emptyDir: {}  # 临时存储卷(与Pod生命周期一致,Pod删除后数据丢失)hostPath:     # 主机路径卷(挂载主机目录到Pod,适用于数据持久化到主机)path: string  # 主机上的目录路径secret:       # Secret卷(挂载Secret资源,存储敏感信息如密码)secretName: string  # Secret资源名称items:- key: string  # Secret中的键path: string # 挂载到容器内的路径configMap:    # ConfigMap卷(挂载ConfigMap资源,存储配置信息)name: string  # ConfigMap资源名称items:- key: stringpath: string
status:  # 可选,Pod状态信息(由Kubernetes自动生成,无需手动配置)phase: [Pending|Running|Succeeded|Failed|Unknown]  # Pod当前阶段conditions:  # Pod状态条件(如就绪状态、调度状态)containersStatuses:  # 容器状态列表(如启动状态、重启次数)

(二)Pod配置实操案例

1. 基础Pod配置(多容器示例)

创建包含两个容器(Nginx和Busybox)的Pod,用于演示基础配置。

  • 配置文件(pod-base.yaml)
apiVersion: v1
kind: Pod
metadata:name: pod-basenamespace: test  # 自定义命名空间(需提前创建,命令:kubectl create ns test)labels:user: user1    # 自定义标签
spec:containers:- name: nginx    # 第一个容器(Nginx,轻量级Web服务)image: nginx:1.17.1- name: busybox  # 第二个容器(Busybox,Linux命令工具集)image: busybox:1.30
  • 创建与查看Pod
    • 创建Pod:
[root@master ~]# kubectl create -f pod-base.yaml
pod/pod-base created
  • 查看Pod状态:刚创建时Pod处于ContainerCreating状态,等待容器拉取和启动;正常启动后READY列显示“2/2”(表示两个容器均就绪)。
[root@master ~]# kubectl get pod -n test
NAME       READY   STATUS              RESTARTS   AGE
pod-base   0/2     ContainerCreating   0          12s
# 等待片刻后再次查看
[root@master ~]# kubectl get pod -n test
NAME       READY   STATUS    RESTARTS   AGE
pod-base   2/2     Running   0          1m
2. 镜像拉取策略配置

imagePullPolicy用于控制容器镜像的拉取行为,避免重复拉取或拉取失败问题。

  • 配置文件(pod-imagepullpolicy.yaml)
apiVersion: v1
kind: Pod
metadata:name: pod-imagepullpolicynamespace: test
spec:containers:- name: nginximage: nginx:1.17.1imagePullPolicy: Never  # 仅使用本地镜像,不远程拉取- name: busyboximage: busybox:1.30imagePullPolicy: IfNotPresent  # 本地有则用本地,无则远程拉取(默认策略)
  • 镜像拉取策略说明
    • Always:每次启动Pod都从远程仓库拉取镜像(适用于镜像标签为latest的场景,默认策略)。
    • IfNotPresent:本地存在镜像则直接使用,不存在时从远程拉取(适用于镜像标签为固定版本的场景,默认策略)。
    • Never:仅使用本地镜像,若本地不存在则启动失败(适用于离线环境或本地测试)。
  • 创建Pod
[root@master ~]# kubectl create -f pod-imagepullpolicy.yaml
pod/pod-imagepullpolicy created
3. 容器启动命令配置

部分容器(如Busybox)启动后会自动退出,需通过command配置自定义启动命令,让容器保持运行。

  • 问题分析:Busybox是工具集而非长期运行服务,默认启动后无持续任务,会立即退出,导致Pod中Busybox容器反复重启。
  • 解决方案:通过command配置循环任务(如每隔3秒向文件写入当前时间),让容器持续运行。
  • 配置文件(pod-command.yaml)
apiVersion: v1
kind: Pod
metadata:name: pod-command1namespace: test
spec:containers:- name: nginximage: nginx:1.17.1imagePullPolicy: Never- name: busyboximage: busybox:1.30imagePullPolicy: Never# 启动命令:创建文件并循环写入时间command: ["/bin/sh", "-c", "touch /tmp/hello.txt; while true; do /bin/echo $(date +%T) >> /tmp/hello.txt; sleep 3; done;"]
  • 命令说明
    • /bin/sh -c:使用sh解释器执行后续命令。
    • touch /tmp/hello.txt:在容器内创建/tmp/hello.txt文件。
    • while true; do ...; done:循环执行命令,每隔3秒将当前时间(date +%T)追加到文件中。
  • 创建与验证Pod
    • 创建Pod:
[root@master ~]# kubectl create -f pod-command.yaml
pod/pod-command1 created
  • 查看Pod状态:两个容器均处于Running状态(READY列显示“2/2”)。
[root@master ~]# kubectl get pods -n test
pod-command1           2/2     Running             0               2s
  • 进入Busybox容器验证:通过kubectl exec命令进入容器,查看文件内容,确认命令正常执行。
# 进入容器(-it表示交互式终端,-c指定容器名称)
[root@master ~]# kubectl exec pod-command1 -n test -it -c busybox /bin/sh
kubectl exec [POD] [COMMAND] is DEPRECATED and will be removed in a future version. Use kubectl exec [POD] -- [COMMAND] instead.
/ # tail -f /tmp/hello.txt  # 实时查看文件内容
17:22:11
17:22:14
17:22:17
17:22:20
  • command与args的关系command对应Dockerfile中的ENTRYPOINTargs对应CMD,两者配合实现命令覆盖:
    1. 若均不配置:使用Dockerfile默认的ENTRYPOINTCMD
    2. 仅配置command:覆盖ENTRYPOINT,忽略Dockerfile的CMD
    3. 仅配置args:保留Dockerfile的ENTRYPOINT,用args替换CMD
    4. 均配置:完全覆盖Dockerfile的ENTRYPOINTCMD,执行command + args
4. 容器环境变量配置

通过env为容器设置环境变量,用于传递配置信息(如数据库账号、服务地址等)。

  • 配置文件(pod-env.yaml)
apiVersion: v1
kind: Pod
metadata:name: pod-envnamespace: test
spec:containers:- name: busyboximage: busybox:1.30imagePullPolicy: Nevercommand: ["/bin/sh", "-c", "while true; do /bin/echo $(date +%T); sleep 60; done;"]env:  # 环境变量列表- name: "username"  # 环境变量名称value: "admin"    # 环境变量值- name: "password"value: "redhat"
  • 创建与验证环境变量
    • 创建Pod:
[root@master ~]# kubectl create -f pod-env.yaml
pod/pod-env created
  • 查看Pod状态:
[root@master ~]# kubectl get pod -n test
pod-env                1/1     Running            0               16s
  • 进入容器验证环境变量:通过echo $变量名查看环境变量值。
[root@master ~]# kubectl exec pod-env -n test -c busybox -it /bin/sh
kubectl exec [POD] [COMMAND] is DEPRECATED and will be removed in a future version. Use kubectl exec [POD] -- [COMMAND] instead.
/ # echo $username
admin
/ # echo $password
redhat
  • 注意事项:直接在配置文件中写敏感信息(如密码)存在安全风险,推荐使用Secret资源存储敏感信息,再通过envvolumeMounts引用。
5. 容器端口配置

通过ports配置容器暴露的端口,便于Service关联和内部通信。

  • 查看ports子选项:通过kubectl explain命令查看ports支持的配置项。
[root@k8s-master01 ~]# kubectl explain pod.spec.containers.ports
KIND:     Pod
VERSION:  v1
RESOURCE: ports <[]Object>
FIELDS:name         <string>  # 端口名称(Pod内唯一,可选)containerPort<integer> # 容器监听端口(1-65535,必选)hostPort     <integer> # 主机暴露端口(可选,不推荐,易冲突)hostIP       <string>  # 主机IP(可选,默认0.0.0.0)protocol     <string>  # 协议(TCP/UDP/SCTP,默认TCP)
  • 配置文件(pod-ports.yaml)
apiVersion: v1
kind: Pod
metadata:name: pod-portsnamespace: test
spec:containers:- name: nginximage: nginx:1.17.1imagePullPolicy: Neverports:- name: nginx-port  # 端口名称containerPort: 80  # 容器监听端口(Nginx默认端口)protocol: TCP      # 协议
  • 创建与验证端口配置
    • 创建Pod:
[root@master ~]# kubectl create -f pod-ports.yaml
pod/pod-ports created
  • 查看Pod详情:通过-o yaml查看完整配置,确认端口配置生效。
[root@master ~]# kubectl get pod pod-ports -n test -o yaml
......
spec:containers:- image: nginx:1.17.1imagePullPolicy: Nevername: nginxports:- containerPort: 80name: nginx-portprotocol: TCP
......
  • 访问容器服务:通过Pod IP和containerPort访问Nginx服务。
    1. 获取Pod IP:
[root@master ~]# kubectl get pod pod-ports -n test -o wide
NAME        READY   STATUS    RESTARTS   AGE     IP            NODE    NOMINATED NODE   READINESS GATES
pod-ports   1/1     Running   0          3m40s   10.244.1.16   node1   <none>           <none>
2. 访问服务:
[root@master ~]# curl http://10.244.1.16:80
<!DOCTYPE html><html><head><title>Welcome to nginx!</title></head><body><h1>Welcome to nginx!</h1>
......</body></html>
6. 容器资源配额配置

通过resources配置容器的CPU和内存资源限制(limits)与请求(requests),避免单个容器占用过多资源,保障集群稳定性。

  • 资源配额核心概念
    • limits:容器运行时的最大资源占用(超过会触发容器重启)。
    • requests:容器启动所需的最小资源(集群资源不足时Pod无法调度)。
  • 资源单位说明
    • CPU:单位为“core”,支持整数(如“1”)或小数(如“0.5”,表示半核)。
    • 内存:单位支持Gi(1Gi=1024Mi)、MiG(1G=1000M)、M,推荐使用Gi/Mi(二进制单位,更符合内存计算逻辑)。
  • 配置文件(pod-resources.yaml)
apiVersion: v1
kind: Pod
metadata:name: pod-resourcesnamespace: test
spec:containers:- name: nginximage: nginx:1.17.1imagePullPolicy: Neverresources:limits:  # 资源上限cpu: "2"        # 最大CPU占用:2核memory: "10Gi"  # 最大内存占用:10Girequests:  # 资源请求cpu: "1"         # 最小CPU需求:1核memory: "10Mi"   # 最小内存需求:10Mi
  • 创建与验证资源配置
    • 正常创建(资源充足场景):
[root@master ~]# kubectl create -f pod-resources.yaml
pod/pod-resources created
[root@master ~]# kubectl get pods -n test
pod-resources          1/1     Running            0                10s
  • 资源不足场景(模拟):修改requests.memory10Gi(超过节点可用内存),Pod会处于Pending状态,无法调度。
    1. 修改配置文件:
requests:memory: "10Gi"
2. 重新创建Pod:
[root@master ~]# kubectl delete -f pod-resources.yaml
pod "pod-resources" deleted
[root@master ~]# kubectl create -f pod-resources.yaml
pod/pod-resources created
3. 查看Pod状态:
[root@master ~]# kubectl get pods -n test
pod-resources          0/1     Pending            0                16s
4. 查看调度失败原因:通过`kubectl describe`查看事件,显示“Insufficient memory”(内存不足)。
[root@master ~]# kubectl describe pod pod-resources -n test
Warning  FailedScheduling  87s   default-scheduler  0/3 nodes are available: 1 node(s) had untolerated taint {node-role.kubernetes.io/control-plane: }, 3 Insufficient memory. preemption: 0/3 nodes are available: 1 Preemption is not helpful for scheduling, 2 No preemption victims found for incoming pod.

(三)Pod关键工具命令

  1. 查看资源可配置项:通过kubectl explain命令查看Pod及子资源的可配置项,便于编写配置文件。
    • 查看Pod一级属性:
kubectl explain pod
  • 查看Pod元数据(metadata)子属性:
kubectl explain pod.metadata
  • 查看容器(containers)子属性:
kubectl explain pod.spec.containers
  1. 进入容器执行命令:通过kubectl exec命令进入Pod中的指定容器,进行调试或操作。
kubectl exec -it <pod名称> -n <命名空间> -c <容器名称> -- <命令>
# 示例:进入pod-command1的busybox容器,执行/bin/sh
kubectl exec -it pod-command1 -n test -c busybox -- /bin/sh
  1. 查看Pod日志:通过kubectl logs命令查看容器日志,排查故障。
kubectl logs <pod名称> -n <命名空间> -c <容器名称>  # 查看指定容器日志
kubectl logs -f <pod名称> -n <命名空间> -c <容器名称>  # 实时查看日志(类似tail -f)

三、总结

  1. Service核心价值:为动态变化的Pod提供固定访问入口,实现集群内/外服务访问与负载均衡,解决Pod IP动态变化和外部访问问题。
  2. Pod核心特性:作为最小部署单元,支持多容器协同运行,通过资源清单精细控制容器的镜像、命令、环境变量、端口、资源配额等配置,满足不同业务场景需求。
  3. 实践建议
    • 生产环境中,优先通过YAML配置文件管理Service和Pod,便于版本控制和批量部署。
    • 容器资源配额需合理配置,避免资源浪费或不足导致的服务不稳定。
    • 敏感信息(如密码、密钥)避免直接写在配置文件中,应使用Secret资源管理。
    • 定期通过kubectl describekubectl logs等命令排查Pod故障,保障服务正常运行。
http://www.dtcms.com/a/553941.html

相关文章:

  • Qt Creator打开项目提示no valid settings file could be found
  • ⑥ leetcode刷题汇总(二叉树)
  • 使用 Zabbix agent 2 监控PostgreSQL
  • 网站推广产品怎么做学校网站建设维护
  • Webpack loader 的执行机制
  • 前端基础之《React(6)—webpack简介-图片模块处理》
  • 西格电力绿电直连通信实战指南:5G、工业以太网、光纤核心对比与协议无缝兼容方案
  • 企业网站有哪些功能?淘宝网页版电脑版入口
  • 排序(选择排序、直接插入排序、冒泡排序、二路归并排序)
  • 少儿编程:6-16 岁孩子的思维启蒙与能力进阶之路
  • 10/31作业
  • 前端样式局部作用域:从Scoped到CSS Modules 的完整指南
  • 穆棱建设局网站seo 哪些媒体网站可以发新闻
  • 物联网卡摄像头从前端至后台的实现过程
  • 整合多中心临床试验的转录组与病理切片数据,提出面向晚期非小细胞肺癌免疫治疗疗效预测的解决方案
  • 【计算机网络】考研408计算机网络:传输介质(导向/非导向)考点梳理
  • 网站开发合同适用印花税互联网专业主要学什么
  • iFluor 594 Styramide,水溶性荧光探针
  • 零基础网站建设及维护视频课程东莞有哪些好的网站建设公司
  • (151页PPT)大型制造集团十五五产业数字化转型规划方案(附下载方式)
  • 新能源硬件架构设计前沿:DFX思维如何平衡可靠性、成本与可维护性
  • 跨平台直播美颜sdk集成攻略:Android、iOS与Web的统一方案
  • Go环境搭建(vscode调试)
  • 宜兴做网站哪个好南充市建设局官方网站
  • 网站建设 交单流程wordpress收录
  • STM32的DH11温湿度模块和LED灯的综合实训
  • 模型微调实现案例分析
  • Blender云渲染农场怎么收费?渲一个一分钟的Blender动画需要多少钱?
  • 搜狐登陆password参数逆向
  • 官宣:Ray 正式加入 PyTorch 基金会