closed
logo logo
关于我们

技术分享

技术分享 基于 rsync 和 ln 实现“写时复制”的快照备份功能

基于 rsync 和 ln 实现“写时复制”的快照备份功能

2018-06-12

一、基本原理

这里“写时复制”加了一个引号,因为这是专门针对使用rsync备份时的写时复制效果,而不是事实上的写时复制(copy-on-write),其达到的目的如下:

使用 rsync 备份数据后,立即创建一份快照:

  1. 该快照的数据状态不会因为之后的同步行为被改变,而是始终保持快照创建时的状态。

  2. 该快照不会占用额外的存储空间。

  3. 再次使用 rsync 备份,原文件发生变化,或出现新的文件,则只有发生变化的文件和新出现的文件才会占用新的存储空间。

实现这一功能,主要依赖于一个事实:使用 rsync 进行备份时,针对内容发生变化的文件,新备份的文件与原文件对比,inode 将被改变。

我们知道,Linux 文件系统中以 inode 作为文件索引,inode 编号相同的多个文件称为硬链接,指向的是硬盘中同一块数据,占用同一份存储空间。多个硬链接之间地位等同,没有主从之分,只要有一份硬链接拷贝没有删除,这个文件所占用的存储空间就不会释放出来。我们使用 rsync 进行备份时,如果文件内容没有发生变化,则rsync跳过该文件不作处理,如果文件内容发生变化,rsync 则删除原文件并重新复制文件为同一文件名,此时虽然文件相同,但 inode 将发生变化,表示备份前后的文件是文件名相同的不同文件。

基于这个事实,我们可以在备份完成后,对每一个文件创建硬连接,并以相同的目录结构保存,这里把这一行为称为创建快照,快照创建完成后,之后有不同的文件备份过来,或有原文件被删除,都在备份目录发生,不会影响快照本身。

二、基本实验

基本步骤:

  1. 模拟真实业务场景,新建一个数据目录,并向数据目录写入实验数据

  2. 创建备份目录,并使用使用 rsync 进行备份

  3. 手动创建快照,对比快照与备份数据的 inode ,查看总占用空间

  4. 更改业务数据

  5. 再次使用 rsync 进行备份,对比备份前后的 快照数据

具体操作如下

# 创建目录并写入数据
mkdir data
dd if=/dev/urandom of=data/bigfile bs=1M count=20
echo the first line in text file. > data/file.txt
echo the another file. > data/file_another.txt

# 备份
mkdir backup
rsync -a --delete data/ backup/

# 手动创建快照
mkdir snapshot-1
ls backup | xargs -i{} ln backup/{} snapshot-1/{}

# 查看结果
du -sh; tree --inodes -sh

结果如下(具体 inode 编号每次实验可能会有不同):

基于 rsync 和 ln 实现“写时复制”的快照备份功能

# 更改业务数据
echo the second line. >> data/file.txt
rm data/file_another.txt

# 同步
rsync -a --delete data/ backup/ 

# 查看结果
du -sh; tree --inodes -sh; diff data/file.txt snapshot-1/file.txt

结果如下:

基于 rsync 和 ln 实现“写时复制”的快照备份功能

三、通用实现

为使这一备份方式便于使用,将创建备份和删除旧备份写成 shell 函数,需要用的脚本 source 后就能使用:

# 用法: mk_snapshot backup_dir snapshot_dir
function mk_snapshot(){
        # mk_snapshot src_dir des_dir
        if [ ! -d "$1" ]; then
                echo "$1" is not a directory! >&2
                return 1
        fi

        WorkDir="$(pwd)"
        Target=$(realpath $2)

        cd "$1"
        find . -type d -exec mkdir -p "${Target}/{}" \;
        find . -type f -exec ln "{}" "${Target}/{}" \;
        # 由于文件夹的mtime不可靠,创建一个.snapshot文件用于后期辅助find判断快照创建时间
        touch "${Target}/.snapshot"
        cd "$WorkDir"
}

# 用法:删除snapshots文件夹下n天前的快照
# clean_snapshot snapshots n
function clean_snapshot(){
        # clean_snapshot snapshot_dir/snapshot_for days_ago
		if [ ! -d "$1" ]; then
			echo "Error: \"$1\" is no a directory!" > &2
			return 1
		fi

        MountPoint=$(df "$1" | tail -1 | awk '{print $NF}')
        TempDir=$(mktemp -dp "$MountPoint")

        find "$1" -maxdepth 2 -mindepth 2 -mtime +$2 -type f -empty \
             -name ".snapshot" -exec dirname "{}" \; | xargs -i{} mv {} $TempDir
        rm -rf "$TempDir"
}

四、优点与不足

这一备份方案的优点:

  1. 可以防止损坏的业务数据污染备份数据,导致备份数据不可用

  2. 快照创建速度快

  3. 对重复的数据不额外占用存储空间

限制与不足:

  1. 由于使用的是硬连接,快照与备份数据必须处于同一分区

  2. 仅适用于类unix系统(windows现在也可以通过mklink创建硬连接,有兴趣的小伙伴可以研究一下,欢迎交流)

 

云祺备份软件,云祺容灾备份系统,虚拟机备份,数据库备份,文件备份,实时备份,勒索软件,美国,图书馆
  • 标签:
  • 容灾备份

您可能感兴趣的新闻 换一批

现在下载,可享30天免费试用

立即下载

请添加好友为您提供支持
jia7jia_7

请拨打电话
为您提供支持

400-9955-698