2016-02-15 20 views
0

我期待CHOWN包含單詞的所有文件「喜」我怎麼會喬恩一切由grep的

我現在有

grep -r $1 $2 
if [ $? -eq 0 ]; then 
     echo "Found text" 
     echo $match 
     echo "start" 

與輸入被一些發現如./test.sh "hi" *

我能夠獲得所有包含hi的文件,但是當我嘗試chown時,我不知道應該如何處理管道我知道你可以將變量傳遞給下一個參數,例如;

grep -r $1 $2 | chown user1:root * 

,但似乎只是做了整個目錄,這不是我想要的。

任何有關閱讀或調查的內容的建議?

回答

6

您正在尋找命令xargs。它從標準輸入中讀取一系列字符串,並將它們轉換爲指定命令的參數。例如:

grep -r --files-with-matches $1 $2 | xargs chown user1:root 

更新:

提意見建議的硬化上面的命令,這的確是一個不錯的主意技術。由於$1$2是腳本的命令行參數,因此通常不能確定它們不包含會改變命令含義的空格或其他字符。因此,引用它們是一個好主意。此外,如果任何文件名稱包含空格 - 包括在包含的路徑段中的任何目錄名稱 - 則除非您提供幫助,否則xargs會誤解結果。這裏的管道的一個版本是這樣的事更穩健:

grep -rlZ "$1" "$2" | xargs -0 chown user1:root 

這個版本取決於GNU擴展到兩個grepxargs-Z選項會導致grep將輸出「行」與一個零值字符而不是換行符分隔開來,並且的參數告訴它相應地解釋傳入數據。該字符具有Unix文件名中不允許的獨特區別。

-l選項(小寫的L,不是數字1)到grep是GNU的--with-file-names選項的縮寫形式;簡短的表單將由任何符合POSIX的grep支持。我在這裏介紹它的完整性和簡潔性。

+0

如果名稱中有奇怪的字符,可能會付錢將** xargs **部分更改爲** xargs -i chown user1:root「{}」** – tink

+0

感謝您的幫助,它有效。你可以解釋爲什麼在使用xargs時你不必在user1:root之後指定目錄路徑嗎? – 21days

+1

@ 21days,'xargs'只是將文件名與「grep」輸出文件名完全相同,並將它們轉換爲參數。如果你的'grep'在一個子目錄中找到一個文件,那麼它報告的文件名將包含該文件路徑的必要前導元素。 'xargs'不會做任何神奇的事情;它只是使用給它的東西。 –