2009-02-19 12 views
33

サブプロセスを使用してpythonスクリプト内からスーパーユーザーとしてプロセスを実行しようとしています。 ipythonシェルでPythonスクリプトからスーパーユーザーとしてコマンドを実行しています

proc = subprocess.Popen('sudo apach2ctl restart', 
         shell=True, stdin=subprocess.PIPE, 
         stdout=subprocess.PIPE, 
         stderr=subprocess.PIPE) 

のようなものが正常に動作しますが、できるだけ早く私は、スクリプトにそれを固執するように私は取得を開始:sudo: apach2ctl: command not found

これは、sudoがubuntuの環境を処理する方法によるものだと思います。 (私も無駄にsudo -E apche2ctl restartsudo env path=$PATH apache2ctl restartを試してみた)

だから私の質問は、私は必要なときに、スーパーユーザーのパスワードをユーザに促し、スーパーユーザーとしてapache2ctl restartを実行したい場合は、どのように私はやって行けば、基本的にはこの?私はスクリプトにパスワードを格納するつもりはない。

編集:

私は両方の文字列などのコマンドに渡してみましたし、リストにトークン化しました。 Pythonインタプリタでは、文字列を使ってパスワードのプロンプトが正しく表示されます(私の元の問題のようにPythonスクリプトでは動作しません)。リストはsudoのヘルプ画面を表示します。

編集2:だから

は私が集まるpopenのはただの文字列など、いくつかのコマンドを使用して動作しますが、シェルは= Trueの場合、それはsudoを得るために「=真の殻」なし

proc = subprocess.Popen(['sudo','/usr/sbin/apache2ctl','restart']) 

を取るときということです働く

ありがとうございます!

+2

パスワードを要求せずにこのコマンドを実行できるようにsudoを設定する方法はありますか? –

+0

あなたは何をしているのかに応じて['proc.wait()'](https://docs.python.org/2/library/subprocess.html#subprocess.Popen.wait)を使いたいかもしれません。子プロセスの実行が終了するまで、「待機」は進まない。 – craymichael

答えて

14

apache2ctlの完全なパスを指定してください。

+0

私はあなたがそれにヒットしたと思います。インタプリタからスクリプトを実行すると、それを実行している対話シェルから$ PATHが継承されます。しかし、スクリプトとして実行すると、$ PATHは非対話型シェルから継承され、同じではない可能性があります。 popen()を使用するときは常に完全なパスを指定することをお勧めします。 –

+0

えええええええええええええええええええええええええええええええええええええええええええええええええええええええええええええええええええ、ところで、 "apch2ctl"のスペルが間違っています。 ;) – ojrac

3

あなたはこのようにpopenのを使用する必要があります。

cmd = ['sudo', 'apache2ctl', 'restart'] 
proc = subprocess.Popen(cmd, shell=True, stdin=subprocess.PIPE, stdout=subprocess.PIPE, stderr=subprocess.PIPE) 

それはリストを期待しています。

+7

http://docs.python.org/library/subprocess.htmlを参照してください。shell = Trueの場合、文字列とシーケンスargsに違いがあります。 – jfs

+0

ああ、私はそれのように前にそれを使用したことはありません。 –

+1

リストを渡すときにshell = Trueを設定しないでください。 –

21

試してみてください。

subprocess.call(['sudo', 'apach2ctl', 'restart'])

サブプロセスは、あなたを促し、およびパスワードで読むことができるようにするために、実際の標準入力/アウト/ ERRにアクセスする必要があります。それらをパイプとして設定する場合は、自分でそのパイプにパスワードを入力する必要があります。

あなたがそれらを定義しない場合、それはsys.stdoutのグラブ、等...

7

もう一つの方法は、ユーザーパスワードレスsudo userようにすることです。

タイプのコマンドラインで次のよう

sudo visudo 

そして、以下を追加し、あなたと<username>を置き換える:

<username> ALL=(ALL) NOPASSWD: ALL 

これは、ユーザーが求めることなく、sudoコマンドを実行できるようになりますパスワード(前記ユーザによって起動されたアプリケーションを含む。これはセキュリティリスクの可能性があります

関連する問題