如何在Python中创建新的控制台会话并进行操作

1 投票
2 回答
3325 浏览
提问于 2025-04-18 17:20

我正在尝试了解如何在Python中使用控制台。假设我有一个Python2的脚本,这个脚本需要创建三个控制台(可以是bash或其他类型),并给它们提供不同的命令。

举个例子:

  • 控制台#1负责进行telnet连接
  • 控制台#2负责执行ping命令
  • 控制台#3负责新的ssh访问

到目前为止,我发现了subprocess模块。

我可以用这个

import subprocess
term1 = subprocess.Popen(['open', '-a', 'Terminal'])

但是我还是不知道怎么给term1发送命令。

谢谢。

2 个回答

1

如果你想和你的子进程进行交流,最好的方法是使用 subprocess.popen

https://docs.python.org/2/library/subprocess.html#subprocess.Popen

这样你就可以创建一个标准输入(stdin)和标准输出(stdout)来和这个进程沟通。就像上面链接里说的,你只需要把它们添加到 popen 的参数中:

subprocess.Popen(args, stdin=PIPE, stdout=PIPE)

还有一个方法是 popen.communicate(input= '你的输入')

这个方法会等到命令执行完毕。

2

我在Linux上测试过使用xterm,可能在MacOS X的终端上也能顺利使用……我希望如此。

关键的想法是从Python创建一个匿名管道,然后指示在终端模拟器中运行的shell从这个管道读取数据:

import os
output, input = os.pipe()
term = subprocess.Popen("xterm -e 'bash </dev/fd/{}'".format(output),shell=True)

f = os.fdopen(input,"wt")

# output as much as command as you want. `flush` between them ... to flush data
f.writelines("echo toto\n")
f.flush()

f.close()

这样可以在图形界面的终端模拟器上产生输出:

toto

如果你想要同时读和写,就需要打开两个管道——但要小心,如果在一个方向上填满管道可能会导致死锁:

>>> import os
>>> output1, input1 = os.pipe()
>>> output2, input2 = os.pipe()
>>> term = subprocess.Popen("xterm -e 'bash </dev/fd/{} >/dev/fd/{}'".format(output1,input2),shell=True)
>>> 
>>> fin = os.fdopen(input1,"wt")
>>> fout = os.fdopen(output2,"rt")
>>> 
# FOR EXPERIMENTAL PURPOSE ONLY: SUBJECT TO DEAD-LOCK !!!
>>> fin.writelines("date\n")
>>> fin.flush()
>>> 
>>> print fout.readline()

Thu Aug 14 23:50:15 CEST 2014

>>> 
>>> fin.close()
>>> fout.close()

话虽如此,在这种配置下,打开终端的唯一好处就是可以在图形界面上显示可能的stderr输出。

如果你只需要和底层命令(比如bash、ping等)进行通信,其实并不需要打开终端,只需连接到相应的子进程标准输入输出就可以了,具体可以参考其他答案。

撰写回答