管理快照Compatible with Milvus 3.0.x
在本指南中,您将学习如何创建和管理快照,包括
创建快照
在创建快照之前,建议您停止向目标 Collection 写入数据,并调用 `flush() ` 方法,以避免可能的数据丢失。
调用 `flush() ` 并非强制要求,但强烈建议执行此操作以避免数据丢失。若跳过此步骤,快照将仅包含已刷新完成的数据。
为快照命名时,请使用清晰、描述性强的名称,例如"daily_backup_20240101" 或"v2.1_production_release" ,并避免使用通用术语,例如"backup1" 和"test" 。请明智地使用快照名称,以区分不同版本、环境和阶段的快照。
下面的代码示例假设您已经有一个名为my_collection 的 Collection。
from pymilvus import MilvusClient
client = MilvusClient(
uri="http://localhost:19530",
token="root:Milvus"
)
# Recommended: Flush data before creating snapshot to ensure all data is included
client.flush(collection_name="my_collection")
# Create snapshot for entire collection
client.create_snapshot(
collection_name="my_collection",
snapshot_name="backup_20240101",
description="Daily backup for January 1st, 2024"
)
// java
import (
"context"
"github.com/milvus-io/milvus/client/v2/milvusclient"
)
client, err := milvusclient.New(context.Background(), &milvusclient.ClientConfig{
Address: "localhost:19530",
Token: "root:Milvus",
})
// Recommended: Flush data before creating snapshot to ensure all data is included
err = client.Flush(context.Background(), milvusclient.NewFlushOption("my_collection"))
if err != nil {
log.Fatal(err)
}
// Create snapshot
createOpt := milvusclient.NewCreateSnapshotOption("backup_20240101", "my_collection").
WithDescription("Daily backup for January 1st, 2024")
err = client.CreateSnapshot(context.Background(), createOpt)
// node.js
# restful
列出快照
您可以列出现有快照的名称。
# List all snapshots for a collection
snapshots = client.list_snapshots(
collection_name="my_collection"
)
// java
// List snapshots for collection
listOpt := milvusclient.NewListSnapshotsOption().
WithCollectionName("my_collection")
snapshots, err := client.ListSnapshots(context.Background(), listOpt)
// node.js
# bash
描述快照
您可以获取特定快照的详细信息。
snapshot_info = client.describe_snapshot(
snapshot_name="backup_20240101",
include_collection_info=True
)
print(f"Snapshot ID: {snapshot_info.id}")
print(f"Collection: {snapshot_info.collection_name}")
print(f"Created: {snapshot_info.create_ts}")
print(f"Description: {snapshot_info.description}")
// java
describeOpt := milvusclient.NewDescribeSnapshotOption("backup_20240101")
resp, err := client.DescribeSnapshot(context.Background(), describeOpt)
fmt.Printf("Snapshot ID: %d\n", resp.GetSnapshotInfo().GetId())
fmt.Printf("Collection: %s\n", resp.GetSnapshotInfo().GetCollectionName())
// node.js
# restful
锁定/解锁快照数据
在恢复过程中,您可以固定快照以暂时保护其底层数据免受垃圾回收的影响,并取消固定以释放数据。
您还可以为固定操作设置生存时间 (TTL),以便在该时间到期时释放被固定的数据。
pin_id = client.pin_snapshot_data(
snapshot_name="backup_20240101",
collection_name="my_collection",
ttl_seconds=3600,
)
client.unpin_snapshot_data(
pin_id=pin_id
)
// java
pinID, err := client.PinSnapshotData(
context.Background(),
milvusclient.NewPinSnapshotDataOption("backup_20240101", "my_collection").WithTTL(3600),
)
if err != nil {
log.Fatal(err)
}
defer func() {
_ = client.UnpinSnapshotData(
context.Background(),
milvusclient.NewUnpinSnapshotDataOption(pinID),
)
}()
// Do work with pinned snapshot data.
// node.js
# restful
恢复快照
您可以将快照恢复到新的 Collection 中。此操作为异步操作,并将返回一个作业 ID 用于跟踪恢复进度。
恢复过程采用分段复制机制而非数据导入,这种方式更为高效,因为它
- 它会直接从快照存储中复制分段文件(二进制日志、增量日志、索引文件)
- 保留字段 ID 和索引 ID,以确保与现有数据文件的兼容性
- 避免了数据重写和索引重建,从而显著缩短了恢复时间,并且
- 与传统的备份和恢复方法相比,性能提升10到100倍
要还原快照,请按以下步骤操作:
# Restore snapshot to new collection
job_id = client.restore_snapshot(
snapshot_name="backup_20240101",
collection_name="restored_collection",
)
// java
restoreOpt := milvusclient.NewRestoreSnapshotOption(
"backup_20240101",
"restored_collection"
)
jobID, err := client.RestoreSnapshot(context.Background(), restoreOpt)
if err != nil {
log.Fatal(err)
}
// node.js
# restful
有关监控恢复作业进度的详细信息,请参阅“获取恢复状态”。
删除快照
如果不再需要某个快照,您可以将其删除。建议您定期删除旧快照以节省存储空间。
client.drop_snapshot(
snapshot_name="backup_20240101"
)
// java
dropOpt := milvusclient.NewDropSnapshotOption("backup_20240101")
err := client.DropSnapshot(context.Background(), dropOpt)
// node.js
# restful
列出恢复任务
您可以使用此 API 获取目标 Collection 中已创建的快照列表。
# List all restore jobs
jobs = client.list_restore_snapshot_jobs()
for job in jobs:
print(f"Job {job.job_id}: {job.snapshot_name} -> Collection {job.collection_id}")
print(f" State: {job.state}, Progress: {job.progress}%")
# List restore jobs for a specific collection
jobs = client.list_restore_snapshot_jobs(collection_name="my_collection")
// java
// List all restore jobs
listOpt := milvusclient.NewListRestoreSnapshotJobsOption()
jobs, err := client.ListRestoreSnapshotJobs(context.Background(), listOpt)
if err != nil {
log.Fatal(err)
}
for _, job := range jobs {
fmt.Printf("Job %d: %s -> Collection %d\n",
job.GetJobId(), job.GetSnapshotName(), job.GetCollectionId())
fmt.Printf(" State: %s, Progress: %d%%\n",
job.GetState(), job.GetProgress())
}
// List restore jobs for a specific collection
listOpt = milvusclient.NewListRestoreSnapshotJobsOption().
WithCollectionName("my_collection")
jobs, err = client.ListRestoreSnapshotJobs(context.Background(), listOpt)
// node.js
# restful
获取恢复状态
获得恢复任务 ID 后,您可以使用该 ID 查询恢复进度。
state = client.get_restore_snapshot_state(job_id=12345)
print(f"Job ID: {state.job_id}")
print(f"Snapshot Name: {state.snapshot_name}")
print(f"Collection ID: {state.collection_id}")
print(f"State: {state.state}")
print(f"Progress: {state.progress}%")
if state.state == "RestoreSnapshotFailed":
print(f"Failure Reason: {state.reason}")
print(f"Time Cost: {state.time_cost}ms")
// java
stateOpt := milvusclient.NewGetRestoreSnapshotStateOption(12345)
state, err := client.GetRestoreSnapshotState(context.Background(), stateOpt)
if err != nil {
log.Fatal(err)
}
fmt.Printf("Job ID: %d\n", state.GetJobId())
fmt.Printf("Snapshot Name: %s\n", state.GetSnapshotName())
fmt.Printf("Collection ID: %d\n", state.GetCollectionId())
fmt.Printf("State: %s\n", state.GetState())
fmt.Printf("Progress: %d%%\n", state.GetProgress())
if state.GetState() == milvuspb.RestoreSnapshotState_RestoreSnapshotFailed {
fmt.Printf("Failure Reason: %s\n", state.GetReason())
}
fmt.Printf("Time Cost: %dms\n", state.GetTimeCost())
// node.js
# restful