python script (main.py)
]からプロセスを開始したい、具体的には以下のコマンドを実行したい
`Nohup python ./myfile.py &`
このファイルmyfile.py
は、メインpythonスクリプトが終了した後でも必要です。
さらに、新しいプロセスのpid
を取得したいです。
os.spawnl*
、os.exec*
subprocess.Popen
メソッドを試しましたが、main.pyスクリプトが終了すると、すべてがmyfile.py
を終了します。
何かが足りないかもしれません。
更新:os.startfile
をxdg-open
と一緒に使用できますか?それは正しいアプローチですか?
例
a = subprocess.Popen([sys.executable, "Nohup /usr/bin/python25 /long_process.py &"],\
stdout=subprocess.PIPE, stderr=subprocess.PIPE, stdin=subprocess.PIPE)
print a.pid
ps aux | grep long_process
をチェックすると、実行中のプロセスが表示されませんでした。
long_process.pyこれはいくつかのテキストを印刷し続けます:終了しません。
ここで何か間違っていますか?
実行時間の長いプロセスを開き、パイプを保持します。だからあなたはそれに話をすることを期待しています。 yorランチャースクリプトが終了すると、会話できなくなります。 長時間実行プロセスはSIGPIPE
を受け取り、終了します。
以下はちょうど私のために働いた(Linux、Python 2.7)。
実行時間の長い実行可能ファイルを作成します。
$ echo "sleep 100" > ~/tmp/sleeper.sh
Python REPL:
$ python
>>>
import subprocess
import os
p = subprocess.Popen(['/bin/sh', os.path.expanduser('~/tmp/sleeper.sh')])
# look ma, no pipes!
print p.pid
# prints 29893
REPLを終了して、実行中のプロセスを確認します。
>>> ^D
$ ps ax | grep sleeper
29893 pts/0 S 0:00 /bin/sh .../tmp/sleeper.sh
29917 pts/0 S+ 0:00 grep --color=auto sleeper
最初に開始されたプロセスと通信し、それをそのままにしてさらに実行する場合は、いくつかのオプションがあります。
SIGPIPE
を処理します。その上で死なないでください。ランチャープロセスが終了した後、stdinなしでライブ。os.fork()
を使用できます。
import os
pid=os.fork()
if pid==0: # new process
os.system("Nohup python ./myfile.py &")
exit()
# parent process continues
実行中のプロセスを確認できませんでした。
子python
プロセスがすぐに終了するため、実行中のプロセスは表示されません。 ser4815162342がコメントで述べている のように、Popen
引数は正しくありません。
完全に独立したプロセスを起動するには、 python-daemon
package を使用するか、systemd/supervisord/etcを使用できます。
#!/usr/bin/python25
import daemon
from long_process import main
with daemon.DaemonContext():
main()
あなたの場合は十分かもしれませんが、正しいPopen
引数で子を開始するには:
with open(os.devnull, 'r+b', 0) as DEVNULL:
p = Popen(['/usr/bin/python25', '/path/to/long_process.py'],
stdin=DEVNULL, stdout=DEVNULL, stderr=STDOUT, close_fds=True)
time.sleep(1) # give it a second to launch
if p.poll(): # the process already finished and it has nonzero exit code
sys.exit(p.returncode)
子プロセスがpython2.5
を必要としない場合は、代わりにsys.executable
を使用できます(親と同じPythonバージョンを使用)。
注:コードは、子プロセスの終了を待たずに親のDEVNULL
を閉じます(子には影響しません)。