8

環境:

を使用して記述されたコードがいくつかありますpexpect。その仕事は、コマンドの「ライブ」出力を提供することです。つまり、コマンドが完了するまで待ってからその出力と対話するのではなく、コマンドが何らかの出力を生成するとき、またはその直後に何かを出力します。

私がしているのは、サービスの開始と停止だけです。これを行うにはspawn、プロセスを実行し、次のように各行を出力します。

def watch(process):
    output = ""
    while True:
        try:
            line = process.read_nonblocking(timeout = -1)
            print(line, end ="")
            output += line
        except pexpect.EOF:
            break
    del process
    return output

while True:
    print("IN 1")
    process = pexpect.spawn("service",["zend-server", "stop"], timeout = None)
    watch(process)
    print("OUT 1")

    print("IN 2")
    process = pexpect.spawn("service",["zend-server", "start"], timeout = None)
    watch(process)
    print("OUT 2")

このコードは、サービスをループするだけです。開始と停止を繰り返し、開始/停止の出力を出力します。出力をうまく印刷します。しかし、最終的には「OUT 2」の直前でハングします。出力を表示して、service呼び出しが実行を停止するのを確認できます。ただし、このwatch関数は EOF を発生させずに終了します。

これは、すべてのサービスで発生するわけではありません。一部のサービスは無期限にループします。zend-serverただし、他のいくつかの無関係なコマンドとともに、同じように断続的に失敗します。

「最終的にハングする」とは、サービスを数回 (実行ごとに可変) 開始/停止し、ハングすることを意味します。それは通常、最初の呼び出しでは決してありませんが、少なくとも 2 番目の呼び出しでは常に 4-6 の後にガムアップします (したがって、delステートメント; 私はそれを安全にプレイすると考えました)。

Python 2.6.6、CentOS (64) 6.3、Pexpect 2.3-6、FWIW

質問:

pexpect特定のコマンドでハングアップするのはなぜですか? この問題を解決するにはどうすればよいですか? タイムアウトを使用することは、実行可能な解決策ではありません。これらのコマンドの一部は、実際には任意の時間実行できるからです。service zend-server stopそれほど長くかからず、終了するのを観察できるので、例として選んだのはこれだけです。

私が試したこと:

watchメソッドを を使用する次のメソッドに置き換えてみましたexpect('\n')が、結果は同じです。さまざまな数の再起動が行われ、最終的にハングします。

とともに編集pexpect.EOFされた配列に追加し、戻り値を処理してループから抜け出すこともできますが、それでも同じ場所でハングします。expect\n

def watch2(process):
    output = ""
    done = False
    while True:
        try:
            if not process.isalive():
                line = process.readline()
                done = True
            else:
                process.expect(['\n'])
                line = process.before
             print(line)
            output += line
            if done:
                raise pexpect.EOF(0)
        except pexpect.EOF:
            break
    del process
    return output
4

1 に答える 1

3

pexpect がさらにデータを待機しているバッファリングの問題のようです。に渡すことでバッファリングを無効にすることができmaxread=1ますpexpect.spawn()

于 2012-11-19T23:09:34.953 に答える