pv-migrate:Kubernetes 持久卷迁移工具技术分析

一、概述

1. 简介

A. 是什么

pv-migrate 是一个 CLI 工具和 kubectl 插件,用于轻松地在 Kubernetes 集群之间迁移 PersistentVolumeClaim(PVC)的内容。

B. 为什么需要

在 Kubernetes 中,迁移普通资源(如 Deployment)很简单,只需复制 YAML 清单并应用即可。但 PVC 不同,它不仅包含元数据,还在底层存储后端存储实际数据。这使得 PVC 迁移变得复杂,需要专门的工具来处理数据传输。

C. 能做什么

  • 在同一命名空间内迁移 PVC
  • 在同一集群的不同命名空间间迁移
  • 跨不同 Kubernetes 集群迁移
  • 更改 StorageClass(如从 ReadWriteOnce 到 ReadWriteMany)
  • 支持安全的数据传输(SSH 加密)
  • 多种迁移策略和自动降级

2. 核心特性

  • 支持 rsync over SSH 传输,使用 Ed25519 或 RSA 密钥
  • 支持多种迁移策略(本地、通过 SSH 等)
  • 支持跨集群、跨命名空间迁移
  • 支持多架构:amd64、arm64、arm32v7
  • 支持主流 Shell 自动补全:bash、zsh、fish、powershell
  • 完全可定制的清单(自定义镜像、亲和性配置等)

二、工作原理

1. 系统架构

graph TB
    subgraph "源集群"
        SourcePVC[源 PVC]
        SourcePod[Rsync Helper Pod]
        SourceSSHD[SSH Daemon Pod]
    end

    subgraph "目标集群"
        DestPVC[目标 PVC]
        DestPod[Rsync Helper Pod]
    end

    CLI[pv-migrate CLI] -->|创建| SourceSSHD
    CLI -->|创建| SourcePod
    CLI -->|创建| DestPod

    SourcePod -->|挂载| SourcePVC
    DestPod -->|挂载| DestPVC

    DestPod -->|SSH 连接| SourceSSHD
    DestPod -->|rsync 传输| SourcePod

pv-migrate 系统架构

2. 迁移流程

sequenceDiagram
    participant User as 用户
    participant CLI as pv-migrate CLI
    participant K8s as Kubernetes API
    participant SPod as 源集群 Rsync Pod
    participant DPod as 目标集群 Rsync Pod

    User->>CLI: 执行迁移命令
    CLI->>K8s: 创建 SSH Daemon Pod(源)
    CLI->>K8s: 创建 Rsync Helper Pod(源)
    CLI->>K8s: 创建 Rsync Helper Pod(目标)
    K8s-->>CLI: Pod 就绪
    DPod->>SPod: 建立 SSH 连接
    DPod->>SPod: 执行 rsync 传输数据
    SPod-->>DPod: 传输进度
    DPod-->>CLI: 迁移完成
    CLI->>K8s: 清理临时 Pod
    CLI-->>User: 报告结果

迁移流程时序图

3. 迁移策略

pv-migrate 支持多种迁移策略,按优先级依次尝试:

A. Local 策略

当源和目标 PVC 在同一节点上时,直接使用本地文件系统复制,无需网络传输。

B. SSH 策略

当 PVC 在不同节点或集群时,通过 SSH 建立加密通道,使用 rsync 传输数据。

C. Tar 策略

当 SSH 不可用时,使用 tar 打包传输作为降级方案。

4. 安全机制

A. SSH 密钥管理

  • 每次迁移自动生成新的 Ed25519 或 RSA 密钥对
  • 密钥仅存在于临时 Pod 生命周期内
  • 传输完成后自动清理

B. 网络安全

  • 跨集群迁移支持 SSH 加密传输
  • 支持 SSH 隧道穿透防火墙
  • 可配置自定义 SSH 参数

三、使用场景

1. PVC 扩容迁移

当 PVC 不支持动态扩容时:

# 创建更大的新 PVC
kubectl apply -f new-pvc.yaml

# 迁移数据
pv-migrate migrate old-pvc new-pvc

2. 跨命名空间迁移

# 在目标命名空间创建同名 PVC
kubectl apply -n target-ns -f pvc.yaml

# 执行迁移
pv-migrate migrate source-pvc --source-ns source-ns \
  --dest-ns target-ns

3. 跨集群迁移

# 配置目标集群 kubeconfig
export KUBECONFIG_DEST=/path/to/dest-cluster.yaml

# 执行跨集群迁移
pv-migrate migrate my-pvc \
  --dest-kubeconfig "$KUBECONFIG_DEST"

4. StorageClass 更换

# 从 ReadWriteOnce 更换到 ReadWriteMany
pv-migrate migrate local-path-pvc nfs-pvc

四、安装方式

1. 使用 krew(kubectl 插件管理器)

kubectl krew index add kvaps
kubectl krew install kvaps/pv-migrate

2. 二进制安装

curl -sLO https://github.com/utkuozdemir/pv-migrate/releases/download/v2.2.1/pv-migrate_2.2.1_linux_amd64.tar.gz
tar -xzf pv-migrate_2.2.1_linux_amd64.tar.gz
sudo mv pv-migrate /usr/local/bin/

3. Docker 方式

docker run --rm -it \
  -v ~/.kube:/root/.kube \
  utkuozdemir/pv-migrate:latest \
  migrate source-pvc dest-pvc

4. 从源码编译

git clone https://github.com/utkuozdemir/pv-migrate.git
cd pv-migrate
make build
sudo mv bin/pv-migrate /usr/local/bin/

五、核心命令

1. 基本语法

pv-migrate [命令] [标志]

2. 主要命令

migrate

执行 PVC 迁移:

pv-migrate migrate <源PVC> <目标PVC> [选项]

常用选项:

  • --source-ns:源 PVC 所在命名空间
  • --dest-ns:目标 PVC 所在命名空间
  • --source-kubeconfig:源集群 kubeconfig 路径
  • --dest-kubeconfig:目标集群 kubeconfig 路径
  • --strategies:指定迁移策略顺序
  • --delete-source-data:迁移完成后删除源数据
  • --compress:启用压缩传输
  • --rsync-path:自定义 rsync 路径

completion

生成 Shell 自动补全脚本:

# Bash
pv-migrate completion bash > /etc/bash_completion.d/pv-migrate

# Zsh
pv-migrate completion zsh > /usr/share/zsh/vendor-completions/_pv-migrate

# Fish
pv-migrate completion fish > ~/.config/fish/completions/pv-migrate.fish

六、高级配置

1. 自定义镜像

使用自定义的 rsync 和 sshd 镜像:

pv-migrate migrate src dest \
  --rsync-image my-registry/rsync:custom \
  --sshd-image my-registry/sshd:custom

2. 节点亲和性配置

指定迁移 Pod 运行的节点:

pv-migrate migrate src dest \
  --source-node-affinity "kubernetes.io/hostname=node-1" \
  --dest-node-affinity "kubernetes.io/hostname=node-2"

3. 资源限制

配置迁移 Pod 的资源请求和限制:

pv-migrate migrate src dest \
  --rsync-cpu-request 500m \
  --rsync-memory-request 256Mi \
  --rsync-cpu-limit 2000m \
  --rsync-memory-limit 1Gi

4. 容忍配置

允许迁移 Pod 调度到特定节点:

pv-migrate migrate src dest \
  --source-taints "key=value:NoSchedule" \
  --dest-taints "key=value:NoSchedule"

七、最佳实践

1. 迁移前准备

  • 确保目标 PVC 容量不小于源 PVC
  • 验证源 PVC 没有被 Pod 挂载或业务已暂停
  • 检查集群节点资源充足
  • 备份重要数据

2. 选择合适的迁移策略

  • 同节点优先:使用 Local 策略
  • 跨节点/集群:使用 SSH 策略
  • 网络受限:考虑 Tar 策略

3. 监控迁移进度

pv-migrate 提供实时进度条显示,可以监控:

  • 已传输数据量
  • 传输速度
  • 预计剩余时间
  • 当前执行策略

4. 迁移后验证

# 检查目标 PVC 容量使用
kubectl exec -it <pod-using-dest-pvc> -- df -h /mount/path

# 验证文件完整性
kubectl exec -it <pod-using-dest-pvc> -- \
  find /mount/path -type f | wc -l

八、故障排查

1. Pod 启动失败

检查镜像拉取和资源配额:

kubectl describe pod -l app=pv-migrate-rsync

2. SSH 连接失败

验证网络策略和防火墙规则,确保 SSH 端口可访问。

3. rsync 传输中断

检查磁盘空间和网络稳定性,可重新执行迁移命令(rsync 支持增量传输)。

九、项目信息

  • 语言:Go(91.7%)、Go Template(5.1%)、Shell(2.0%)
  • 许可证:Apache-2.0
  • GitHub Stars:2.2k
  • 最新版本:v2.2.1(2025 年 2 月)
  • 维护状态:活跃(最近更新于 2026 年 1 月)

参考资料

  1. pv-migrate GitHub 仓库
  2. Kubernetes Persistent Volumes 官方文档
  3. rsync 官方文档
最后修改:2026 年 01 月 24 日
如果觉得我的文章对你有用,请随意赞赏