Rsync
只有當它包含與模式匹配的文件時,rsync 才能用於排除整個目錄和子內容?
我希望通過排除包含“.protect”文件的目錄的整個目錄和內容,在 linux 中使用 rsync 為我的 NAS 實現大約 20TB 的一些清理功能
我在子文件夾中生成非常大的記憶體,例如
記憶體/simulation_v001/reallybigfiles_*.bgeo
記憶體/simulation_v002/reallybigfiles_*.bgeo
記憶體/simulation_v003/reallybigfiles_*.bgeo
如果存在這樣的文件-cache/simulation_v002/.protect
然後我想建構一個 rsync 操作,將所有文件夾移動到臨時 /recycle 位置,不包括 cache/simulation_v002/ 及其所有內容。
我以前用 python 做過類似的事情,但我很好奇是否可以使用 rsync 或其他方法簡化操作。
感謝 cas 的提示,我能夠創建這個工作流來解決 bash 腳本的問題。它並不理想,因為如果它為更快的操作做了一個動作會更好(我希望 rsync 有這個能力)。該腳本將在目前文件夾下方搜尋帶有 find 的文件,創建排除列表,然後使用基本卷中的 rsync 將所有其他文件夾移動到垃圾文件夾,保留下面的完整路徑,以便可以非破壞性地恢復任何錯誤。
如果此解決方案在 git dev 分支中,則連結到目前狀態 - https://github.com/firehawkvfx/openfirehawk-houdini-tools/blob/dev/scripts/modules/trashcan.sh
#!/bin/bash # trash everything below the current path that does not have a .protect file in # the folder. it should normally only be run from the folder such as # 'job/seq/shot/cache' to trash all data below this path. # see opmenu and firehawk_submit.py for tools to add protect files based on # a top net tree for any given hip file. argument="$1" echo "" ARGS='' if [[ -z $argument ]] ; then echo "DRY RUN. To move files to trash, use argument -m after reviewing the exclude_list.txt and you are sure it lists everything you wish to protect from being moved to the trash." echo "" ARGS1='--remove-source-files' ARGS2='--dry-run' else case $argument in -m|--move) echo "MOVING FILES TO TRASH." echo "" ARGS1='--remove-source-files' ARGS2='' ;; *) raise_error "Unknown argument: ${argument}" return ;; esac fi current_dir=$(pwd) echo "current dir $current_dir" base_dir=$(pwd | cut -d/ -f1-2) echo "base_dir $base_dir" source=$(realpath --relative-to=$base_dir $current_dir)/ echo "source $source" target=trash/ echo "target $target" # ensure trash exists at base dir. mkdir -p $base_dir/$target echo "" echo "Build exclude_list.txt contents with directories containing .protect files" find . -name .protect -print0 | while IFS= read -r -d '' line; do path=$(realpath --relative-to=. "$line") dirname $path done > exclude_list.txt path_to_list=$(realpath --relative-to=. exclude_list.txt) echo $path_to_list >> exclude_list.txt cat exclude_list.txt cd $base_dir # run this command from the drive root, eg /prod. rsync -a $ARGS1 --prune-empty-dirs --inplace --relative --exclude-from="$current_dir/exclude_list.txt" --include='*' --include='*/' $source $target $ARGS2 -v cd $current_dir