プログラマーのメモ書き

伊勢在住のプログラマーが気になることを気ままにメモったブログです

WSL2 経由での cron + rsnapshot によるバックアップ

こちらの記事で書いたように、手元の環境では Windows のファイル履歴が今一つうまく動いてくれませんでした。

ということで、代替案として、 wsl2 があるので、 rsync (結果的に rsnapshot を使いました)を使って作業フォルダのバックアップを取ればいいやと考えたので、それを実現する方法を試したのをメモっておきます。

cron の自動実行

何はともあれ rsync ( rsnapshot ) を使うには、 wsl で cron が動いてくれないと話になりません。で、wsl2 の cron を調べてみると、残念ながら自動起動してくれないようです。

mor@DESKTOP-DE7IL4F:/etc$ sudo service cron status
 * cron is not running
mor@DESKTOP-DE7IL4F:/etc$

手作業で起動すれば動きます。

mor@DESKTOP-DE7IL4F:/$ sudo service cron start
 * Starting periodic command scheduler cron                                                                      [ OK ]
mor@DESKTOP-DE7IL4F:/$
mor@DESKTOP-DE7IL4F:/$ sudo service cron status
 * cron is running
mor@DESKTOP-DE7IL4F:/$

でも、これだと、PCを起動するたびに、手作業で動かさないといけないので、いまいちです。

同じことで困っている人はたくさんいるようで、ググるとすぐに解決策が見つかりました。

バッチファイル+スタートアップによる起動

こちらの

WSL上cronをwindows起動時に自動実行する - Qiita

を参考に試してみました。

cron を起動するためのバッチファイルを作成します。例えば、こんな感じ。

wsl -u root -- service cron start

これを以下の場所に保存します(Windowsキー + R で shell:startup を指定すると一発で開きます)。

C:\Users\ユーザー名\AppData\Roaming\Microsoft\Windows\Start Menu\Programs\Startup

一度、Windows を再起動して、wslを開いて確認すると

mor@DESKTOP-DE7IL4F:/$ sudo service cron status
 * cron is running
mor@DESKTOP-DE7IL4F:/$

おぉ、起動していますね。

ただ、これだと、バッチファイル実行時に黒い画面が一瞬表示されるのがいまいちです。ということで、最終的には、下記記事を参考にして、黒い画面が表示されないように VBScript のファイルにしました。

バッチファイルを実行する時に黒いコマンドプロンプト画面を表示しない方法 | パソコンが便利で楽になるものを紹介しています

スタートアップフォルダに保存するファイルは拡張子を .vbs にしておきます。ここでは start_cron.vbs としました。中身はこんな感じです。

Set ws = CreateObject("Wscript.Shell")
ws.run "cmd /c wsl -u root -- service cron start", vbhide

こちらをさきほどのスタートアップフォルダに保存し、 Windows を再起動すると黒い画面が表示されずに、 cron が起動されることになります。

参考:sudoers を用いる方法

ちなみに、wsl -u root を使わずに、 sudoers を指定してパスワードを回避する方法もあるようです。

WSL2 で cron を有効にして OpenSSH server を走らせる - Qiita

参考:タスクスケジューラによる起動

今回は試していませんが、同じことをタスクスケジューラで行うこともできます。

WSLでCronを自動的に起動する方法 Windows 10 そして、11

こちらの方法だと、 Windows にログオンする前に起動させることもできますね。好きな方法で起動させればよいかと思います。

rsnapshot によるバックアップ

ここからが本題です。wsl2 で rsync によるバックアップを行います。と思ったのですが、 rsync だと保存対象と同じ1セットを更新する形になります(『同期』がとられます)。

バックアップ先のディスクは NAS の iSCSI を想定しており、この部分は NAS側で毎日スナップショットを取っているので、これでも問題ないといえば問題ないですが、どうせなら世代バックアップをやりたいと思います。

Linux だと、 rsnapshot というツールを使えば、 rsync をはじめとする標準的なツールを組み合わせて、世代間バックアップを実現してくれるそうです。

なので、下記の記事などを参考にして、 wsl 上でも rsnapshot によるバックアップができないか試していきます。

インストール

毎度なじみですね。

mor@DESKTOP-DE7IL4F:~$ sudo apt install rsnapshot

ちなみに、バージョンは

  • rsnapshot 1.4.3-2
  • rsync 3.1.3-8

でした。

設定

/etc/rsnapshot.conf が設定ファイルになるので、これを編集していきます。編集の前に、元のファイルを残しておきます。

mor@DESKTOP-DE7IL4F:/etc$ sudo cp -p rsnapshot.conf rsnapshot.conf.org

configファイルの設定内容は、基本的には上記のリンク先を参照してもらえればよいと思います。デフォルトから変更した点は以下になります。

mor@DESKTOP-DE7IL4F:/etc$ diff rsnapshot.conf.org rsnapshot.conf
23c23
< snapshot_root /var/cache/rsnapshot/
---
> snapshot_root /mnt/e/backup/
63c63
< #cmd_du               /usr/bin/du
---
> cmd_du                /usr/bin/du
67c67
< #cmd_rsnapshot_diff   /usr/bin/rsnapshot-diff
---
> cmd_rsnapshot_diff    /usr/bin/rsnapshot-diff
93,95c93,95
< retain        alpha   6
< retain        beta    7
< retain        gamma   4
---
> #retain       alpha   6
> #retain       beta    7
> #retain       gamma   4
96a97,99
> retain        hourly  4
> retain        daily   5
> retain        weekly  14
121c124
< #logfile      /var/log/rsnapshot.log
---
> logfile       /var/log/rsnapshot.log
227,229c230,235
< backup        /home/          localhost/
< backup        /etc/           localhost/
< backup        /usr/local/     localhost/
---
> #backup       /home/          localhost/
> #backup       /etc/           localhost/
> #backup       /usr/local/     localhost/
> backup        /home/mor/              localhost/
> backup        /mnt/c/Users/mor/bin/   localhost/
> backup        /mnt/d/                 localhost/
mor@DESKTOP-DE7IL4F:/etc$

retain で残す世代数を指定しますが、名称が alpha, beta, ・・・というのが分かりにくいので、 hourly, daily, weekly に変えています。 また、世代数は、詳しくは自動化で後述するように、今回のバックアップ対象のPCが常時稼働ではないので、少なめの世代数にしています。

あと、バックアップ対象として

backup        /home/mor/              localhost/
backup        /mnt/c/Users/mor/bin/   localhost/
backup        /mnt/d/                 localhost/

のようにしています。これは、

  • WSL のホームディレクトリ
  • C:\Users\ユーザー名\bin
  • D:\

を指定しており、 WSL 側のホームディレクトリと Windows 側のユーザーデータとデータドライブ( C の一部と D 全体)をまとめてバックアップをとるようにしました。

設定ファイルを記述できたら、構文があっているかテストします。

mor@DESKTOP-DE7IL4F:/etc$ rsnapshot configtest
Syntax OK
mor@DESKTOP-DE7IL4F:/etc$

問題なければテスト実行してみます。

mor@DESKTOP-DE7IL4F:/etc$ rsnapshot -t hourly
echo 1920 > /var/run/rsnapshot.pid
mkdir -m 0700 -p /mnt/e/backup/
mkdir -m 0755 -p /mnt/e/backup/hourly.0/
/usr/bin/rsync -a --delete --numeric-ids --relative --delete-excluded \
    /home/mor/ /mnt/e/backup/hourly.0/localhost/
mkdir -m 0755 -p /mnt/e/backup/hourly.0/
/usr/bin/rsync -a --delete --numeric-ids --relative --delete-excluded \
    /mnt/c/Users/mor/bin/ /mnt/e/backup/hourly.0/localhost/
mkdir -m 0755 -p /mnt/e/backup/hourly.0/
/usr/bin/rsync -a --delete --numeric-ids --relative --delete-excluded \
    /mnt/d/ /mnt/e/backup/hourly.0/localhost/
touch /mnt/e/backup/hourly.0/
mor@DESKTOP-DE7IL4F:/etc$

大丈夫そうですね。

ちなみに、 daily をテストすると

mor@DESKTOP-DE7IL4F:/etc$ rsnapshot -t daily
echo 1956 > /var/run/rsnapshot.pid
mkdir -m 0700 -p /mnt/e/backup/
/mnt/e/backup/hourly.3 not present (yet), nothing to copy
mor@DESKTOP-DE7IL4F:/etc$

となります。hourly.3 (4世代前のバックアップ)がないので、これも妥当ですね。

自動化

rsnapshot の自動化は cron を使うようです。rsnapshot をインストールすると /etc/cron.d に rsnapshot ファイルが作成されますので、これをもとに変更していきます。

さて、前述したように、作業 PC のデータフォルダのバックアップを取ることが目的のためなのですが、作業PCという性格のため、仕事終わりには電源を落としていきます。なので、常にPCが動作しているとは限りません。その点を考慮して、設定内容を検討しました。

rsnapshot の説明を読むと、 rsnapshot.conf の BACKUP LEVELS / INTERVALS セクションは保持する世代を表しており、 cron.d/rsnapshot の内容はrsnapshot を実行するタイミングを表しているようです。

サンプルなどを見ると、通常、この2つは対応しており、デフォルトだと

retain alpha   6
retain beta    7
retain gamma   4
retain delta   3

に対して、

0 */4         * * *           root    /usr/bin/rsnapshot alpha
30 3          * * *           root    /usr/bin/rsnapshot beta
0  3          * * 1           root    /usr/bin/rsnapshot gamma
30 2          1 * *           root    /usr/bin/rsnapshot delta

となっています。

内容を確認すると、

  • alpha は 4 時間おきにcronを実行しして、24 / 4 = 6、で 6 回実行し、6 世代分保持
  • beta は daily に該当し、毎日決められた時間( 3 時半)に実行して、一週間分の 7 世代を保持
  • weekly に相当する gamma は月曜日の 3 時に実行し、 4 世代( 4 週間分)
  • delta が毎月 1 日の 2 時半に実行し、 3 世代分( 3 か月分)を保持

となっています。つまり、 1 日当たりのバックアップ回数、 1 週間当たりの日ごとのバックアップ数、 1 月あたりの週ごとのバックアップ数と保持する世代数が対応する形です。

しかし、上述したように今回の対象は Windows の作業用 PC であるため電源をつけっぱなしではないので、作業データを保持するために、

rsnapshot の世代数 < cron で指定する rsnapshot の実行回数

となるようにしてみました。

こうすると、PCが起動されていれば各世代は順次上書きされていき、hourly のもっとも古いものが daily に付け替えられて、その時点で最も古い世代を残していくことになります。

微妙な点としては、PCの稼働時間によって、 hourly のもっとも古いものが必ずその日のもっとも古いデータである保証がない点です。例えば、

  • 一日の作業時間が長い場合は、その日の最初のバックアップがその日のバックアップとして取られるのではなく、その日のどこか作業途中のタイミングのバックアップになります
  • 一方、一日の作業時間が短い場合は、同じ日のバックアップでデータが更新されずに、前日より前のデータが、その日のバックアップとして取られるケースも出てきます

という感じです。とはいえ、過去の作業データがある程度の時間間隔で残っているほうが重要なので、この点は目をつぶることにします。

また、cronの実行タイミングは仕事しているときなら、昼頃は電源を入れている場合が多いだろうからとして、日中を指定しました。

ということで設定内容を下記のようにしました。

4 */2           * * *           root    /usr/bin/rsnapshot hourly
32 11           * * *           root    /usr/bin/rsnapshot daily
2  11           * * 1           root    /usr/bin/rsnapshot weekly

バックアップの実施とトラブルシューティング

これで、設定ファイルがOKと思い、実際に動かしてみます。すると、予想外にいろいろと問題がでてきてしまいました。

トラブル1

テストではなく、実際に動かしてみると、下記のwarningがでてきました。

[2022-01-07T22:07:42] WARNING: Some files and/or directories in /mnt/d/ only transferred partially during rsync operation

調べてみると、類似の現象があるようです。

[rsnapshot-discuss] rsync file partially transferred

ファイルを開いたままの場合などにエラーが出ることがあるようです。

ただ、この時は特にファイルを開いていたものもなかったので、解決策はちょっと見えません。

とりあえず、

  • ログレベルを 3 -> 5 に変更
  • /mnt/d/ としてドライブ全体を対象にすると、 Windows が作ったシステムフォルダ( $RECYCLE.BIN や System Volume Information など)もバックアップ対象になってたので、必要なデータフォルダのみを明示的に指定するように変更(システムディレクトリを対象外にする)

としてみました。具体的には、 rsnapshot.conf の backup の部分を

backup  /home/mor/              localhost/
backup  /mnt/c/Users/mor/bin/   localhost/
#backup /mnt/d/                 localhost/
backup  /mnt/d/avd/                     localhost/
backup  /mnt/d/work/                    localhost/
backup  /mnt/d/VirtualBox VMs/          localhost/

のように、 D ドライブ以下の必要なデータフォルダを指定する形としました。

この状態で、もう一度、rsnapshotを試してみると、無事エラーなくコピー処理が完了しました。どうも、システムフォルダ関係が何かしていたようです。

トラブル2

上記でバックアップ作成後、2回目の hourly 実行時に下記のようなエラーが出てきました。

[2022-01-11T14:04:01] /bin/cp -al /mnt/e/backup/hourly.0 /mnt/e/backup/hourly.1
[2022-01-11T15:37:35] /usr/bin/rsnapshot hourly: ERROR: /bin/cp -al /mnt/e/backup/hourly.0 /mnt/e/backup/hourly.1 failed (result 256, exit status 1).
[2022-01-11T15:37:35] /usr/bin/rsnapshot hourly: ERROR: Error! cp_al("/mnt/e/backup/hourly.0/", "/mnt/e/backup/hourly.1/")
[2022-01-11T15:37:35] rm -f /var/run/rsnapshot.pid

これについては、ググるといろいろと出てくるのですが、コピー先のディスク容量も inode も十分あるようだし、解決先がよくわからないです。

なので、仕方なく順番にディレクトリごとに比較してみて、何か手掛かりはないか探ってみます。

mor@DESKTOP-DE7IL4F:/mnt/e/backup$ diff -r -q ./hourly.0/localhost/home/ ./hourly.1/localhost/home/
./hourly.0/localhost/home/mor/work/cs50/week4/pset4/filter/less/filter のみに存在: images
./hourly.0/localhost/home/mor/work/cs50/week4/pset4/filter/more/filter のみに存在: images
./hourly.0/localhost/home/mor/work/cs50/week5/pset5/speller のみに存在: dictionaries
./hourly.0/localhost/home/mor/work/cs50/week5/pset5/speller のみに存在: keys
./hourly.0/localhost/home/mor/work/cs50/week5/pset5/speller のみに存在: texts
./hourly.0/localhost/home/mor/work/cs50/week6/pset6/dna/dna のみに存在: databases
./hourly.0/localhost/home/mor/work/cs50/week6/pset6/dna/dna のみに存在: sequences
mor@DESKTOP-DE7IL4F:/mnt/e/backup$
mor@DESKTOP-DE7IL4F:/mnt/e/backup$ diff -r -q ./hourly.0/localhost/mnt/c/ ./hourly.1/localhost/mnt/c/

ん?一部のファイルがコピーされていないのが見つかりました。

見てみると、

mor@DESKTOP-DE7IL4F:/etc$ cd /mnt/e/backup/hourly.0/localhost/home/mor/work/cs50/week4/pset4/filter/less/filter
mor@DESKTOP-DE7IL4F:/mnt/e/backup/hourly.0/localhost/home/mor/work/cs50/week4/pset4/filter/less/filter$ ls -l
合計 2884
-rwxrwxrwx 2 mor mor    330 107 22:00 Makefile
-rwxrwxrwx 2 mor mor   1755  929  2019 bmp.h
-rwxrwxrwx 2 mor mor  55424 107 22:09 filter
-rwxrwxrwx 2 mor mor   3493  929  2019 filter.c
-rwxrwxrwx 2 mor mor   2736 107 22:09 helpers.c
-rwxrwxrwx 2 mor mor    394  929  2019 helpers.h
lrwxrwxrwx 1 mor mor     21 107 16:43 images -> ../filter.org/images/
-rwxrwxrwx 2 mor mor 720054 107 22:09 out_blur.bmp
-rwxrwxrwx 2 mor mor 720054 107 22:01 out_gray.bmp
-rwxrwxrwx 2 mor mor 720054 107 22:02 out_reflect.bmp
-rwxrwxrwx 2 mor mor 720054 107 22:01 out_sepia.bmp
mor@DESKTOP-DE7IL4F:/mnt/e/backup/hourly.0/localhost/home/mor/work/cs50/week4/pset4/filter/less/filter$

cs50.jp の問題をいろいろと試した際、画像ファイルを入れたフォルダへのシンボリックリンクを張ってて、そのシンボリックリンクのコピーで失敗してるっぽいです。

一度、 cp -al をコマンドラインから試してみます。

mor@DESKTOP-DE7IL4F:/mnt/e/backup/hourly.0/localhost/home/mor/work/cs50/week4/pset4/filter/less/filter$ cp -al images /mnt/e/backup/hourly.1/localhost/home/mor/work/cs50/week4/pset4/filter/less/filter/
cp: '/mnt/e/backup/hourly.1/localhost/home/mor/work/cs50/week4/pset4/filter/less/filter/images' から 'images' へのハードリンクを作成できません: ディレクトリです
mor@DESKTOP-DE7IL4F:/mnt/e/backup/hourly.0/localhost/home/mor/work/cs50/week4/pset4/filter/less/filter$

エラーになりました。これが怪しいですね。

早速、調べてみました。 cp -al はハードリンクを生成するので、この場合はシンボリックリンク自体のハードリンクを生成しようとしてるようです。たぶん、 -a オプションがあると、 --no-dereference が有効になるようで、これがあるとシンボリックリンクはたどられないため、シンボリックリンク自体のハードリンクを生成しているんじゃないかなと推測されます。

だけど、NTFS の場合フォルダに対するハードリンクはできないようで、そのためにエラーになっているっぽいです。

これらをキーワードにして調べると、似たようなものが、 wsl の issue としても挙げられていました。

On drvfs 'cp -al' sometimes fails to hard link symlink-to-dir. 'linkat' returns EISDIR · Issue #6171 · microsoft/WSL · GitHub

となると、これに対する対応策は当面なさそうです。

さきほどのフォルダは大して重要でもないので、バックアップ対象から除外して、シンボリックリンクを含まないデータフォルダのみを対象にして実行するようにします。実際の指定方法は下記の通りとしました。

rsnapshot.conf の変更

バックアップ対象にシンボリックリンクを含まないようにするために、シンボリックリンクを含む一部のフォルダをバックアップ対象から除外してやればいいかと思います。

rsnapshot.conf の exclude を指定すると、その値が rsync に渡されて、除外対象になるようです。ただ、 exclude に書くと、すべての backup 対象で exclude オプションが有効になるようです。今回の場合は、問題のあるのは wsl のホームディレクトリ以下のフォルダなので、wsl のホームディレクトリのバックアップ時にのみ除外の条件を付加したいと思います。

rsnapshot.conf の書き方を調べると、backup の指定ごとに、 rsync 用のオプションを追加指定することができるようです。具体的には backup の指定の際に、 4 つ目のパラメータとして +rsync_long_args を書けばよいようです。そして、これに複数の exclude オプションを渡せばOKです。なお、複数の exclude を +rsync_long_args で指定する場合はスペース区切りで書くそうです。

これらを調整したものはこんな形になりました(デフォルトのものとの差分で示します)。

mor@DESKTOP-DE7IL4F:/etc$ diff rsnapshot.conf.org rsnapshot.conf
23c23
< snapshot_root /var/cache/rsnapshot/
---
> snapshot_root /mnt/e/backup/
63c63
< #cmd_du               /usr/bin/du
---
> cmd_du                /usr/bin/du
67c67
< #cmd_rsnapshot_diff   /usr/bin/rsnapshot-diff
---
> cmd_rsnapshot_diff    /usr/bin/rsnapshot-diff
93,95c93,95
< retain        alpha   6
< retain        beta    7
< retain        gamma   4
---
> #retain       alpha   6
> #retain       beta    7
> #retain       gamma   4
96a97,99
> retain        hourly  4
> retain        daily   5
> retain        weekly  14
116c119
< loglevel      3
---
> loglevel      5
121c124
< #logfile      /var/log/rsnapshot.log
---
> logfile       /var/log/rsnapshot.log
227,229c230,237
< backup        /home/          localhost/
< backup        /etc/           localhost/
< backup        /usr/local/     localhost/
---
> #backup       /home/          localhost/
> #backup       /etc/           localhost/
> #backup       /usr/local/     localhost/
> backup        /home/mor/              localhost/      +rsync_long_args=--exclude=/home/mor/work/ --exclude=/home/mor/tmp/ --exclude=/home/mor/.cache/
> backup        /mnt/c/Users/mor/bin/   localhost/
> backup        /mnt/d/avd/                     localhost/
> backup        /mnt/d/work/                    localhost/
> backup        /mnt/d/VirtualBox VMs/          localhost/
mor@DESKTOP-DE7IL4F:/etc$

なお、 rsnapshot のデフォルトだと rsync 呼び出し時のオプションとして --relative がつきます(man rsnapshot の rsync_long_args あたりをご覧ください)。このため、 --exclude オプションは絶対パスで書かないと、うまく除外できませんでした(man rsync の ANCHORING INCLUDE/EXCLUDE PATTERNS あたりのサンプルを見ると参考になります)。

再実行

ここまで調整して、再度実行してみます。 コピーに時間がかかるのはありますが、とりあえず問題なく動くようです。

なお、コピーに時間がかかるので、 cron.d/rsnapshot の hourly は3時間おきに実行するように修正しました。

4 */3           * * *           root    /usr/bin/rsnapshot hourly
32 11           * * *           root    /usr/bin/rsnapshot daily
2  11           * * 1           root    /usr/bin/rsnapshot weekly

なお、ファイルをオープンしていたりすると、トラブル1で示したのと同じ warning が出力されるのですが、これは致し方ないですね。まあ当面はこのままで運用してみようと思います。

残件

上記設定で使い始めるといくつか気になるところが出てきました。備忘録として、ここにまとめておきます。

処理が遅い

上記でも書きましたが、ファイルのコピーが非常に遅いようにも思えます。

  • 一番最初だと、約 600GB をコピーするのに、 4 時間近くかかってました
  • 2 回目以降のコピー時だと、処理全体でおおよそ 2 時間近くかかっており、なかでもハードリンクを生成する cp -al が 1 時間半近くかかってます

こんなものだといえば、こんなものなのかもしれません。

ですが、ちょっと調べてみると、どうも、 wsl2 から Windows 側のファイルを扱う時は、 9p というプロトコルを使っており、これが遅いようです。

StackExchange を見ると、 etx4 に変更すると早くなるようなことが書いてあります。

rsnapshot very slow - Unix & Linux Stack Exchange

フォーマットを NTFS から ext4 に変更しても、 Windows から直接 ext4 をマウントして利用することもできるので、試してみるのもありだと思いますが、今回はいったん保留にしておいて、また時間ができたときに挑戦しようと思います。

warning 発生時に通知が欲しい

再実行のところに書きましたが、ファイルを開いていたりすると warning が発生することがあります。

通常は大きな問題は無いはずなのですが、念のためこのような時は、通知を受け取りたいと思います。

PC 停止時の挙動

バックアップ処理にそれなりに時間がかかっているので、PCの電源を落とす際に、バックアップが動作中ということがあり得ます。例えば、 hourly のバックアップ動作中に、PC をシャットダウンすると

[2022-01-13T21:08:04] /bin/cp -al /mnt/e/backup/hourly.0 /mnt/e/backup/hourly.1
[2022-01-13T22:16:24] /usr/bin/rsnapshot hourly: ERROR: /bin/cp -al /mnt/e/backup/hourly.0 /mnt/e/backup/hourly.1 failed (result 256, exit status 1).
[2022-01-13T22:16:24] /usr/bin/rsnapshot hourly: ERROR: Error! cp_al("/mnt/e/backup/hourly.0/", "/mnt/e/backup/hourly.1/")
[2022-01-13T22:16:24] rm -f /var/run/rsnapshot.pid

のようなログを出して、停止していました。

上記の場合、 hourly.0 を hourly.1 にコピー(ハードリンクでのコピー)している途中でエラーになっています。そうなると、 hourly.1 の中身は不完全になっているので、削除するか手動で再度バックアップを取るかしたほうがよさそうです。

もちろん、いきなりシャットダウンするのでなくても、シグナルを送って停止させた場合でも、 cp -al の途中であれば、コピー先が不完全になるのは同じです。

どう対応するか、ちょっと悩ましいですね。

とりあえずは、運用としてバックアップ実行中にシャットダウンしないようにするぐらいかなー。いい方法がないか改めて検討してみたいと思います。

参考

今回は試しませんでしたが、 lsyncd を使って、リアルタイムにバックアップを作っていくというのもありました。

lsyncd と rsnapshot でリアルタイム Time Machine 風バックアップを組もう - Qiita

ご参考までに。

参考2(2022/1/15 追記)

第24回伊勢IT交流会で、この記事の内容をLT で話しました。その際のスライドも載せておきます。

www.slideshare.net

まとめ

コピーに時間がかかるなど問題もありますが、一応これで Windows のファイル履歴を使わずに、データドライブのバックアップを取ることができるようになりました。しばらく使ってみて、問題があるようなら、また見直したいと思います。