2

bash スクリプトをプラグインとして実行する必要がある Python フレームワークがあります。multiprocessing モジュールを使用して、multiprocessing.JoinableQueue からプラグインの詳細を取得し、subprocess.Popen() を使用してプラグインを実行するワーカー プロセスを作成しています。

シェル スクリプトによって生成された最終出力が切り捨てられ、最終的に実行全体が無駄になることが確認されています。

そこで、シェル スクリプト プロセスを生成するサブプロセス メカニズムを維持するワーカーを Python スレッドに移行しようとしました。そして切り捨てはもはや起こっていませんでした。しかし、スレッドは非常に遅く (GIL が原因)、シグナルとイベントへの応答も不確定です (おそらく GIL リリースのタイミングが原因です)。

マルチプロセッシングモジュールがstdoutのバッファリングを行うというスタックオーバーフローの他の質問を含む多くの場所で読みました。これが問題であることはわかっています。しかし、シェルスクリプトがファイルにエコーしなければならないデータに対して sys.stdout.flush を python から与えることができないため、適切な解決策を見つけることができません。

また、いくつかのサンプルで os.fsync を試しましたが、切り捨ては発生していません。ここでも、シェル スクリプトによって作成されたファイルの名前がフレームワークに認識されないため、この目的のために直接使用することはできません。フレームワークによって最終的なアーカイブのみが取り戻されます。

私の質問は、マルチプロセッシング モジュールから生成されたプロセスでこのバッファリングを防ぐ方法はありますか? ここで、Python インタープリターの -u オプションが役立ちますか? または、/usr/lib64/python2.6/multiprocessing の python ライブラリを変更すると、この問題は解決しますか?

4

1 に答える 1

1

スクリプト内で ssh 経由で送信されたコマンドは、出力で切り捨てられていたものであることがわかりました。

このために、問題を解決した ssh の -n フラグを使用しました。もう切り捨てはありません。しかし、これは Python マルチプロセッシング環境でのみ発生する奇妙な問題であり、そのようなモデルを独自の目的で使用しようとする人は真剣に検討する必要があります。

-n オプションのマニュアルページには次のように書かれています

/dev/null から stdin をリダイレクトします (実際には、stdin からの読み取りを防ぎます)。これは、ssh がバックグラウンドで実行されている場合に使用する必要があります。一般的なトリックは、これを使用してリモート マシンで X11 プログラムを実行することです。たとえば、ssh -n shadows.cs.hut.fi emacs & は、shadows.cs.hut.fi で emacs を開始し、X11 接続は暗号化されたチャネルを介して自動的に転送されます。ssh プログラムはバックグラウンドで実行されます。(これは、ssh がパスワードまたはパスフレーズを要求する必要がある場合には機能しません。-f オプションも参照してください。)

于 2012-06-18T10:36:05.133 に答える