数据备份
Doris 支持将当前数据以文件的形式备份到 HDFS 和对象存储。之后可以通过恢复命令,从远端存储系统中将数据恢复到任意 Doris 集群。通过这个功能,Doris 可以支持将数据定期地进行快照备份。也可以通过这个功能,在不同集群间进行数据迁移,集群间无损迁移可以使用 CCR (../ccr.md)。
该功能需要 Doris 版本 0.8.2+
原理说明
备份操作是将指定表或分区的数据,直接以 Doris 存储的文件的形式,上传到远端仓库中进行存储。当用户提交 Backup 请求后,系统内部会做如下操作:
-
快照及快照上传
快照阶段会对指定的表或分区数据文件进行快照。之后,备份都是对快照进行操作。在快照之后,对表进行的更改、导入等操作都不再影响备份的结果。快照只是对当前数据文件产生一个硬链,耗时很少。快照完成后,会开始对这些快照文件进行逐一上传。快照上传由各个 Backend 并发完成。
-
元数据准备及上传
数据文件快照上传完成后,Frontend 会首先将对应元数据写成本地文件,然后通过 broker 将本地元数据文件上传到远端仓库。完成最终备份作业
-
动态分区表说明
如果该表是动态分区表,备份之后会自动禁用动态分区属性,在做恢复的时候需要手动将该表的动态分区属性启用,命令如下:
ALTER TABLE tbl1 SET ("dynamic_partition.enable"="true")
-
备份和恢复操作都不会保留表的
colocate_with
属性。
开始备份
-
创建一个 HDFS 的远程仓库 example_repo(S3 存储请参考 2):
CREATE REPOSITORY `example_repo`
WITH HDFS
ON LOCATION "hdfs://hadoop-name-node:54310/path/to/repo/"
PROPERTIES
(
"fs.defaultFS"="hdfs://hdfs_host:port",
"hadoop.username" = "hadoop"
); -
创建一个 S3 的远程仓库 : s3_repo(HDFS 存储请参考 1)
CREATE REPOSITORY `s3_repo`
WITH S3
ON LOCATION "s3://bucket_name/test"
PROPERTIES
(
"AWS_ENDPOINT" = "http://xxxx.xxxx.com",
"AWS_ACCESS_KEY" = "xxxx",
"AWS_SECRET_KEY"="xxx",
"AWS_REGION" = "xxx"
);注意:
ON LOCATION 这里后面跟的是 Bucket Name
-
全量备份 example_db 下的表 example_tbl 到仓库 example_repo 中:
BACKUP SNAPSHOT example_db.snapshot_label1
TO example_repo
ON (example_tbl)
PROPERTIES ("type" = "full"); -
全量备份 example_db 下,表 example_tbl 的 p1, p2 分区,以及表 example_tbl2 到仓库 example_repo 中:
BACKUP SNAPSHOT example_db.snapshot_label2
TO example_repo
ON
(
example_tbl PARTITION (p1,p2),
example_tbl2
); -
查看最近 backup 作业的执行情况:
mysql> show BACKUP\G;
*************************** 1. row ***************************
JobId: 17891847
SnapshotName: snapshot_label1
DbName: example_db
State: FINISHED
BackupObjs: [default_cluster:example_db.example_tbl]
CreateTime: 2022-04-08 15:52:29
SnapshotFinishedTime: 2022-04-08 15:52:32
UploadFinishedTime: 2022-04-08 15:52:38
FinishedTime: 2022-04-08 15:52:44
UnfinishedTasks:
Progress:
TaskErrMsg:
Status: [OK]
Timeout: 86400
1 row in set (0.01 sec) -
查看远端仓库中已存在的备份
mysql> SHOW SNAPSHOT ON example_repo WHERE SNAPSHOT = "snapshot_label1";
+-----------------+---------------------+--------+
| Snapshot | Timestamp | Status |
+-----------------+---------------------+--------+
| snapshot_label1 | 2022-04-08-15-52-29 | OK |
+-----------------+---------------------+--------+
1 row in set (0.15 sec)
BACKUP 的更多用法可参考 这里。
最佳实践
备份
当前我们支持最小分区(Partition)粒度的全量备份(增量备份有可能在未来版本支持)。如果需要对数据进行定期备份,首先需要在建表时,合理的规划表的分区及分桶,比如按时间进行分区。然后在之后的运行过程中,按照分区粒度进行定期的数据备份。
数据迁移
用户可以先将数据备份到远端仓库,再通过远端仓库将数据恢复到另一个集群,完成数据迁移。因为数据备份是通过快照的形式完成的,所以,在备份作业的快照阶段之后的新的导入数据,是不会备份的。因此,在快照完成后,到恢复作业完成这期间,在原集群上导入的数据,都需要在新集群上同样导入一遍。
建议在迁移完成后,对新旧两个集群并行导入一段时间。完成数据和业务正确性校验后,再将业务迁移到新的集群。
说明
- 备份恢复相关的操作目前只允许拥有 ADMIN 权限的用户执行。
- 一个 Database 内,只允许有一个正在执行的备份或恢复作业。
- 备份和恢复都支持最小分区(Partition)级别的操作,当表的数据量很大时,建议按分区分别执行,以降低失败重试的代价。
- 因为备份恢复操作,操作的都是实际的数据文件。所以当一个表的分片过多,或者一个分片有过多的小版本时,可能即使总数据量很小,依然需要备份或恢复很长时间。用户可以通过
SHOW PARTITIONS FROM table_name;
和SHOW TABLETS FROM table_name;
来查看各个分区的分片数量,以及各个分片的文件版本数量,来预估作业执行时间。文件数量对作业执行的时间影响非常大,所以建议在建表时,合理规划分区分桶,以避免过多的分片。 - 当通过
SHOW BACKUP
或者SHOW RESTORE
命令查看作业状态时。有可能会在TaskErrMsg
一列中看到错误信息。但只要State
列不为CANCELLED
,则说明作业依然在继续。这些 Task 有可能会重试成功。当然,有些 Task 错误,也会直接导致作业失败。 常见的TaskErrMsg
错误如下: Q1:备份到 HDFS,状态显示 UPLOADING,TaskErrMsg 错误信息:[13333: Close broker writer failed, broker:TNetworkAddress(hostname=10.10.0.0,port=8000) msg:errors while close file output stream, cause by: DataStreamer Exception: ] 这个一般是网络通信问题,查看broker日志,看某个ip 或者端口不通,如果是云服务,则需要查看是否访问了内网,如果是,则可以在borker/conf文件夹下添加hdfs-site.xml,还需在hdfs-site.xml配置文件下添加dfs.client.use.datanode.hostname=true,并在broker节点上配置HADOOP集群的主机名映射。 - 如果恢复作业是一次覆盖操作(指定恢复数据到已经存在的表或分区中),那么从恢复作业的
COMMIT
阶段开始,当前集群上被覆盖的数据有可能不能再被还原。此时如果恢复作业失败或被取消,有可能造成之前的数据已损坏且无法访问。这种情况下,只能通过再次执行恢复操作,并等待作业完成。因此,我们建议,如无必要,尽量不要使用覆盖的方式恢复数据,除非确认当前数据已不再使用。
相关命令
和备份恢复功能相关的命令如下。以下命令,都可以通过 mysql-client 连接 Doris 后,使用 help cmd;
的方式查看详细帮助。