我想在python中执行linux shell,例如:
import os
cmd='ps -ef | grep java | grep -v grep'
p=os.popen(cmd)
print p.read()
代码在python2.7中运行良好,但在python2.4或python2.6中效果不佳
问题是:当环境是2.4或2.6时,linux中的每个进程只返回一行。例如:
这就是我想要的(这就是2.7中返回的内容):
59996 17038 17033 0 14:08 pts/3 00:00:02 java -Xms64m -Xmx256m classpath=/home/admin/axxxX xxxx//xxxxxxxx ....
root 85751 85750 0 12:25 XXXXX XXXXXXX XXXXXXXX
但实际上它会像这样返回(在2.4 2.6中):
59996 17038 17033 0 14:08 pts/3 00:00:02 java -Xms64m -Xmx256m classpath=/home/admin/ax\n
root 85751 85750 0 12:25 XXXXX XXXXXXX XXXXXXXX\n
这意味着它会剪切每个项目,然后每个项目只剩下一行,并为结果中的每个项目添加\n
,这是我不想看到的< / p>
我尝试过其他方法,例如subprocess.Popen
或commands.getstatusoutput(command)
,但结果是一样的 - 我只得到每一项(流程)一行
信息:
如果我直接在linux的ssh上执行shell,结果很好
如果我执行ps -ef |grep java |grep -v grep >>1.txt
,将结果设为txtFile,结果也可以
python脚本将在如此多的机器上执行,因此将所有机器更新为python2.7或更新版本
是不合适的我有点担心,因为截止日期很快就会到来,我需要帮助。 期待您的回答,非常感谢
答案 0 :(得分:3)
你对read
的行为做出了无根据的假设。使用subprocess.Popen(尤其是其communicate
方法)来阅读整个内容。它是在2.4中引入的。
如果您需要单独的行,请使用字符串splitlines
方法。
答案 1 :(得分:0)
ps
通常根据终端宽度剪切其输出,但由于您将输出汇总到grep
,ps
无法确定宽度,因此它确定来自各种诸如终端类型,环境变量或命令行选项之类的东西,例如--cols
。
您可能会发现根据执行python脚本的方式会得到不同的结果。在交互式会话中,您很可能会看到管道的输出被剪切到您的终端宽度。如果从命令行运行脚本,您可能会看到完整的输出。
对不同版本的python的测试是否在同一台机器上运行,并以相同的方式运行(交互式命令行与命令行)?我怀疑这里的一些不一致可能导致不同的输出。
幸运的是,您可以使用ps
命令行选项告诉-ww
使用无限宽度:
import os
cmd='ps -efww | grep java | grep -v grep'
p = os.popen(cmd)
print p.read()
有了这个,你应该收到完整的ps
输出。
虽然subprocess.Popen()
应该产生相同的结果(因为ps
正在进行裁剪),但您应该使用它而不是os.popen()
- 当与subprocess.communicate()
一起使用时,您可以避免死锁。