2017-04-12 10 views
1

一般的な問題は、pexpectを使用してsudo権限が必要なスクリプトを呼び出すことですが、パスワードを入力する必要はありません。pexpectでexpect()とinteract()を同時に使用する

私の計画は、pdopectを使ってsudo権限でbashセッションを作成し、そこからスクリプトを呼び出すことです。基本的に私はいつもセッションをビジーにしたい、1つのスクリプトが停止したときに、別のスクリプトを開始したい。しかし、スクリプトが実行されている間、私はユーザーに制御権を与えたい。意味:

スクリプトはexpect( "root @")の後に呼び出される必要があります。セッションがアイドル状態になると、別のスクリプトが開始されます。スクリプトがinteract()を実行している間に、ユーザーが入力したい入力を制御できます。

私の考えは、この問題を解決するために別のスレッドを使用することでした。私はこのスクリプトを呼び出すとき

import pexpect 
import threading 

class BashInteractThread(threading.Thread): 
    def __init__(self, process): 
     threading.Thread.__init__(self) 
     self.pproc = process 

    def run(self): 
     self.pproc.interact() 


s = pexpect.spawn("/bin/bash", ['-i', '-c', "sudo bash"]) 

it = BashInteractThread(s) 
it.start() 

s.expect("[email protected]") 
s.sendline("cd ~") 
while(s.isalive()): 
    pass 


s.close() 

、それは私に任意の出力を与えるものではありませんが、プロセスが開始されているようだ:(概念実証のための)私のコードは次のようになります。それでも、CTRL-CやCTRL-Dでプロセスを強制終了することはできません。プロセスを個別に終了する必要があります。私が期待している動作は、パスワードの入力を求めるプロンプトが表示された後、自動的にディレクトリをホームディレクトリに変更する必要があります。 私はそれがうまくいかない理由を正確には知りませんが、出力はinteract()またはexpect()のどちらかにしか転送されません。

これを解決する方法を知っている人はいますか?前もって感謝します。

答えて

1

interact(output_filter=func)を利用することができます。私は単純な例を書いただけです(コーディングスタイルはありません)。それは、Bashシェルを生成し、ユーザーが対話するために繰り返しPythonを呼び出すことです。トラップを終了するには、魔法の言葉LET ME OUTを入力(または印刷)するだけです。

expect()interact()の後にはもう機能しませんので、手動でパターンマッチング作業を行う必要があります。

コード:

[STEP 101] # cat interact_with_filter.py 
import pexpect, re 

def output_filter(s): 
    global proc, bash_prompt, filter_buf, filter_buf_size, let_me_out 

    filter_buf += s 
    filter_buf = filter_buf[-filter_buf_size:] 

    if "LET ME OUT" in filter_buf: 
     let_me_out = True 

    if bash_prompt.search(filter_buf): 
     if let_me_out: 
      proc.sendline('exit') 
      proc.expect(pexpect.EOF) 
      proc.wait() 
     else: 
      proc.sendline('python') 

    return s 

filter_buf = '' 
filter_buf_size = 256 
let_me_out = False 
bash_prompt = re.compile('bash-[.0-9]+[$#] $') 

proc = pexpect.spawn('bash --noprofile --norc') 
proc.interact(output_filter=output_filter) 

print "BYE" 
[STEP 102] # 

のは、それを試してみましょう:

[STEP 102] # python interact_with_filter.py 
bash-4.4# python 
Python 2.7.9 (default, Jun 29 2016, 13:08:31) 
[GCC 4.9.2] on linux2 
Type "help", "copyright", "credits" or "license" for more information. 
>>> exit()   <---- user input 
bash-4.4# python 
Python 2.7.9 (default, Jun 29 2016, 13:08:31) 
[GCC 4.9.2] on linux2 
Type "help", "copyright", "credits" or "license" for more information. 
>>> exit()   <---- user input 
bash-4.4# python 
Python 2.7.9 (default, Jun 29 2016, 13:08:31) 
[GCC 4.9.2] on linux2 
Type "help", "copyright", "credits" or "license" for more information. 
>>> LET ME OUT  <---- user input 
    File "<stdin>", line 1 
    LET ME OUT 
     ^
SyntaxError: invalid syntax 
>>> exit()   <---- user input 
bash-4.4# BYE 
[STEP 103] # 
+0

Greadはアイデア!ありがとう、これは動作させる必要があります! – brandenb

関連する問題