K8s 持久化存储
PV / PVC / StorageClass 关系
PV(PersistentVolume) = 仓库(管理员准备好的存储空间)
PVC(PersistentVolumeClaim)= 租仓单(用户申请多大空间、什么类型)
StorageClass = 仓库分类标准(高性能/普通/便宜)
静态供应 vs 动态供应
静态供应
管理员提前创建 PV,用户创建 PVC 去绑定。适合小规模或特殊存储要求场景。
# PV
apiVersion: v1
kind: PersistentVolume
metadata:
name: my-pv
spec:
capacity:
storage: 10Gi
accessModes:
- ReadWriteOnce
persistentVolumeReclaimPolicy: Retain
nfs:
server: 192.168.1.100
path: /data/nfs
# PVC
apiVersion: v1
kind: PersistentVolumeClaim
metadata:
name: my-pvc
spec:
accessModes:
- ReadWriteOnce
resources:
requests:
storage: 5Gi # 必须 ≤ PV 的 capacity
动态供应(推荐)
通过 StorageClass 自动创建 PV,用户只需在 PVC 中指定 StorageClass。
# StorageClass
apiVersion: storage.k8s.io/v1
kind: StorageClass
metadata:
name: fast-ssd
provisioner: kubernetes.io/aws-ebs
parameters:
type: gp2
encrypted: "true"
# PVC(指定 storageClassName 即可动态创建 PV)
apiVersion: v1
kind: PersistentVolumeClaim
metadata:
name: dynamic-pvc
spec:
accessModes:
- ReadWriteOnce
storageClassName: fast-ssd
resources:
requests:
storage: 20Gi
生命周期
Available(可用)→ Bound(已绑定)→ Released(已释放)→ Failed(失败)
回收策略
| 策略 | 行为 | 适用场景 |
|---|---|---|
| Retain ✅ | 保留数据,需手动清理 | 数据库等有状态应用(数据安全第一) |
| Delete | 自动删除 PV 和底层存储 | 临时数据/日志 |
| Recycle | 已废弃,不推荐 | — |
访问模式
| 模式 | 缩写 | 说明 | 适用场景 |
|---|---|---|---|
| ReadWriteOnce | RWO | 单节点读写 | 数据库(MySQL/Redis)— 最常用 |
| ReadOnlyMany | ROX | 多节点只读 | 配置文件、静态资源 |
| ReadWriteMany | RWX | 多节点读写 | 共享文件存储(需存储后端支持,如 NFS) |
⚠️ 坑:用了不支持 RWX 的存储系统,Pod 会一直 Pending。详见 storage-troubleshooting。
生产案例
案例 1:MySQL 数据库持久化
apiVersion: apps/v1
kind: Deployment
metadata:
name: mysql
spec:
replicas: 1
selector:
matchLabels:
app: mysql
template:
spec:
containers:
- name: mysql
image: mysql:8.0
volumeMounts:
- name: mysql-storage
mountPath: /var/lib/mysql
volumes:
- name: mysql-storage
persistentVolumeClaim:
claimName: mysql-pvc
关键点:加密 EBS 卷 + Retain 策略 + 挂载到数据目录。
案例 2:多 Pod 共享存储(NFS)
apiVersion: v1
kind: PersistentVolume
metadata:
name: shared-pv
spec:
capacity:
storage: 50Gi
accessModes:
- ReadWriteMany
nfs:
server: nfs-server.example.com
path: /shared/data
必须使用支持 RWX 的存储后端(如 NFS、CephFS)。
存储选型建议
| 场景 | 存储类型 | 访问模式 | 回收策略 |
|---|---|---|---|
| 数据库(MySQL/Redis) | SSD | RWO | Retain |
| 文件服务/共享存储 | 网络存储(NFS) | RWX | Delete |
| 日志收集 | HDD(大容量) | RWO | Delete |
| 临时数据 | 本地存储 | RWO | Delete |
性能优化
- 数据库 → SSD(IOPS 高、延迟低)
- 日志/备份 → HDD(容量大、成本低)
- 配置文件 → 网络存储(可共享)
- 预留 20-30% 空间用于扩展
- 定期清理无用数据
监控告警
groups:
- name: storage.rules
rules:
- alert: PVCStorageUsageHigh
expr: (kubelet_volume_stats_used_bytes / kubelet_volume_stats_capacity_bytes) * 100 > 85
for: 5m
labels:
severity: warning
常见问题
| 问题 | 排查方向 |
|---|---|
| PVC Pending | kubectl describe pvc 查看事件 / kubectl get pv / kubectl get storageclass |
| Pod 挂载失败 | 节点是否支持该存储类型 / 权限 / 存储系统状态 |
| 数据丢失 | 使用 Retain 策略 / 定期备份 / 演练恢复流程 |
完整排障方法见 storage-troubleshooting。
关于数据库上 K8s 的架构选型讨论,参见 database-on-kubernetes-debate。
关联页面
| 页面 | 关联点 |
|---|---|
| node-troubleshooting | Node 排障与 k8s-statefulset-guide 的 Pod 行为交叉 |
| jenkins-multi-master-k8s-deployment | Jenkins 多 Master 部署中的 StatefulSet + PVC 实际案例 |
- linux-nfs-mount-parameters-guide — NFS 挂载参数全解析(K8s 中使用 NFS 作为 PV 时的参数配置)