2. K8s 核心概念回顾:Pod、Deployment、Service、ConfigMap、Secret、Namespace
在深入流水线自动化之前,必须对齐 Kubernetes 的核心抽象层。这些资源是发布、配置、网络与隔离的基石;配置漂移与回滚修复正是围绕这些对象的版本与状态展开。
2.1 资源层级与职责总览
下表从“发布流水线”视角重新定义每个核心对象的角色,而非单纯罗列定义。
| 资源 | API 版本(稳定) | 在流水线中的核心职责 | 是否直接参与发布 |
|---|---|---|---|
| Pod | v1 | 运行容器实例,是发布的最小原子单元 | 否(由控制器管理) |
| Deployment | apps/v1 | 声明式更新、滚动发布、回滚版本控制 | 是 |
| Service | v1 | 提供稳定的网络端点,解耦 Pod IP 变化 | 否(但影响流量切换) |
| ConfigMap | v1 | 注入非敏感配置,环境变量/文件挂载 | 是(配置变更触发) |
| Secret | v1 | 注入敏感数据(密钥、证书、) | 是(配置变更触发) |
| Namespace | v1 | 资源隔离与多环境(dev/staging/prod)划分 | 否(环境边界) |
流水线视角: 配置漂移通常发生在 Deployment.spec.template 中的镜像版本、环境变量(来自 ConfigMap/Secret)或资源限制字段。回滚修复的本质是将 Deployment 的 revision 恢复到已知正确的历史版本。
2.2 Pod:不可变的最小调度单元
Pod 是 K8s 中可创建和部署的最小计算单元。一个 Pod 封装一个或多个容器、存储资源、网络 IP 以及容器运行选项。
- 生命周期短暂: Pod 被设计为“有生死的”,不会自愈;控制器(如 Deployment)负责维持期望的 Pod 副本数。
- 共享网络与存储: 同一 Pod 内的容器共享网络栈(localhost 通信)和 Volume。
- 在流水线中的角色: 发布流水线不直接操作 Pod,而是通过更新 Deployment 的 PodTemplate 来触发 Pod 重建。
# 一个简单的 Pod 定义(通常不直接用于生产发布)
apiVersion: v1
kind: Pod
metadata:
name: my-app-pod
labels:
app: my-app
spec:
containers:
- name: app
image: registry.example.com/my-app:v1.2.3
ports:
- containerPort: 8080
2.3 Deployment:发布与回滚的核心控制器
Deployment 为 Pod 和 ReplicaSet 提供声明式更新能力。它是 CI/CD 流水线中最常操作的对象。
- 滚动更新(RollingUpdate): 默认策略,逐步替换旧 Pod,保证服务不中断。
- 版本记录(Revision): 每次 .spec.template 变更都会生成一个新的 ReplicaSet 并记录版本号。
- 回滚(Rollback): 通过
kubectl rollout undo或指定 revision 恢复到历史版本。
配置漂移典型场景: 手动执行
kubectl set image 或 kubectl edit deployment 绕过流水线,导致集群中的 Deployment 与 Git 仓库中的 YAML 不一致。回滚修复即重新应用 Git 中的正确版本并重置 revision。
# Deployment 示例(流水线自动生成)
apiVersion: apps/v1
kind: Deployment
metadata:
name: my-app
namespace: production
spec:
replicas: 3
revisionHistoryLimit: 10 # 保留最近 10 个版本用于回滚
strategy:
type: RollingUpdate
rollingUpdate:
maxUnavailable: 1
maxSurge: 1
selector:
matchLabels:
app: my-app
template:
metadata:
labels:
app: my-app
spec:
containers:
- name: app
image: registry.example.com/my-app:v1.2.3
envFrom:
- configMapRef:
name: app-config
- secretRef:
name: app-secret
2.4 Service:稳定的网络抽象层
Service 定义一组 Pod 的访问策略,提供固定的 ClusterIP 或 DNS 名称,屏蔽后端 Pod 的 IP 变化。
| Service 类型 | 访问范围 | 典型用途 |
|---|---|---|
| ClusterIP | 集群内部 | 微服务间调用 |
| NodePort | 集群外部(节点 IP + 端口) | 开发测试环境暴露 |
| LoadBalancer | 外部通过云负载均衡器 | 生产环境公网入口 |
注意: Service 本身不参与版本回滚,但发布流水线必须确保 Service 的 selector 与新 Deployment 的 Pod 标签匹配,否则流量无法路由到新版本 Pod,造成“发布成功但服务不可用”的漂移假象。
2.5 ConfigMap 与 Secret:配置与敏感数据注入
这两个资源将配置数据从容器镜像中解耦,是实现“不可变基础设施”的关键。
- ConfigMap: 存储非敏感配置(如应用配置文件、环境变量)。
- Secret: 存储敏感数据(密码、、TLS 证书),数据以 Base64 编码存储,支持加密(如 KMS)。
- 注入方式: 环境变量(
envFrom或valueFrom)或 Volume 挂载(volumes+volumeMounts)。
# ConfigMap 示例
apiVersion: v1
kind: ConfigMap
metadata:
name: app-config
namespace: production
data:
APP_ENV: "production"
LOG_LEVEL: "info"
app.properties: |
db.host=db.internal
db.port=5432
---
# Secret 示例(data 字段需 Base64 编码)
apiVersion: v1
kind: Secret
metadata:
name: app-secret
namespace: production
type: Opaque
data:
DB_PASSWORD: c3VwZXJzZWNyZXQ= # "supersecret" 的 Base64
配置漂移高发区: ConfigMap/Secret 的内容变更不会自动触发 Pod 重启。流水线必须通过更新 Deployment 的注解(如
checksum/config)或使用工具(Reloader)来触发滚动更新,否则新配置不会生效,形成“配置已更新但应用未感知”的漂移。
2.6 Namespace:多环境隔离边界
Namespace 将物理集群划分为多个虚拟集群,是 CI/CD 流水线中区分开发、测试、预发布、生产环境的逻辑边界。
- 资源隔离: 不同 Namespace 中的 Pod、Service、ConfigMap 相互不可见(除非通过跨 Namespace 服务发现)。
- 配额管理: 可为每个 Namespace 设置 ResourceQuota 和 LimitRange,防止资源争抢。
- 流水线映射: 通常 Git 分支(feature/staging/main)对应不同 Namespace(dev/staging/prod)。
2.7 核心对象关系图
下图展示了发布流水线中核心 K8s 对象的协作关系,以及配置漂移可能发生的链路。
2.8 配置漂移与回滚修复的关键映射
将上述概念映射到流水线自动化场景:
- 漂移检测: 比较 Git 仓库中的 Deployment YAML(特别是
spec.template.spec.containers[].image和envFrom引用)与集群中实际运行的资源。 - 回滚修复: 使用
kubectl rollout undo deployment/my-app --to-revision=N或通过 GitOps 工具(ArgoCD)自动同步回 Git 中的正确版本。 - 配置同步: 当 ConfigMap/Secret 变更时,流水线必须更新 Deployment 的
template.metadata.annotations(如kubectl patch deployment my-app -p '{"spec":{"template":{"metadata":{"annotations":{"config-update":"2025-01-15T10:00:00Z"}}}}}}')来触发滚动更新。
最佳实践: 在 CI/CD 流水线中,每次部署前执行
kubectl diff -f k8s/manifests/ 对比当前集群状态与期望清单,提前发现漂移并中断流水线,而非事后回滚。