使用 rsync 从 Linux 服务器备份 Windows 文件夹

使用 rsync 从 Linux 服务器备份 Windows 文件夹

Windows 现在有一个内置的 openssh 服务器,因此我们也可以使用 rsync 来备份 Windows PC 上的文件夹。问题是,如果我尝试

rsync --relative -aqz --numeric-ids --delete-after -e 'ssh' 's2@black:C:\Users\s2\.gnupg' black

从 Linux 服务器,我最终得到如下所示的本地目录结构:

black/
└── C:\Users\s2\.gnupg
    ├── crls.d
    │   └── DIR.txt
    ├── gpg-agent.conf
  [...]
    └── trustdb.gpg

因此根文件夹是名为的单个文件夹C:\Users\s2\.gnupg,而不是像这样的三个文件夹Users/s2/.gnupg。有没有办法将 Windows 路径转换为 ​​Linux 路径,以便备份有意义?

答案1

你可以随后将目录合并到

./script black

该脚本使用 GNU find-print0循环遍历 C: 并创建所有目录、mv所有文件并删除旧目录。只有问题目录会丢失像 xattrs 这样的元数据(但可以用几行代码轻松克服chown chcon等)

脚本

find "$@" -depth -type d -iname 'C:\\*' -print0 | while IFS= read -r -d '' dir || [ "$dir" ]
  do
    path="${dir%/*}"
    dir="${dir##*/}"
    mkdir -p "$path/${dir//\\//}"
    find "$path/$dir" -maxdepth 1 -not -type d -exec mv {} "$path/${dir//\\//}" +
    rmdir "$path/$dir"
done

编辑:

对于混合路径,您需要更多代码进行合并。您可以改用cp -l通过mv硬链接移动文件。元数据被保留

脚本

#!/bin/bash
# or sh supporting read -d

# random name
tmp="${0##*/}_$(date '+%s')_tmp~"

# search for windows drive letters 'C:\' in 'black'
find -L "$@" -type d -iname '[A-Z]:\\*' -print0 | sort -z | while IFS= read -r -d '' dir || [ "$dir" ]
  do
    printf "'%s' -> " "$dir"

    # resolve symlinks
    dir="$(realpath "$dir")"

    path="${dir%/*}"
    dir="${dir##*/}"
    win="${dir%\\*}"
    nix="${dir##*\\}"

    printf "'%s'\n" "${dir//\\//}"

    # create linux directories
    mkdir -p "$path/${dir//\\//}"

    # move childs windows -> linux preserving metadata (via hard-links)
    find "$path/$dir" -mindepth 1 -maxdepth 1 \( -exec cp -abflPx {} "$path/${dir//\\//}" \; -a -exec rm -r {} \; \)

    # rename parent windows -> linux
    mkdir -p "$path/$tmp"
    mv "$path/$dir" "$path/$tmp/$nix"

    # copy parent metadata
    rsync -aAX "$path/$tmp/$nix" "$path/${win//\\//}"

    # delete windows directories
    rmdir "$path/$tmp/$nix" "$path/$tmp"
done

不幸的是,它的速度要慢得多,因为find -exec \;一些不必要的sortecho

答案2

您需要/mnt/c/先挂载
或使用 cwrsync

相关内容