xargsにfindをパイピングすると、別の場所にある同じ名前のファイルを変更できません。

xargsにfindをパイピングすると、別の場所にある同じ名前のファイルを変更できません。

MacでGNUツールを使用する

何が起こっているのかわかりませんが、xargsのfind出力をパイピングすると、ディレクトリ構造内の別の場所に表示される同じ名前のファイルを扱う際にいくつかの問題があるようです。

私のディレクトリ:

dir
-- dirone
---- myfile.txt
---- otherfile.txt
-- dirtwo
---- myfile.txt

このコマンドを実行すると、権限拒否エラーが発生します。

find dir -name "myfile.txt" | xargs -0 -I FILE sh -c "ls FILE"

/ lsファイルに触れることもできません。 「otherfile.txt」を含む「otherfile.txt」にアクセスしても問題はありません。

find dir -name "otherfile.txt" | xargs -0 -I FILE sh -c "ls FILE"

どのような競争条件がありますか?結局、このファイルを変更したいのですが、sed -i変更することもできません。わかりません。フルファイルパスがxargsに渡されるので、フルパスが必要であり、同じ名前にすることは重要ではありません。

編集:良いです。権限エラーが発生する理由はまだ理解されていませんが、次のように動作するようです。

find dir -name "otherfile.txt" -type file -print0 | xargs -0 -I FILE sh -c "ls FILE"

ただ削除-0しても動作します。どのような方法が良いと安全かどうかはよくわかりません。

答え1

ディレクトリ設定を考慮すると、次のようになります。

$ find dir
dir
dir/dirtwo
dir/dirtwo/myfile.txt
dir/dirone
dir/dirone/myfile.txt
dir/dirone/otherfile.txt

あなたの(元の)コマンドを使用すると、元の問題を再現できます。

$ find dir -name "myfile.txt" | xargs -0 -I FILE sh -c "ls FILE"
dir/dirtwo/myfile.txt
sh: line 1: dir/dirone/myfile.txt: Permission denied
$

何が起こっているのかをよりよく理解するために、次のコマンドを変形してみましょう。

$ find dir -name "myfile.txt" | xargs -0 -I FILE echo -FILE-
-dir/dirtwo/myfile.txt
dir/dirone/myfile.txt
-

FILEは次に展開されます。一つトークン:dir/dirtwo/myfile.txt\ndir/dirone/myfile.txt\nなぜですか?これは、スイッチをxargs使用してタグをNULで区切るように指示し、-02つのファイル名の間にNUL文字がないためです。

したがって、元のコマンドに戻ると、... | xargs -0 -I FILE sh -c "ls FILE"次のようになります。

ls dir/dirtwo/myfile.txt
dir/dirone/myfile.txt

だから1つをリストし、2番目のものを実行しようとします。これが「許可されていません」というメッセージが表示される理由です。 2番目のファイルは実行可能ではありません。

見つかったようにオプションを追加すると成功-print0しました。findこのオプションを使用すると、findトークン間に NUL 文字が配置されます。これはxargs、このオプションを使用した-0ときに予想されるのと同じ文字です。繰り返しますが、-0オプションをオフにするだけで問題は解決します。なぜなら、とはxargs基本的に区切り文字としてスペースを使用するからです。findxargs

-print0オプションは、-0ファイル名にスペースを含めることができる場合に便利です(これにより、トークン区切り文字として扱われるスペースのデフォルトの動作が中断されます)。

関連情報