2. K8s核心概念回顾:Pod、Deployment、Service、Ingress、Namespace基础
在深入金丝雀发布流水线之前,必须对齐Kubernetes的五大核心原语。这些对象构成了应用部署、网络暴露与多环境隔离的基石。本章以“声明式期望状态”为主线,逐一拆解每个原语的角色、生命周期与协作关系。
2.1 Pod:最小的调度与运行单元
Pod是K8s中可创建和管理的最小计算单元。一个Pod封装一个或多个容器(通常为一个主容器加若干Sidecar),共享网络栈(IP+端口空间)和存储卷。
- 共享网络:Pod内所有容器通过
localhost通信,对外暴露统一IP。 - 共享存储:通过Volume挂载,容器间可交换数据。
- 生命周期短暂:Pod被设计为“可抛弃的”,重建后IP会变化。
- 健康检查:支持
livenessProbe(存活)与readinessProbe(就绪)。
金丝雀视角:金丝雀发布中,新版Pod与旧版Pod同时运行,通过流量权重控制用户访问比例。Pod的
readinessProbe必须精准配置,确保未就绪的新版本不接收流量。
2.2 Deployment:声明式副本管理与滚动更新
Deployment是无状态工作负载的控制器,负责管理ReplicaSet并驱动Pod达到期望状态。它提供了金丝雀发布最核心的机制——滚动更新与回滚。
| 特性 | 说明 | 金丝雀相关 |
|---|---|---|
| 期望副本数 | 声明Pod数量,控制器自动扩缩 | 金丝雀阶段可临时增加副本数 |
| 更新策略 | RollingUpdate(默认)或 Recreate |
金丝雀必须使用 RollingUpdate |
| maxSurge | 更新期间允许超出期望副本数的最大Pod数 | 控制金丝雀扩容速度 |
| maxUnavailable | 更新期间允许不可用Pod的最大数量 | 保障金丝雀期间服务不降级 |
| 回滚 | 通过Revision历史快速恢复至旧版本 | 金丝雀失败时一键回滚 |
# 金丝雀场景:Deployment更新策略示例
apiVersion: apps/v1
kind: Deployment
metadata:
name: my-app-stable
spec:
replicas: 10
strategy:
type: RollingUpdate
rollingUpdate:
maxSurge: 2 # 允许最多2个额外Pod
maxUnavailable: 1 # 允许1个Pod不可用
selector:
matchLabels:
app: my-app
version: stable
template:
metadata:
labels:
app: my-app
version: stable
spec:
containers:
- name: app
image: my-app:1.0.0
readinessProbe:
httpGet:
path: /healthz
port: 8080
2.3 Service:稳定的网络访问抽象层
由于Pod IP不固定,Service提供了稳定的虚拟IP(ClusterIP)和DNS名称,作为Pod前端的负载均衡器。Service通过 selector 标签动态绑定后端Pod。
- ClusterIP(默认):集群内部可访问,金丝雀流量分发的基础。
- NodePort:在每个节点开放固定端口,外部可通过
NodeIP:NodePort访问。 - LoadBalancer:云厂商提供外部负载均衡器。
- 无头Service(Headless):不分配ClusterIP,直接返回Pod IP列表,用于StatefulSet。
金丝雀关键点:Service的
selector通常只匹配 app: my-app,不区分版本。新版Pod和旧版Pod只要都带有 app: my-app 标签,就会被Service同时纳入后端,实现流量混合。
2.4 Ingress:七层路由与流量治理
Ingress是K8s的七层(HTTP/HTTPS)入口网关,负责将外部请求按域名、路径路由到集群内部Service。相比Service的L4转发,Ingress支持更精细的流量切分——这正是金丝雀发布的关键能力。
| Ingress控制器 | 金丝雀支持方式 | 适用场景 |
|---|---|---|
| Nginx Ingress | 通过 nginx.ingress.kubernetes.io/canary 注解 |
基于权重或Header的金丝雀 |
| Traefik | 通过 traefik.ingress.kubernetes.io/router.middlewares |
基于权重或Cookie的金丝雀 |
| Istio Gateway | 通过VirtualService的 weight 字段 |
精细化流量治理与服务网格 |
# Nginx Ingress 金丝雀示例:10%流量导向新版
apiVersion: networking.k8s.io/v1
kind: Ingress
metadata:
name: my-app-canary
annotations:
nginx.ingress.kubernetes.io/canary: "true"
nginx.ingress.kubernetes.io/canary-weight: "10"
spec:
ingressClassName: nginx
rules:
- host: my-app.example.com
http:
paths:
- path: /
pathType: Prefix
backend:
service:
name: my-app-canary-svc
port:
number: 80
2.5 Namespace:多租户隔离与资源边界
Namespace将物理集群划分为多个虚拟集群,用于环境隔离(dev/staging/prod)、团队隔离或金丝雀发布中的“蓝绿环境”隔离。
- 资源配额:通过
ResourceQuota限制每个Namespace的CPU/内存总量。 - 网络策略:通过
NetworkPolicy控制Namespace内外的流量。 - 角色绑定:通过RBAC为不同Namespace分配不同权限。
- 金丝雀实践:通常将稳定版与金丝雀版部署在同一Namespace,通过标签区分;但大型项目也可使用独立Namespace实现完全隔离。
注意:金丝雀发布不建议跨Namespace部署同一应用的不同版本,因为Service无法跨Namespace直接发现Pod。同一Namespace内通过标签选择器即可完成流量分发,更简洁可控。
2.6 五大原语协作关系图
下图展示了从外部请求到Pod的完整流量路径,以及各原语在金丝雀发布中的角色定位。
2.7 核心概念速查表
| 原语 | API版本(稳定) | 作用域 | 金丝雀发布中的角色 |
|---|---|---|---|
| Pod | v1 |
Namespace | 运行容器实例,新版与旧版共存 |
| Deployment | apps/v1 |
Namespace | 管理Pod副本,控制滚动更新节奏 |
| Service | v1 |
Namespace | 提供统一入口,将流量分发至新旧Pod |
| Ingress | networking.k8s.io/v1 |
Namespace | 七层路由,实现权重/Header金丝雀切流 |
| Namespace | v1 |
集群 | 逻辑隔离环境,资源配额与网络策略边界 |
2.8 金丝雀发布中的原语协作流程
- 用户请求到达Ingress控制器(如Nginx Ingress)。
- Ingress根据金丝雀注解(权重10%或特定Header)将请求路由到金丝雀Service或主Service。
- Service通过标签选择器将请求转发至后端Pod:主Service匹配
version=stable,金丝雀Service匹配version=canary。 - Deployment分别管理稳定版和金丝雀版的Pod副本数与更新策略。
- 金丝雀验证通过后,逐步调整Ingress权重(10% → 50% → 100%),最终将金丝雀Deployment提升为稳定版。
核心原则:金丝雀发布不依赖任何特殊K8s扩展,仅通过Ingress流量权重 + Deployment多版本共存 + Service标签选择即可实现。理解这五大原语的协作关系,是后续自动化流水线设计的基础。