267 lines
7.3 KiB
Markdown
267 lines
7.3 KiB
Markdown
|
|
---
|
|||
|
|
tags: [microservice, kubernetes, k8s, container-orchestration]
|
|||
|
|
create time: 2026-05-05
|
|||
|
|
---
|
|||
|
|
|
|||
|
|
# Kubernetes
|
|||
|
|
|
|||
|
|
## 概述
|
|||
|
|
|
|||
|
|
Kubernetes (K8s) 是微服务架构的事实标准编排引擎。它将容器化的服务组织成声明式的资源对象,自动处理部署、扩展、故障恢复。
|
|||
|
|
|
|||
|
|
```mermaid
|
|||
|
|
graph TB
|
|||
|
|
subgraph CLUSTER["K8s Cluster"]
|
|||
|
|
Master["控制面<br/>API Server / Scheduler / Controller Manager / etcd"]
|
|||
|
|
|
|||
|
|
subgraph NODES["工作节点"]
|
|||
|
|
N1["Node A<br/>kubelet + kube-proxy"]
|
|||
|
|
N2["Node B<br/>kubelet + kube-proxy"]
|
|||
|
|
end
|
|||
|
|
|
|||
|
|
Master --> N1
|
|||
|
|
Master --> N2
|
|||
|
|
|
|||
|
|
subgraph APPS["应用层"]
|
|||
|
|
Order["Order Service Deployment"]
|
|||
|
|
Pay["Payment Service Deployment"]
|
|||
|
|
end
|
|||
|
|
|
|||
|
|
N1 --> Order
|
|||
|
|
N2 --> Order
|
|||
|
|
N1 --> Pay
|
|||
|
|
N2 --> Pay
|
|||
|
|
end
|
|||
|
|
|
|||
|
|
SVC["Service (ClusterIP)"] -->|Load Balance| Order
|
|||
|
|
Ingress["Ingress (HTTP Routing)"] --> SVC
|
|||
|
|
|
|||
|
|
style Master fill:#e3f2fd
|
|||
|
|
style N1 fill:#fff3e0
|
|||
|
|
style N2 fill:#fff3e0
|
|||
|
|
```
|
|||
|
|
|
|||
|
|
## 核心概念速查
|
|||
|
|
|
|||
|
|
| K8s 对象 | 用途 | 类比 |
|
|||
|
|
|---------|------|------|
|
|||
|
|
| **Pod** | 最小部署单元,包含一个或多个容器 | 应用实例 |
|
|||
|
|
| **Deployment** | 管理 Pod 的副本数和滚动更新 | 应用的"模板" |
|
|||
|
|
| **Service** | 稳定的网络入口,负载均衡 | 内部 VIP |
|
|||
|
|
| **Ingress** | HTTP/HTTPS 路由规则 | 外部网关 |
|
|||
|
|
| **ConfigMap** | 配置注入(明文) | 环境变量/配置文件 |
|
|||
|
|
| **Secret** | 敏感配置注入(base64) | 密码/API Key |
|
|||
|
|
| **HPA** | 根据指标自动扩缩容 | 弹性伸缩 |
|
|||
|
|
| **StatefulSet** | 有状态应用的有序管理 | DB、ZK |
|
|||
|
|
| **Job/CronJob** | 一次性任务 / 定时任务 | 批处理 |
|
|||
|
|
|
|||
|
|
## Deployment 详解
|
|||
|
|
|
|||
|
|
### 完整示例
|
|||
|
|
|
|||
|
|
```yaml
|
|||
|
|
apiVersion: apps/v1
|
|||
|
|
kind: Deployment
|
|||
|
|
metadata:
|
|||
|
|
name: order-service
|
|||
|
|
labels:
|
|||
|
|
app: order
|
|||
|
|
version: v1.2.3
|
|||
|
|
spec:
|
|||
|
|
replicas: 3 # 期望副本数
|
|||
|
|
strategy:
|
|||
|
|
type: RollingUpdate
|
|||
|
|
rollingUpdate:
|
|||
|
|
maxSurge: 1 # 最多超额 1 个 Pod
|
|||
|
|
maxUnavailable: 0 # 滚动更新期间不允许不可用
|
|||
|
|
|
|||
|
|
selector:
|
|||
|
|
matchLabels:
|
|||
|
|
app: order
|
|||
|
|
|
|||
|
|
template:
|
|||
|
|
metadata:
|
|||
|
|
labels:
|
|||
|
|
app: order
|
|||
|
|
version: v1.2.3
|
|||
|
|
spec:
|
|||
|
|
containers:
|
|||
|
|
- name: order-service
|
|||
|
|
image: registry.example.com/order:v1.2.3
|
|||
|
|
ports:
|
|||
|
|
- containerPort: 8080
|
|||
|
|
|
|||
|
|
# ========== 资源配置 ==========
|
|||
|
|
resources:
|
|||
|
|
requests: # 调度依据:保证至少有这些
|
|||
|
|
cpu: "250m"
|
|||
|
|
memory: "256Mi"
|
|||
|
|
limits: # 硬上限:超过则 OOMKill/CPU Throttle
|
|||
|
|
cpu: "500m"
|
|||
|
|
memory: "512Mi"
|
|||
|
|
|
|||
|
|
# ========== 探针 ==========
|
|||
|
|
livenessProbe:
|
|||
|
|
httpGet:
|
|||
|
|
path: /healthz
|
|||
|
|
port: 8080
|
|||
|
|
initialDelaySeconds: 15
|
|||
|
|
periodSeconds: 10
|
|||
|
|
failureThreshold: 3 # 连续失败 3 次才重启
|
|||
|
|
|
|||
|
|
readinessProbe:
|
|||
|
|
httpGet:
|
|||
|
|
path: /ready
|
|||
|
|
port: 8080
|
|||
|
|
initialDelaySeconds: 5
|
|||
|
|
periodSeconds: 5
|
|||
|
|
failureThreshold: 3
|
|||
|
|
|
|||
|
|
startupProbe:
|
|||
|
|
httpGet:
|
|||
|
|
path: /healthz
|
|||
|
|
port: 8080
|
|||
|
|
failureThreshold: 30 # 最长等待 300s (慢启动友好)
|
|||
|
|
|
|||
|
|
# ========== 环境变量 & 挂载 ==========
|
|||
|
|
envFrom:
|
|||
|
|
- configMapRef:
|
|||
|
|
name: order-service-config
|
|||
|
|
- secretRef:
|
|||
|
|
name: order-service-secrets
|
|||
|
|
|
|||
|
|
lifecycle:
|
|||
|
|
preStop:
|
|||
|
|
exec:
|
|||
|
|
command: ["sh", "-c", "sleep 15"] # 优雅退出,给 LB 摘流时间
|
|||
|
|
```
|
|||
|
|
|
|||
|
|
### Probe 选择指南
|
|||
|
|
|
|||
|
|
| 探针类型 | 触发条件 | 动作 | 适用场景 |
|
|||
|
|
|---------|---------|------|---------|
|
|||
|
|
| **Liveness** | `/healthz` 返回非 2xx | 重启容器 | 死锁、无法恢复的崩溃 |
|
|||
|
|
| **Readiness** | `/ready` 返回非 2xx | 摘除 Service 流量 | 依赖未就绪、热加载中 |
|
|||
|
|
| **Startup** | 首次成功前持续失败 | 不重启,只等待 | 大模型/JVM 冷启动 |
|
|||
|
|
|
|||
|
|
> [!warning] 经典陷阱:CrashLoopBackOff
|
|||
|
|
>
|
|||
|
|
> 如果 Liveness Probe 因为 DB 连接超时而返回 503,K8s 会认为容器挂了并反复重启它——这就是 CrashLoopBackOff。正确做法是:让 `/healthz` 做降级判断(DB 不可用时返回 200),用 `/ready` 来摘除流量。
|
|||
|
|
|
|||
|
|
## Service 与 Ingress
|
|||
|
|
|
|||
|
|
### Service 类型
|
|||
|
|
|
|||
|
|
| 类型 | 特点 | 使用场景 |
|
|||
|
|
|------|------|---------|
|
|||
|
|
| **ClusterIP** | 集群内 IP,外部不可访问 | 默认,内部服务间调用 |
|
|||
|
|
| **NodePort** | 在每个 Node 上开端口 | 调试、临时访问 |
|
|||
|
|
| **LoadBalancer** | 云厂商分配公网 IP | 对外暴露的服务 |
|
|||
|
|
| **ExternalName** | CNAME 到外部域名 | 对接外部系统 |
|
|||
|
|
|
|||
|
|
```yaml
|
|||
|
|
# ClusterIP Service — 服务发现的载体
|
|||
|
|
apiVersion: v1
|
|||
|
|
kind: Service
|
|||
|
|
metadata:
|
|||
|
|
name: order-service
|
|||
|
|
spec:
|
|||
|
|
selector:
|
|||
|
|
app: order
|
|||
|
|
ports:
|
|||
|
|
- port: 80
|
|||
|
|
targetPort: 8080
|
|||
|
|
protocol: TCP
|
|||
|
|
type: ClusterIP
|
|||
|
|
```
|
|||
|
|
|
|||
|
|
调用方只需 `http://order-service:80`,K8s 通过 iptables/IPVS 自动实现负载均衡。
|
|||
|
|
|
|||
|
|
### Ingress — HTTP 路由
|
|||
|
|
|
|||
|
|
```yaml
|
|||
|
|
apiVersion: networking.k8s.io/v1
|
|||
|
|
kind: Ingress
|
|||
|
|
metadata:
|
|||
|
|
name: main-ingress
|
|||
|
|
annotations:
|
|||
|
|
nginx.ingress.kubernetes.io/rewrite-target: /
|
|||
|
|
spec:
|
|||
|
|
rules:
|
|||
|
|
- host: api.example.com
|
|||
|
|
http:
|
|||
|
|
paths:
|
|||
|
|
- path: /orders
|
|||
|
|
pathType: Prefix
|
|||
|
|
backend:
|
|||
|
|
service:
|
|||
|
|
name: order-service
|
|||
|
|
port:
|
|||
|
|
number: 80
|
|||
|
|
- path: /users
|
|||
|
|
pathType: Prefix
|
|||
|
|
backend:
|
|||
|
|
service:
|
|||
|
|
name: user-service
|
|||
|
|
port:
|
|||
|
|
number: 80
|
|||
|
|
```
|
|||
|
|
|
|||
|
|
## HPA 弹性伸缩
|
|||
|
|
|
|||
|
|
```yaml
|
|||
|
|
apiVersion: autoscaling/v2
|
|||
|
|
kind: HorizontalPodAutoscaler
|
|||
|
|
metadata:
|
|||
|
|
name: order-service-hpa
|
|||
|
|
spec:
|
|||
|
|
scaleTargetRef:
|
|||
|
|
apiVersion: apps/v1
|
|||
|
|
kind: Deployment
|
|||
|
|
name: order-service
|
|||
|
|
minReplicas: 3
|
|||
|
|
maxReplicas: 20
|
|||
|
|
metrics:
|
|||
|
|
- type: Resource
|
|||
|
|
resource:
|
|||
|
|
name: cpu
|
|||
|
|
target:
|
|||
|
|
type: Utilization
|
|||
|
|
averageUtilization: 70 # CPU > 70% 时扩容
|
|||
|
|
- type: Resource
|
|||
|
|
resource:
|
|||
|
|
name: memory
|
|||
|
|
target:
|
|||
|
|
type: Utilization
|
|||
|
|
averageUtilization: 80
|
|||
|
|
behavior:
|
|||
|
|
scaleUp:
|
|||
|
|
stabilizationWindowSeconds: 60 # 扩容稳定期
|
|||
|
|
policies:
|
|||
|
|
- type: Pods
|
|||
|
|
value: 2
|
|||
|
|
periodSeconds: 60 # 每分钟最多扩 2 个
|
|||
|
|
scaleDown:
|
|||
|
|
stabilizationWindowSeconds: 300 # 缩容稳定期 5min(防抖动)
|
|||
|
|
```
|
|||
|
|
|
|||
|
|
## K8s 运维 Checklist
|
|||
|
|
|
|||
|
|
每次上线前过一遍这个清单:
|
|||
|
|
|
|||
|
|
| # | 检查项 | 说明 |
|
|||
|
|
|---|--------|------|
|
|||
|
|
| 1 | **Probe 已配置** | liveness/readiness/startup 都设定了阈值 |
|
|||
|
|
| 2 | **Resources Limits** | 防止单个 Pod OOMKill 拖垮整台机器 |
|
|||
|
|
| 3 | **日志输出到 stdout/stderr** | 可被采集器解析为 JSON |
|
|||
|
|
| 4 | **trace_id 透传** | 跨服务调用链 trace_id 不丢失 |
|
|||
|
|
| 5 | **回滚预案** | `kubectl rollout undo deployment/order-service` 能用 |
|
|||
|
|
| 6 | **告警已配置** | 关键指标异常时有人收到通知 |
|
|||
|
|
| 7 | **镜像 Tag** | 不用 latest,用语义化版本或 commit SHA |
|
|||
|
|
|
|||
|
|
## 关联笔记
|
|||
|
|
|
|||
|
|
- [[02-服务治理/04-服务发现]] — K8s Service 是服务端发现模式的代表
|
|||
|
|
- [[02-服务治理/08-流量治理]] — Istio VirtualService 在 K8s 上的高级路由
|
|||
|
|
- [[05-部署运维/04-SRE实践]] — SLO/Error Budget 在 K8s 中的落地
|