Python subprocess communicate kills my process

故事扮演 提交于 2019-12-11 03:00:47

问题


Why does communicate kill my process? I want an interactive process but communicate does something so that I cannot take raw_input any more in my process.

from sys import stdin 
from threading import Thread
from time import sleep

if __name__ == '__main__':
    print("Still Running\n")
    x = raw_input()    
    i = 0
    while ('n' not in x ) :
        print("Still Running " + str(i) + " \r\n")
        x = raw_input()
        i += 1

    print("quit")



print(aSubProc.theProcess.communicate('y'))
print(aSubProc.theProcess.communicate('y'))

exception!

self.stdin.write(input)
ValueError: I/O operation on closed file

回答1:


communicate and wait methods of Popen objects, close the PIPE after the process returns. If you want stay in communication with the process try something like this:

import subprocess
proc = subprocess.Popen("some_process", stdout=subprocess.PIPE, stdin=subprocess.PIPE)
proc.stdin.write("input")
proc.stdout.readline()



回答2:


Why does communicate kill my process?

From the docs for Popen.communicate(input=None, timeout=None):

Interact with process: Send data to stdin. Read data from stdout and
stderr, until end-of-file is reached. Wait for process to terminate. emphasize mine

You may call .communicate() only once. It means that you should provide all input at once:

#!/usr/bin/env python
import os
import sys
from subprocess import Popen, PIPE

p = Popen([sys.executable, 'child.py'], stdin=PIPE, stdout=PIPE)
print p.communicate(os.linesep.join('yyn'))[0]

Output

Still Running

Still Running 0 

Still Running 1 

quit

Notice the doubled newlines: one from '\r\n' and another from print statement itself in your script for the child process.

Output shows that the child process received three input lines successfully ('y', 'y', and 'n').

Here's a similar code using subprocess.check_output()'s input parameter from Python3.4:

#!/usr/bin/env python3.4
import os
import sys
from subprocess import check_output

output = check_output(['python2', 'child.py'], universal_newlines=True,
                      input='\n'.join('yyn'))
print(output, end='')

It produces the same output.


If you want to provide a different input depending on responses from the child processes then use pexpect module or its analogs to avoid issues mentioned in Why not just use a pipe (popen())?



来源:https://stackoverflow.com/questions/22045090/python-subprocess-communicate-kills-my-process

易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!