Bash

使用 tar/gz 將目錄存檔到多個位置並省略額外的副本

  • January 10, 2022

我有一個簡單的備份腳本,它還將本地數據的 tar/gzip 存檔創建到外部 USB 設備,然後將該存檔複製到第二個 USB 設備。

例如:

usb1="/mnt/usbone"
usb2="/mnt/usbtwo"
source="/home/user"

tar cfz ${usb1}/source.tar.gz ${source}
cp -ar ${usb1}/source.tar.gz ${usb2}

這似乎可以優化為tar在兩個驅動器上創建副本,而不是創建一個存檔,然後再复制。生成的存檔相當小(<1GB)。我知道這不是一種安全的備份方法。


編輯:我已經快速測試了 Archemar 的解決方案並比較了這些方法。為了更好地衡量,我還使用rsync. time使用(not bash time, /usr/bin/time) 和我用來測試它的腳本查看結果。

源是用dd if=/dev/urandom bs=1M count=1024 of=/tmp/random.blob. 主機是從 microSD 卡執行的 Raspberry Pi 3B,安裝的目標是 USB 2.0 快閃記憶體驅動器(${a}${b})。

a.sh(焦油和 cp):

tar cfz ${a}/r1.tar.gz ${s}
cp -ar ${a}/r1.tar.gz ${b}/r1.tar.gz

b.sh(焦油和三通):

tar cfz - ${s} | tee ${a}/r2.tar.gz &gt; ${b}/r2.tar.gz

c.sh(tar 和 rsync):

tar cfz ${a}/r3.tar.gz ${s}
rsync -aW ${a}/r3.tar.gz ${b}/r3.tar.gz

結果:

# /usr/bin/time -v bash a.sh 
       Command being timed: "bash a.sh"
       User time (seconds): 218.71
       System time (seconds): 28.33
       Percent of CPU this job got: 68%
       Elapsed (wall clock) time (h:mm:ss or m:ss): 6:03.13
       Average shared text size (kbytes): 0
       Average unshared data size (kbytes): 0
       Average stack size (kbytes): 0
       Average total size (kbytes): 0
       Maximum resident set size (kbytes): 2480
       Average resident set size (kbytes): 0
       Major (requiring I/O) page faults: 41
       Minor (reclaiming a frame) page faults: 1250
       Voluntary context switches: 45519
       Involuntary context switches: 25576
       Swaps: 0
       File system inputs: 3668157
       File system outputs: 4197336
       Socket messages sent: 0
       Socket messages received: 0
       Signals delivered: 0
       Page size (bytes): 4096
       Exit status: 0

       
# /usr/bin/time -v bash b.sh 
       Command being timed: "bash b.sh"
       User time (seconds): 221.64
       System time (seconds): 28.62
       Percent of CPU this job got: 85%
       Elapsed (wall clock) time (h:mm:ss or m:ss): 4:53.98
       Average shared text size (kbytes): 0
       Average unshared data size (kbytes): 0
       Average stack size (kbytes): 0
       Average total size (kbytes): 0
       Maximum resident set size (kbytes): 2536
       Average resident set size (kbytes): 0
       Major (requiring I/O) page faults: 31
       Minor (reclaiming a frame) page faults: 1162
       Voluntary context switches: 68310
       Involuntary context switches: 35582
       Swaps: 0
       File system inputs: 2101321
       File system outputs: 4197832
       Socket messages sent: 0
       Socket messages received: 0
       Signals delivered: 0
       Page size (bytes): 4096
       Exit status: 0

       
# /usr/bin/time -v bash c.sh 
       Command being timed: "bash c.sh"
       User time (seconds): 235.24
       System time (seconds): 35.01
       Percent of CPU this job got: 74%
       Elapsed (wall clock) time (h:mm:ss or m:ss): 6:04.03
       Average shared text size (kbytes): 0
       Average unshared data size (kbytes): 0
       Average stack size (kbytes): 0
       Average total size (kbytes): 0
       Maximum resident set size (kbytes): 2652
       Average resident set size (kbytes): 0
       Major (requiring I/O) page faults: 40
       Minor (reclaiming a frame) page faults: 2310
       Voluntary context switches: 65402
       Involuntary context switches: 45179
       Swaps: 0
       File system inputs: 4200957
       File system outputs: 4197496
       Socket messages sent: 0
       Socket messages received: 0
       Signals delivered: 0
       Page size (bytes): 4096
       Exit status: 0

令我驚訝的是,結果並沒有那麼明顯。File system inputs: 2101321不過,使用 tar/tee 方法要低很多,我希望這對 SD 卡的使用壽命有好處。

你可以使用tee命令

usb1="/mnt/usbone"
usb2="/mnt/usbtwo"
source="/home/user"

tar -cz -f - "${source}" | tee "${usb2}/source.tar.gz" &gt; "${usb1}/source.tar.gz"

在哪裡

  • -f -告訴tar使用標準輸出作為備份文件。
  • tee "${usb2}/source.tar.gz" 將標準輸入複製到指定的文件和標準輸出。
  • &gt; "${usb1}/source.tar.gz"將標準輸出從重定向tee到文件。

引用自:https://unix.stackexchange.com/questions/685770