このスクリプトを数回実行しようとしましたが、ハングし続けます。 60,000枚の画像があり、約1000枚を通過して停止します。 topコマンドを実行していて、プロセスpngquantが消えたようです。どんな助けでも大歓迎です。
私が得た最後の出力は
Optimized PNG: ./12/thumbnail/112.png
Optimized PNG: ./12/thumbnail/photography.png
Optimized PNG: ./12/thumbnail/Christmas-01.png
Optimized PNG: ./12/thumbnail/OA1920.png
error: cannot open ./12/thumbnail/The for reading
Optimized PNG: ./12/thumbnail/The
error: cannot open Official for reading
Optimized PNG: Official
error: cannot open AndreasCY for reading
Optimized PNG: AndreasCY
そして、それは止まりました。スクリプトは次のようになります。
#!/bin/bash
cd /var/www/html/wp-content/uploads/2014/
for PNG in $(find . -name '*.png'); do
pngquant --ext .png --force 256 ${PNG}
echo "Optimized PNG: ${PNG}"
done
ルイの答えにはいくつかの良いアドバイスが含まれていますが、彼はあなたのコマンドの失敗の実際の原因を見逃しているようです。出力から、_./12/thumbnail/The Official AndreasCY ….png
_という名前のファイルがあることがわかります。
あなたが言う時
_for PNG in $(find . -name '*.png')
_
それは言うようなものです
pNGの場合./12/thumbnail/112.png ./12/thumbnail/photography.png ./12/thumbnail/Christmas-01.png\ ./ 12/thumbnail/OA1920.png ./12/thumbnail /公式AndreasCY…。png…
その結果、_./12/thumbnail/The
_、Official
、およびAndreasCY
は、別々のファイル名であるかのように扱われます。そうでないため、エラーが発生します。 $(…)
を使用してファイル名のリストを生成する場合は、十分に注意する必要があります。つまり、可能な限りそれを行わないようにしてください。 _find … -exec
_ははるかに優れたアプローチです。ただし、Ruiが指定したコマンドは機能しません。_-exec "Optimized PNG: "
_などのコマンドがないため、_"Optimized PNG: "
_は失敗します。
元の回答とRuiの回答の次の部分を保持することをお勧めします。
#!/ bin/sh cd/var/www/html/wp-content/uploads/2014 (最後に「/」は必要ありません。) 検索。 -name '* .png' -typef…
次に、次のいずれかで終了します。
-exec pngquant --ext .png --force 256 {} \; -exec echo "Optimized PNG:" {} \;
_-exec pngquant --ext .png --force 256 {} \; -printf "Optimized PNG: %p\n"
_-exec sh -c 'pngquant --ext .png --force 256 "$1"; echo "Optimized PNG: $1"' sh {} \;
_、または_-exec myscript {} \;
_
ここで、myscript
は
_#!/bin/sh
pngquant --ext .png --force 256 "$1"
echo "Optimized PNG: $1"
_
シェル変数(例:_"$PNG"
_および_"$1"
_)は、正当な理由がない限り、常に引用符で囲む必要があります。sure自分が何であるかを知っているやっています。対照的に、中括弧(_${PNG}
_など)は重要な場合がありますが、引用符ほど重要ではありません。また、一般的な原則として、bash機能に依存し、POSIX準拠のシェルでは機能しないスクリプトを明示的に記述していない限り、_#!/bin/sh
_を使用することをお勧めします。
スクリプトでは、find出力が実際のコマンドラインに展開されますが、サイズに制限があります。したがって、findによって入力された引数がサイズを超えると、残りは無視されます。
この記事は問題のあるものを扱っています: http://www.cyberciti.biz/faq/argument-list-too-long-error-solution/
Findコマンドも非常に強力なコマンドであり、コマンドを呼び出すオプションがあり、大きなファイルを処理するときにこれらの制限を回避する方法の1つです。
次のようにコマンドを実行できます。
find $DIR -name '*.png' -type f -exec command {} \;
{}は処理されるファイルであり、タイプfはファイルを処理することを定義し、$ DIRはコマンドが再帰的に機能するベースディレクトリです。
1つのラインライナーで必要なことを行う簡単な方法の1つは次のとおりです。
find /var/www/html/wp-content/uploads/2014 . -name '*.png' -type f \
-exec pngquant --ext .png --force 256 {} \; -exec echo "Optimized PNG: " {} \;
(\は、投稿を明確にするためにコマンドを2行に分割するために使用されます)
Findをexecオプションと一緒に使用する方法についての記事もここに残しておきます。
http://linuxaria.com/howto/linux-Shell-how-to-use-the-exec-option-in-find-with-examples
グロブ構文は、forループに直接入れることができます。 find
はまったく必要ありません。また、forループで直接グロブを使用する場合は、シェルが自動的に処理するため、Wordの分割について心配する必要はありません。
コマンドに表示されるときにシェル変数を引用することもお勧めします。引用しないと、置換後に単語が分割されます。
最後に、printf
ではなくecho
を選択します。これは、ファイル名に特定の文字が含まれている場合に正しく動作し、さまざまな実装間で移植性が高くなるためです。
for PNG in *.png; do
pngquant --ext .png --force 256 "$PNG"
printf "Optimized PNG: %s\n" "$PNG"
done
Zshおよびbash 関連するオプションセットを使用 では、次のような再帰的なグロブを実行できます。
for PNG in **/*.png; do
pngquant --ext .png --force 256 "$PNG"
printf "Optimized PNG: %s\n" "$PNG"
done
これにより、find
コマンドと同様に、検索がサブディレクトリに下降します。ただし、これはPOSIX標準ではないため、すべてのPOSIXに似たシステムで移植可能に機能するものが必要な場合は、他のいずれかの回答を使用する必要があります。