我正在寻找一种Python解决方案,它允许我将命令的输出保存在文件中,而不会将其从控制台中隐藏.
仅供参考:我问的是tee(作为Unix命令行实用程序)而不是Python intertools模块中具有相同名称的函数.
tee,在Windows下不可用)stderr而努力stdoutstderr = subprocess.STDOUT不起作用.以下是我发现的一些不完整的解决方案:
图http://blog.i18n.ro/wp-content/uploads/2010/06/Drawing_tee_py.png
#!/usr/bin/python
from __future__ import print_function
import sys, os, time, subprocess, io, threading
cmd = "python -E test_output.py"
from threading import Thread
class StreamThread ( Thread ):
def __init__(self, buffer):
Thread.__init__(self)
self.buffer = buffer
def run ( self ):
while 1:
line = self.buffer.readline()
print(line,end="") …Run Code Online (Sandbox Code Playgroud) 我一直在寻找一种从python脚本运行外部进程的方法,并在执行期间打印其stdout消息.
下面的代码可以工作,但在运行时打印没有stdout输出.当它退出时,我收到以下错误:
sys.stdout.write(nextline)TypeError:必须是str,而不是bytes
p = subprocess.Popen(["demo.exe"],stdout = subprocess.PIPE, stderr= subprocess.PIPE)
# Poll process for new output until finished
while True:
nextline = p.stdout.readline()
if nextline == '' and p.poll() != None:
break
sys.stdout.write(nextline)
sys.stdout.flush()
output = p.communicate()[0]
exitCode = p.returncode
Run Code Online (Sandbox Code Playgroud)
我使用的是python 3.3.2
我正在使用Popen调用一个shell脚本,该脚本不断将其stdout和stderr写入日志文件.有没有办法连续同时输出日志文件(到屏幕),或者让shell脚本同时写入日志文件和标准输出?
我基本上想在Python中做这样的事情:
cat file 2>&1 | tee -a logfile #"cat file" will be replaced with some script
Run Code Online (Sandbox Code Playgroud)
再次,这将stderr/stdout连接到tee,将它写入stdout和我的日志文件.
我知道如何在Python中将stdout和stderr写入日志文件.我被困在哪里是如何将这些复制回屏幕:
subprocess.Popen("cat file", shell=True, stdout=logfile, stderr=logfile)
Run Code Online (Sandbox Code Playgroud)
当然我可以做这样的事情,但有没有办法在没有tee和shell文件描述符重定向的情况下做到这一点?:
subprocess.Popen("cat file 2>&1 | tee -a logfile", shell=True)
Run Code Online (Sandbox Code Playgroud) 我正在寻找从python调用shell脚本的方法,并使用日志记录将他们的stdout和stderr写入文件.这是我的代码:
import logging
import tempfile
import shlex
import os
def run_shell_command(command_line):
command_line_args = shlex.split(command_line)
logging.info('Subprocess: \"' + command_line + '\"')
process_succeeded = True
try:
process_output_filename = tempfile.mktemp(suffix = 'subprocess_tmp_file_')
process_output = open(process_output_filename, 'w')
command_line_process = subprocess.Popen(command_line_args,\
stdout = process_output,\
stderr = process_output)
command_line_process.wait()
process_output.close()
process_output = open(process_output_filename, 'r')
log_subprocess_output(process_output)
process_output.close()
os.remove(process_output_filename)
except:
exception = sys.exc_info()[1]
logging.info('Exception occured: ' + str(exception))
process_succeeded = False
if process_succeeded:
logging.info('Subprocess finished')
else:
logging.info('Subprocess failed')
return process_succeeded
Run Code Online (Sandbox Code Playgroud)
我确信无需创建临时文件来存储流程输出就可以实现.有任何想法吗?
是否可以修改以下代码以从'stdout'和'stderr'打印输出:
代码:
#!/usr/bin/python3
# -*- coding: utf-8 -*-
import subprocess
def run_cmd(command, cwd=None):
p = subprocess.Popen(command, cwd=cwd, shell=False,
stdout=subprocess.PIPE,
stderr=subprocess.PIPE)
outs, errs = p.communicate()
rc = p.returncode
outs = outs.decode('utf-8')
errs = errs.decode('utf-8')
return (rc, (outs, errs))
Run Code Online (Sandbox Code Playgroud)
感谢@unutbu,特别感谢@ jf-sebastian,最终功能:
#!/usr/bin/python3
# -*- coding: utf-8 -*-
import sys
from queue import Queue
from subprocess import PIPE, Popen
from threading import Thread
def read_output(pipe, funcs):
for line in iter(pipe.readline, b''):
for func in funcs: …Run Code Online (Sandbox Code Playgroud) 我正在运行一个脚本,通过使用执行许多可执行文件
subprocess.call(cmdArgs,stdout=outf, stderr=errf)
Run Code Online (Sandbox Code Playgroud)
when outf/ errf是None或文件描述符(stdout/的不同文件stderr).
有什么方法可以执行每个exe,以便将stdout和stderr一起写入文件和终端?
我正在使用子进程从Python(3.5.2)脚本运行命令行程序,我在Jupyter笔记本中运行该脚本.子进程需要很长时间才能运行,因此我希望它的stdout能够在Jupyter笔记本中实时打印到屏幕上.
我可以在从终端运行的普通Python脚本中做到这一点没问题.我这样做使用:
def run_command(cmd):
from subprocess import Popen, PIPE
import shlex
with Popen(shlex.split(cmd), stdout=PIPE, bufsize=1, universal_newlines=True) as p:
for line in p.stdout:
print(line, end='')
exit_code = p.poll()
return exit_code
Run Code Online (Sandbox Code Playgroud)
但是,当我在Jupyter笔记本中运行脚本时,它不会将stdout实时打印到屏幕上.相反,它会在子进程运行完毕后打印所有内容.
有没有人对如何解决这个问题有任何想法?
非常感谢,约翰尼
我正在通过Python的子进程模块运行脚本.目前我使用:
p = subprocess.Popen('/path/to/script', stdout=subprocess.PIPE, stderr=subprocess.PIPE)
result = p.communicate()
Run Code Online (Sandbox Code Playgroud)
然后我将结果打印到stdout.这很好,但由于脚本需要很长时间才能完成,我还希望从脚本到stdout的实时输出.我输出输出的原因是因为我想解析它.
我正在使用 Python 及其子进程库来使用 strace 检查调用的输出,具体如下:
subprocess.check_output(["strace", str(processname)])
Run Code Online (Sandbox Code Playgroud)
但是,这只在被调用的子进程完成后才给我输出,这对我的用例来说非常有限。
我需要进程的一种“流”或实时输出,因此我需要在进程仍在运行时读取输出,而不是仅在进程完成后读取输出。
有没有一种使用子流程库来实现此目的的便捷方法?我正在考虑每 x 秒进行一次轮询,但没有找到有关如何在文档中实现此功能的任何提示。
提前谢谢了。
我注意到两种不同的行为,两种方法应该产生相同的结果.
目标 - 使用子进程模块执行外部程序,发送一些数据并读取结果.
外部程序是PLINK,平台是WindowsXP,Python版本3.3.
主要想法 -
execution=["C:\\Pr..\\...\\plink.exe", "-l", username, "-pw", "***", IP]
a=subprocess.Popen(execution, bufsize=0, stdout=PIPE, stdin=PIPE, stderr=STDOUT, shell=False)
con=a.stdout.readline()
if (con.decode("utf-8").count("FATAL ERROR: Network error: Connection timed out")==0):
a.stdin.write(b"con rout 1\n")
print(a.stdout.readline().decode("utf-8"))
a.stdin.write(b"infodf\n")
print(a.stdout.readline().decode("utf-8"))
else:
print("ERROR")
a.kill()
Run Code Online (Sandbox Code Playgroud)
到现在为止还挺好.
现在,我想能够做一个循环(在每次写入子进程的stdin之后),等待直到子进程的stdout的EOF,打印它,然后是另一个stdin命令,依此类推.
所以我首先尝试了之前关于相同主题的讨论产生(从subprocess命令实时输出,逐行读取子进程stdout,python,subprocess:从子进程读取输出).
并且它没有工作(它永远挂起),因为PLINK进程保持活着,直到我自己杀死它,因此没有使用等待子进程的stdout到达EOF或在stdout为真时进行循环,因为它在我杀了它之前一直都是真的.
所以我每次写stdin时都决定从stdout读两次(对我来说很好) -
execution=["C:\\Pr..\\...\\plink.exe", "-l", username, "-pw", "***", IP]
a=subprocess.Popen(execution, bufsize=0, stdout=PIPE, stdin=PIPE, stderr=STDOUT, shell=False)
con=a.stdout.readline()
if (con.decode("utf-8").count("FATAL ERROR: Network error: Connection timed out")==0):
a.stdin.write(b"con rout 1\n")
print(a.stdout.readline().decode("utf-8"))
print(a.stdout.readline().decode("utf-8")) //the extra line [1]
a.stdin.write(b"infodf\n") …Run Code Online (Sandbox Code Playgroud) python ×10
subprocess ×9
stdout ×3
popen ×2
console ×1
ipython ×1
jupyter ×1
logging ×1
parent ×1
python-3.3 ×1
python-3.x ×1
stderr ×1
stream ×1
tee ×1