subprocess.Popen与CLI提示交互
Posted
tags:
篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了subprocess.Popen与CLI提示交互相关的知识,希望对你有一定的参考价值。
我正在尝试使用subprocess.Popen
编写和读取CLI程序。
因此,每次向CLI发出命令时,它都会打印一些内容,而这正是我想要读取的内容。我将尝试用一个具体的例子来解释我想做什么,这样每个人都可以尝试。
因此,我将使用my real program
代替使用ipython
问题:
p = subprocess.Popen(['ipython'],stdin=subprocess.PIPE, stdout=subprocess.PIPE, stderr=subprocess.PIPE)
stdout, stderr = p.communicate(input="5+5")
如果你使用Popen.communicate(input=command)
,你可以在stdout
上获得ipython
将在终端中打印的所有文本,如果我直接从shell
执行它。
我想做的事:
而不是使用communicate
。我希望能够发送单个命令并读取立即输出。例如,我想做:
p.stdin.write("5+5")
out1 = p.stdout.read()
p.stdin.write("5*10")
out2 = p.stdout.read()
所以out1
应该是5,而out2
应该是50。
问题:
在关闭stdout
之前,你不能阅读stdin
。
你是怎样做的 ?我不能使用read(n)
或readline()
,因为在我的实际应用中我不知道输出的长度。
调用communicate()
块直到进程退出,这不是你想要的。你需要阅读p.stdout
并写信给p.stdin
。
或者,您可能会发现pexpect
模块很有用。
通过一些小的修改,我能够从this question工作的方法。
使用Python3:
>>> from subprocess import Popen, PIPE
>>>
>>> fw = open("tmpout", "wb")
>>> fr = open("tmpout", "r")
>>> p = Popen("ipython", stdin=PIPE, stdout=fw, stderr=fw, bufsize=1, universal_newlines=True)
>>> header = fr.read()
>>> p.stdin.write("100*50
")
7
>>> fr.read()
'
In [1]: Out[1]:
5000
'
>>> p.stdin.write("2/3.
")
5
>>> fr.read()
'
In [2]: Out[2]:
0.6667
'
如您所见,它以交互方式工作。
一个技巧是,在Py3下,bufsize=1
仅在universal_newlines=True
时才进行I / O线缓冲。
以上是关于subprocess.Popen与CLI提示交互的主要内容,如果未能解决你的问题,请参考以下文章
当从 Django 内部调用时,Subprocess.Popen 与交互式程序一起挂起