Python-子进程执行系统命令,并实时获取输出数据和返回结果
背景
调用系统命令,需要获取执行之后的返回结果。
代码
- shell=True
- 如果把shell设置成True,指定的命令会在shell里解释执行。
- close_fds=True
- 如果把close_fds设置成True,*nix下会在开子进程前把除了0、1、2以外的文件描述符都先关闭。在 Windows下也不会继承其他文件描述符。
- stdin stdout和stderr
- 分别表示子程序的标准输入、标准输出和标准错误。可选的值有PIPE或者一个有效的文件描述符(其实是个正整数)或者一个文件对象,还有None。
- subprocess.PIPE
- 如果是PIPE,则表示需要创建一个新的管道,如果是None,不会做任何重定向工作,子进程的文件描述符会继承父进程的。另外,stderr的值还可以是STDOUT,表示子进程的标准错误也输出到标准输出。
- p.poll() : 定时检查命令有没有执行完毕,执行完毕后返回执行结果的状态,没有执行完毕返回None
# #!/usr/bin/env python
# -*- coding: utf-8 -*-
import subprocess
def run_cmd(_cmd):
"""
开启子进程,执行对应指令,控制台打印执行过程,然后返回子进程执行的状态码和执行返回的数据
:param _cmd: 子进程命令
:return: 子进程状态码和执行结果
"""
p = subprocess.Popen(_cmd, shell=True, close_fds=True, stdin=subprocess.PIPE, stdout=subprocess.PIPE,
stderr=subprocess.PIPE)
_RunCmdStdout, _ColorStdout = [], '\033[1;35m{0}\033[0m'
while p.poll() is None:
line = p.stdout.readline().rstrip()
if not line:
continue
_RunCmdStdout.append(line)
print(_ColorStdout.format(line))
last_line = p.stdout.read().rstrip()
if last_line:
_RunCmdStdout.append(last_line)
print(_ColorStdout.format(last_line))
_RunCmdReturn = p.wait()
return _RunCmdReturn, b'\n'.join(_RunCmdStdout), p.stderr.read()
if __name__ == '__main__':
code, stdout, stderr = run_cmd('ping -c 3 baidu.com')
print('\nreturn:', code, '\nstdout:', stdout, '\nstderr:', stderr)
需要用到子进程功能的时候,直接导入该文件,调用run(...)
方法即可。