跳到主要内容
版本:v3.0.x

设置 CDC 复制

本指南介绍如何使用 Milvus Operator 部署两个独立的 Milvus 集群,并配置 CDC 复制从源集群到目标集群。

示例使用

  • source-cluster 作为主群集。
  • target-cluster 作为备用群集。
  • milvus 作为 Milvus 群集的命名空间。
  • milvus-operator 作为 Milvus Operator 的命名空间。

开始之前,请阅读Milvus CDC以了解主备模型和故障转移选项。

先决条件

  • Milvus v2.6.16 或更高版本。
  • Milvus Operator v1.3.4 或更高版本。
  • Kubernetes 集群可用。
  • 源群集和目标群集可以通过网络相互连接。
  • 拥有两个 Milvus 集群的管理员凭证。
  • 知道每个群集的物理通道数。

步骤 1:升级 Milvus 操作符

添加 Milvus Operator Helm 资源库:

helm repo add zilliztech-milvus-operator https://zilliztech.github.io/milvus-operator/

更新版本库:

helm repo update zilliztech-milvus-operator

安装或升级 Milvus Operator:

helm -n milvus-operator upgrade --install milvus-operator \
zilliztech-milvus-operator/milvus-operator \
--create-namespace

检查操作符 pod 是否正在运行:

kubectl get pods -n milvus-operator

输出示例:

NAME                               READY   STATUS    RESTARTS   AGE
milvus-operator-6f7d8c9c7d-xm4tj 1/1 Running 0 54s

步骤 2:部署源群集

创建名为milvus_source_cluster.yaml 的文件:

apiVersion: milvus.io/v1beta1
kind: Milvus
metadata:
name: source-cluster
namespace: milvus
labels:
app: milvus
spec:
mode: standalone
components:
image: milvusdb/milvus:v2.6.16
cdc:
replicas: 1
dependencies:
msgStreamType: woodpecker

应用配置:

kubectl create namespace milvus
kubectl apply -f milvus_source_cluster.yaml

检查源群集 pod 是否正在运行:

kubectl get pods -n milvus

示例输出:

NAME                                                   READY   STATUS    RESTARTS   AGE
source-cluster-etcd-0 1/1 Running 0 3m
source-cluster-minio-6d8f7d9b9f-9t7j2 1/1 Running 0 3m
source-cluster-milvus-standalone-7f8d9c8f6d-r2m5x 1/1 Running 0 2m
source-cluster-milvus-cdc-66d64747bd-sckxj 1/1 Running 0 2m

确保 CDC pod(如source-cluster-milvus-cdc-... )处于Running 状态。

第 3 步:部署目标群集

创建名为milvus_target_cluster.yaml 的文件:

apiVersion: milvus.io/v1beta1
kind: Milvus
metadata:
name: target-cluster
namespace: milvus
labels:
app: milvus
spec:
mode: standalone
components:
image: milvusdb/milvus:v2.6.16
cdc:
replicas: 1
dependencies:
msgStreamType: woodpecker

CDC 组件也已在目标群集上启用。在目标群集为备用群集时,该组件处于空闲状态,但如果目标群集在切换后成为主群集,则需要该组件。

应用配置:

kubectl apply -f milvus_target_cluster.yaml

检查目标群集 pod 是否正在运行:

kubectl get pods -n milvus | grep -E 'NAME|target-cluster'

输出示例:

NAME                                                   READY   STATUS    RESTARTS   AGE
target-cluster-etcd-0 1/1 Running 0 3m
target-cluster-minio-5f7c8d9b6f-k8s2q 1/1 Running 0 3m
target-cluster-milvus-standalone-66dc8d9f7f-5n6bp 1/1 Running 0 2m
target-cluster-milvus-cdc-7f8c9d6b8c-q4t9m 1/1 Running 0 2m

步骤 4:准备群集信息

获取两个群集的 Milvus 服务地址:

kubectl get svc -n milvus | grep -E 'NAME|source-cluster|target-cluster'

输出示例

NAME                                  TYPE        CLUSTER-IP       EXTERNAL-IP   PORT(S)              AGE
source-cluster-milvus ClusterIP 10.98.124.90 <none> 19530/TCP,9091/TCP 8m
target-cluster-milvus ClusterIP 10.109.234.172 <none> 19530/TCP,9091/TCP 3m

准备两种地址:

  • 群集地址被写入复制配置并由 CDC 组件使用。这些地址必须可以从 CDC pod 到达。
  • 客户端地址仅在调用 Milvus API 时由 Python 客户端使用。如果在 Kubernetes 集群外运行 Python 客户端,请通过正常访问方法(如负载平衡器、入口或端口转发)公开 Milvus 服务。

为两个集群准备连接信息和 pchannel 列表:

source_cluster_addr = "http://source-cluster-milvus.milvus.svc.cluster.local:19530"
target_cluster_addr = "http://target-cluster-milvus.milvus.svc.cluster.local:19530"

source_client_addr = source_cluster_addr
target_client_addr = target_cluster_addr

# If your Python client runs outside the Kubernetes cluster, replace only
# source_client_addr and target_client_addr with externally reachable addresses.
# Keep source_cluster_addr and target_cluster_addr reachable from CDC pods.
# For example:
# source_client_addr = "http://127.0.0.1:19530"
# target_client_addr = "http://127.0.0.1:19531"

source_cluster_token = "root:Milvus"
target_cluster_token = "root:Milvus"

source_cluster_id = "source-cluster"
target_cluster_id = "target-cluster"

pchannel_num = 16
source_cluster_pchannels = [
f"{source_cluster_id}-rootcoord-dml_{i}"
for i in range(pchannel_num)
]
target_cluster_pchannels = [
f"{target_cluster_id}-rootcoord-dml_{i}"
for i in range(pchannel_num)
]

将地址替换为环境中实际的 Milvus 服务地址。不要将source_cluster_addrtarget_cluster_addr 设置为本地端口转发地址,除非 CDC pod 也能到达该地址。pchannel 列表必须与 Milvus 部署相匹配。请勿在未检查群集配置的情况下复制示例值。

第 5 步:创建复制配置

创建从source-clustertarget-cluster 的复制配置:

replicate_config = {
"clusters": [
{
"cluster_id": source_cluster_id,
"connection_param": {
"uri": source_cluster_addr,
"token": source_cluster_token,
},
"pchannels": source_cluster_pchannels,
},
{
"cluster_id": target_cluster_id,
"connection_param": {
"uri": target_cluster_addr,
"token": target_cluster_token,
},
"pchannels": target_cluster_pchannels,
},
],
"cross_cluster_topology": [
{
"source_cluster_id": source_cluster_id,
"target_cluster_id": target_cluster_id,
}
],
}

第 6 步:应用复制配置

对两个群集应用相同的配置:

from pymilvus import MilvusClient

source_client = MilvusClient(
uri=source_client_addr,
token=source_cluster_token,
)
target_client = MilvusClient(
uri=target_client_addr,
token=target_cluster_token,
)

try:
source_client.update_replicate_configuration(**replicate_config)
target_client.update_replicate_configuration(**replicate_config)
finally:
source_client.close()
target_client.close()

对于生产自动化,请使用单独的短命客户机进行此控制平面操作。这样可以避免在群集角色发生变化时与应用程序 DML 流量共享同一个 gRPC 通道。

应用配置后,写入source-cluster 的更改将复制到target-cluster

第 7 步:验证数据复制

验证复制是否有效:

  1. 连接到source-cluster
  2. 创建 Collection。
  3. 将数据插入 Collection。
  4. 加载 Collection 并在source-cluster 上运行查询或搜索。
  5. 连接到target-cluster
  6. target-cluster 上运行相同的查询或搜索,无需在备用群集上手动加载 Collection。
  7. 确认预期数据在两个群集上都可见。

目标群集是此拓扑中的备用群集。请勿在备用群集上运行手动 DDL 或 DCL 操作,如load_collection 。这些操作应在源群集上执行,并复制到目标群集。

确切的验证码取决于您的 Collection Schema。有关基本的 Milvus Collection 工作流程,请参阅 Milvus 快速入门文档。

CDC 滞后

CDC 滞后是指主集群和备用集群之间的数据窗口。配置复制后,应持续监控它。

CDC 滞后会在以下情况下增加:

  • 主写入率高。
  • 群集之间的网络延迟或数据包丢失增加。
  • 备用群集超载。
  • CDC 节点配置不足。
  • 正在运行大型 DDL 或导入操作。

使用 CDC 滞后来指导操作符决策:

  • 如果滞后较低,切换应更快完成。
  • 如果滞后较高,故障切换可能会丢失更多数据。

可以使用以下 PromQL 查询估算 CDC 滞后:

clamp_min(
max by (channel_name) (
milvus_wal_last_confirmed_time_tick
)
- min by (channel_name) (
milvus_cdc_last_replicated_time_tick
),
0
)

结果以秒为单位。对于每个源通道,该查询将最新确认的 WAL 时间戳与 CDC 复制的最后一个时间戳进行比较。如果主集群复制到多个备用集群,min by (channel_name) 表达式会报告该通道最慢的复制进度。

如果 Prometheus 扫描多个 Milvus 群集,请添加与部署相匹配的标签过滤器,如namespaceapp_kubernetes_io_instance ,以避免混合来自不同群集的指标。

常见问题

我需要在两个集群上都调用update_replicate_configuration 吗?

需要。对所有参与的群集应用相同的拓扑结构。如果一个群集在调用时不是主群集,它将等待,直到通过 CDC 应用拓扑。

如何选择cluster_id

为每个群集使用一个稳定、唯一的 ID。该 ID 也用于 pchannel 名称和复制拓扑引用。

配置复制后,能否更改 pchannel?

可以更新拓扑,但 pchannel 列表必须与群集布局相匹配。将 pchannel 更改视为高级操作符,并在更改后仔细验证复制。