
この単純なBASHスクリプトは、PHPプロジェクトからmsgstrを収集します。
#!/bin/sh
TARGET=/path/to/project
LPATH=locale/cy_GB/LC_MESSAGES
POFILE=messages.po
mkdir -p $LPATH
touch $TARGET/$LPATH/$POFILE
cd $TARGET
find . -name '*.php' -print | xargs xgettext -j --from-code=UTF-8 -o $TARGET/$LPATH/$POFILE
2つの質問があります。
-printが見つかったファイルをリストしないのはなぜですか?すべての文書に記載されていますか?
findがファイルを処理する順序を指定する方法はありますか?同等のPHPスクリプトを実行すると、lsにリストされている順序でファイルを処理してディレクトリに移動します。しかし、 find はファイルが明確な順序になっておらず、ディレクトリがあちこちに散らばっていて、それ自体で作業を行うようです。
答え1
find
Bashとは何の関係もなく、Linuxを実行している場合は、システムでGNU findutilsが提供する別のユーティリティです。
-print
ファイルはリストされますが、必要ありません。これがデフォルトです。おそらくあなたがそれを「見ない」理由は、その出力が標準入力を介してxargs
取られるからです。それは決してあなたの端末に到達しません。両方で動作させるには、またはtee
同様のものを使用する必要があります(信頼できないファイル名を取得した場合は、次のことを行う必要があります)。いつもuse -print0
, これは移植できない拡張なので、ここには含まれません):
find . -name '*.php' |
tee >(xargs xgettext -j --from-code=UTF-8 -o "$TARGET/$LPATH/$POFILE")
find
ファイルはソートされていない順序で印刷されます。整理したい場合は、sort
まず実行する必要があります。
答え2
find . -name '*.php' -print
ファイル名のリストを印刷します。ここがxargs
入力を受けているところです。
ファイル名にスペースやその他の特殊文字が含まれているときにパニックにならないようにするには-print0
、xargs -0
find . -name '*.php' -print0 | xargs -0 xgettext -j --from-code=UTF-8 -o "$TARGET/$LPATH/$POFILE"
または、次の-exec
タスクを代わりに使用してください。
find . -name '*.php' -exec xgettext -j --from-code=UTF-8 -o "$TARGET/$LPATH/$POFILE" {} +
ファイルが多すぎる場合は、xgettext
各ファイルのバッチに対して一度に複数回実行されます。これはまたはxargs
を使用しても同じです-exec
。これを回避するにはbashを使用しているため、組み込みの再帰ディレクトリナビゲーション機能を代わりに使用してくださいfind
。
shopt -s globstar
xgettext -j --from-code=UTF-8 -o "$TARGET/$LPATH/$POFILE" **/*.php
これにより、関連付けられたファイル名がコマンドラインの長さ制限を超えると、自動的に切り捨てられたファイルの代わりにエラーが表示されます。 Bashでは、**/
ディレクトリだけでなくディレクトリへのシンボリックリンクも巡回されます。問題が発生した場合は、bashの代わりにkshまたはzshを使用するか、別の方法を使用してください。
を使用している場合にfind
出力ファイルが自動的に上書きされないようにするには、標準出力に書き込み、コマンド全体をファイルにfind
リダイレクトします。
find . -name '*.php' -exec xgettext -j --from-code=UTF-8 {} + >"$TARGET/$LPATH/$POFILE"
find
ファイルが見つかった順序でリストされ、ソートは実行されません。他のファイルの前または後に名前やディレクトリに基づいて並べ替えないでください。 (ディレクトリはファイルです。ディレクトリ内には別のサブディレクトリやその他のファイルのリストはありません。)
find
常にディレクトリ自体の直後にディレクトリの内容をリストします。 options を使用すると-depth
状況が反転します。まず、ディレクトリの内容、次にディレクトリ自体です。
答え3
ターゲットディレクトリにサブフォルダがない場合、およびで*
終わるすべてのファイルを展開してみることができます。これを行うと必要はありません。.php
xgettext
find
xargs
for i in ./*.php; do
xgettext -j --from-code=UTF-8 -o $TARGET/$LPATH/$POFILE $i
done
を使用して再帰検索を実行する必要がある場合は、find
コマンドを含むサブシェルの出力を繰り返すことができますfind
。
for i in $(find . -name '*.php'); do
xgettext -j --from-code=UTF-8 -o $TARGET/$LPATH/$POFILE $i
done