當輸出饋送到 tar 時,「find」中的濾波器將被忽略

當輸出饋送到 tar 時,「find」中的濾波器將被忽略

我有以下目錄結構:

test/
test/1/
test/foo2bar/
test/3/

我想壓縮目錄“test”,不包括子目錄中的所有內容(深度未預先定義),其中包括字串“1”或“2”。在 bash shell 中,我想使用尋找並將其輸出饋送到柏油。我先測試尋找

find test/ -not -path "*1*" -not -path "*2*"

輸出:

test/
test/3

偉大的。所以我把它與柏油

find test/ -not -path "*1*" -not -path "*2*" | tar -czvf test.tar.gz --files-from -

輸出:

test/
test/3/
test/1/
test/foo2bar/
test/3/

事實上,「test/1」和「test/foo2bar」都存在於檔案中。如果這些參數不應該出現在 find 輸出中,為什麼要傳遞給 tar?

答案1

為了擴展 @cuonglm 所說的內容,預設tar是遞歸操作的。如果你給它一個目錄名,它就會歸檔內容該目錄的。

您可以修改find命令以僅返回檔案名,而不返回目錄...

find test/ -type f -not -path "*1*" -not -path "*2*" |
tar -czvf test.tar.gz --files-from -

您可以使用該--no-recursion標誌來tar

find test/ -not -path "*1*" -not -path "*2*" | 
tar -czvf test.tar.gz --no-recursion --files-from - 

結果是:

test/
test/3/

--no-recursion標誌特定於 GNU tar。如果您正在使用其他功能,請查閱相應的手冊頁以查看是否有類似的功能可用。

請注意,您的find命令將排除文件包含12在路徑和目錄中。

答案2

使用 GNU tar,您還可以使用該--exclude選項根據名稱排除檔案。

$ tar --exclude "*1*" --exclude "*2*" -cvf foo.tar  test/
test/
test/3/

還有-Xor --exclude-fromwhich 需要一個檔案來讀取排除模式。


儘管 as find -not -path "*1*",這也會排除名稱包含1或的檔案2。僅跳過目錄其名稱與模式匹配,使用find -prunetar --no-recursion

$ touch test/3/blah.1
$ find test/ -type d \( -name "*1*" -o -name "*2*" \) -prune -o -print |
   tar cvf test.tar --files-from - --no-recursion
test/
test/3/
test/3/blah.1

(至少 GNU tar 和 FreeBSD tar 有--no-recursion

相關內容