如何处理需要交互式响应的可执行文件?(How to handle an executable req

2019-10-20 02:23发布

我有一个可执行文件,名为tsfoil2.exe,我想从我的Python环境中运行这个.exe文件。 我在Windows 7上运行的Python 2.7.3,与Spyder的2.1.11。

为了操作中的.exe,它需要一些输入,默认的硬盘驱动器(“I:\”),用于输入文件(“SC20610.inp”),为OUTPUTFILE(“测试”)的名称,名称。

我的一个同事建议我使用使用os.system,并与临时输入文件提供此,它包含了所有的参数。

f = open('temp', 'w') 
f.write('I:\ \n') 
f.write('test \n')
f.write('SC20610.inp\n')  
f.close() 

我再与参数通过以下方式中的.exe提供此文件:

os.system("tsfoil2.exe < temp")

这一切工作,但该计划需要一个“ENTER”键来关闭。 出于某种原因,该.exe文件反复询问到“按ENTER键退出”。 甚至,当我按在我的Spyder控制台回车键,该程序不会终止。

有没有办法给予“ENTER”键作为交互式输入到.EXE? 我试图使用SendKeys类,但因为程序不会终止,它没有达到的代码包含的SendKeys命令行。 我也试着将其包括在参数文件,但是这也不管用。

此外,我还发现,它可能是有益的切换到子进程的命令,因为它可能给我更多指挥权的执行,但我一直无法运行与输入文件的可执行文件。

是有可能提供必要的“确认”使用使用os.system,或我应该切换到子过程,并且如果是,如何可以构造类似于使用os.system(“tsfoil2.exe <临时”)的方法,我现在使用。

我已经试过这样:

import subprocess as sub
f = open('temp', 'w') 
f.write('I:\ \n') 
f.write('test \n')
f.write('SC20610.inp\n')  
f.close() 
proc=sub.Popen(["tsfoil2.exe","temp"], shell=True)

和这个

import subprocess as sub
p=sub.Popen('tsfoil2.exe')
p.communicate(input='I:' )

但是,该方案并没有给予提出答辩。

MWE:

import os
f = open('temp', 'w') 
f.write('I:\ \n') 
f.write('test \n')
f.write('SC20610.inp\n')  
f.close() 

os.system("tsfoil2.exe < temp")

两个程序可以经由找到http://www.dept.aoe.vt.edu/~mason/Mason_f/tsfoil2.exe ,输入文件可以通过找到http://www.dept.aoe.vt.edu /~mason/Mason_f/SC20610.inp 。

我希望一切都清楚了,你能帮助我。

Answer 1:

'Press the ENTER key to exit'意味着该方案需要一个换行符。

我看到在末尾没有空行temp文件。 此外,您可能意味着'I:\\\n'你需要使用- '\\'在Python字符串字面如果你想\输出。

现在的问题是什么tsfoil2.exe把换行符如b'\r\n'或只是b'\n'以及它希望接收它:从stdin( getchar()从控制台)或直接( getch()

假设该方案预计b'\r\n'从标准输入在Windows上:

import os
from subprocess import CalledProcessError, Popen, PIPE

cmd = "tsfoil2.exe"
input_data = os.linesep.join(['I:\\', 'test', 'SC20610.inp', os.linesep])
p = Popen(cmd, stdin=PIPE, bufsize=0)
p.communicate(input_data.encode('ascii'))
if p.returncode != 0:
   raise CalledProcessError(p.returncode, cmd)

这个怎么运作

os.linesep == "\r\n"在Windows上。 "\n".join(["a", "b"]) == "a\nb"

每个进程可能有三个标准流 :标准输入,标准输出,标准错误。 在Python中,他们表示为sys.stdinsys.stdoutsys.stderr 。 您可以从标准输入读取输入和写入到stdout,STDERR例如, input函数从标准输入读取和print写入默认标准输出。 标准错误可以用来写错误消息。

stdin=PIPE告诉Popen创建它称为父进程和新的子进程(“tsfoil2.exe”)之间的管道和重定向子标准输入。 p.communicate(data)将数据写入p.stdin ,关闭它,等待子进程结束。 p.returncode包含子进程的退出状态。 通常非零状态表示失败。

它模拟壳管道,而无需实际产卵壳:

$ echo input data | tsfoil2.exe

如果输入从控制台直接预期,你可以尝试SendKeys模块或它的纯Python实现SendKeys-ctypes

from SendKeys import SendKeys

SendKeys(r"""
    {LWIN}
    {PAUSE .25}
    r
    C:\Path\To\tsfoil2.exe{ENTER}
    {PAUSE 1}
    I:\{ENTER}
    {PAUSE 1}
    test{ENTER}
    {PAUSE 1}
    SC20610.inp{ENTER}
    {PAUSE 1}
    {ENTER}
""")

我没有测试它。



文章来源: How to handle an executable requiring interactive responses?