4. Velero 实战部署:Helm 部署 + MinIO 存储 + 备份恢复验证
Velero 这个工具,说白了就是 Kubernetes 的「时光机」。它能帮你把整个命名空间、应用状态、PV 数据,一股脑儿备份到对象存储里。哪天集群炸了、误删了、升级回滚了,拉回来就能用。
我最早接触 Velero 是在一个金融客户的灾备项目里。当时他们要求 RPO 小于 15 分钟,RTO 小于 30 分钟。嗯,Velero 配合定时备份和快速恢复,确实扛住了压力。今天咱们就手把手把它部署起来。
4.1 整体架构速览
先看一张图,把 Velero 的组件和流程理清楚。你心里有个谱,后面操作才不会迷路。
Velero 由两部分组成:服务端(运行在集群里的控制器)和 客户端(命令行工具 velero)。服务端负责干活,客户端负责发号施令。
4.2 前置准备
动手之前,先把环境理清楚。我习惯列个清单,一项项打勾,省得到时候手忙脚乱。
| 项目 | 要求 | 说明 |
|---|---|---|
| Kubernetes 集群 | v1.20+ | 建议用 1.24+,CRI 兼容性更好 |
| Helm | v3.8+ | 我用的 v3.12,稳定 |
| MinIO | 最新稳定版 | 可以部署在集群内或外部 |
| kubectl | 与集群版本匹配 | 别差太多版本 |
| 对象存储桶 | 1 个 | 名字随意,比如 velero-backup |
4.3 部署 MinIO
MinIO 的部署方式很多。这里我用 Docker 快速起一个,方便演示。生产环境建议用 StatefulSet 部署到集群里,或者直接用硬件。
# 创建数据目录
mkdir -p /data/minio
# 启动 MinIO 容器
docker run -d \
--name minio \
-p 9000:9000 \
-p 9001:9001 \
-e MINIO_ROOT_USER=admin \
-e MINIO_ROOT_PASSWORD=admin123456 \
-v /data/minio:/data \
quay.io/minio/minio server /data --console-address ":9001"
# 创建 bucket
# 访问 http://<你的IP>:9001,用 admin/admin123456 登录
# 手动创建一个名为 velero-backup 的桶
嗯,这里要注意。MinIO 的 Access Key 和 Secret Key 后面要用到,记下来。我一般把它们存到 Kubernetes Secret 里,而不是明文写在配置里。
4.4 使用 Helm 部署 Velero
Helm 部署 Velero 是最省事的方式。官方 Chart 已经把大部分配置都封装好了。你只需要提供 MinIO 的访问信息。
4.4.1 添加 Helm 仓库
helm repo add vmware-tanzu https://vmware-tanzu.github.io/helm-charts
helm repo update
4.4.2 创建 values 文件
我个人习惯把配置写到一个 values.yaml 里,方便版本管理和复用。下面是我常用的配置模板:
# velero-values.yaml
configuration:
provider: aws
backupStorageLocation:
- name: default
provider: aws
bucket: velero-backup
config:
region: minio
s3Url: http://192.168.1.100:9000
publicUrl: http://192.168.1.100:9000
s3ForcePathStyle: true
volumeSnapshotLocation:
- name: default
provider: aws
config:
region: minio
credentials:
useSecret: true
secretContents:
cloud: |
[default]
aws_access_key_id = admin
aws_secret_access_key = admin123456
initContainers:
- name: velero-plugin-for-aws
image: velero/velero-plugin-for-aws:v1.7.0
volumeMounts:
- mountPath: /target
name: plugins
deployRestic: true
restic:
podVolumePath: /var/lib/kubelet/pods
4.4.3 执行部署
helm install velero vmware-tanzu/velero \
--namespace velero \
--create-namespace \
-f velero-values.yaml
等个一两分钟,检查 Pod 状态:
kubectl get pods -n velero
# 输出示例:
# NAME READY STATUS RESTARTS AGE
# velero-7d8f9c6b8c-abc12 1/1 Running 0 2m
看到 Running 就说明部署成功了。如果一直 Pending 或 CrashLoopBackOff,别慌。先看日志:
kubectl logs -n velero deployment/velero
大部分问题都是 MinIO 连不上、密钥不对、或者桶不存在。排查思路很直接。
4.5 安装 Velero CLI
服务端跑起来了,还得装个客户端工具。CLI 用来下发备份、恢复、查看状态等操作。
# 下载最新版 CLI
wget https://github.com/vmware-tanzu/velero/releases/download/v1.12.0/velero-v1.12.0-linux-amd64.tar.gz
tar -xzf velero-v1.12.0-linux-amd64.tar.gz
sudo mv velero-v1.12.0-linux-amd64/velero /usr/local/bin/
# 验证
velero version
CLI 会自动读取 kubeconfig 和 velero 命名空间。你不需要额外配置,直接就能用。
4.6 验证备份功能
部署完了,得真刀真枪试一下。我一般先备份一个测试命名空间,看看能不能正常跑通。
4.6.1 创建测试应用
kubectl create namespace test-backup
kubectl create deployment nginx -n test-backup --image=nginx
kubectl expose deployment nginx -n test-backup --port=80
4.6.2 执行手动备份
velero backup create test-backup-001 \
--include-namespaces test-backup \
--ttl 72h
备份命令执行后,Velero 会做以下几件事:
- 调用 K8s API 获取 test-backup 命名空间下的所有资源清单
- 通过 Restic 读取挂载的 PV 数据
- 将所有数据打包成 tar.gz,上传到 MinIO 桶
查看备份状态:
velero backup get
# 输出示例:
# NAME STATUS CREATED EXPIRES
# test-backup-001 Completed 2024-01-15 10:30:00 +0800 CST 3d
STATUS 为 Completed 就说明备份成功了。如果显示 Failed,用 velero backup describe test-backup-001 看详细错误。
backups/test-backup-001/,里面包含资源清单的 JSON 和 PV 数据的 tar 包。
4.7 验证恢复功能
备份是为了恢复。咱们模拟一个灾难场景:把 test-backup 命名空间删了,然后用 Velero 恢复。
4.7.1 模拟灾难
kubectl delete namespace test-backup
# 确认命名空间已删除
kubectl get ns test-backup
# 输出:Error from server (NotFound): namespaces "test-backup" not found
4.7.2 执行恢复
velero restore create --from-backup test-backup-001
恢复过程是备份的逆操作:
- 从 MinIO 下载备份包
- 解析资源清单,调用 K8s API 重建资源
- 如果有 PV 数据,通过 Restic 恢复到对应 PVC
查看恢复状态:
velero restore get
# 输出示例:
# NAME BACKUP STATUS CREATED
# test-backup-001-202401151045 test-backup-001 Completed 2024-01-15 10:45:00 +0800 CST
验证恢复结果:
kubectl get all -n test-backup
# 应该能看到 nginx deployment 和 service 都回来了
--namespace-mappings 参数把备份恢复到不同的命名空间,比如 --namespace-mappings test-backup:test-backup-restored。这在做跨集群迁移时特别有用。
4.8 定时备份配置
手动备份只是验证功能。生产环境肯定要配定时备份。Velero 用 Schedule 资源来实现。
# 创建每天凌晨 2 点执行的定时备份
velero schedule create daily-backup \
--schedule="0 2 * * *" \
--include-namespaces test-backup \
--ttl 168h
查看定时任务:
velero schedule get
# 输出示例:
# NAME STATUS CREATED SCHEDULE
# daily-backup Enabled 2024-01-15 11:00:00 +0800 CST 0 2 * * *
定时备份会自动创建备份对象,你只需要定期检查备份状态就行。我一般会在监控里加一条告警:如果最近一次备份失败,就发钉钉或邮件通知。
4.9 常见问题与避坑
最后,分享几个我实际项目中遇到过的问题,你遇到了可以少走弯路。
| 问题 | 原因 | 解决方案 |
|---|---|---|
| 备份一直 Pending | Velero 无法连接 MinIO | 检查 s3Url 是否正确,网络是否可达 |
| 备份 Failed,报 403 | Access Key / Secret Key 错误,或 s3ForcePathStyle 未设置 | 检查密钥,添加 s3ForcePathStyle: true |
| 恢复后 Pod 起不来 | PV 数据恢复失败,或 StorageClass 不匹配 | 检查 Restic 日志,确认 PVC 的 StorageClass 存在 |
| Restic 备份很慢 | PV 数据量大,或网络带宽不足 | 考虑使用 Kopia 替代 Restic,或限速备份 |
restic.podVolumePath 和你的集群配置一致。
好了,到这一步,Velero 的部署、备份、恢复、定时任务就全跑通了。你可以在测试环境多试几次,熟悉一下各种参数。后面咱们会讲更高级的用法,比如跨集群迁移、加密备份、增量备份等等。