执行代码:
os.popen('allure')
抛出异常,未捕获到输出内容。
再次尝试代码:
os.popen("sc query state= all")
成功获取输出内容。
观察输出内容发现,异常语句的返回内容包含中文。
查看源码:
# Supply os.popen()
def popen(cmd, mode="r", buffering=-1):
if not isinstance(cmd, str):
raise TypeError("invalid cmd type (%s, expected string)" % type(cmd))
if mode not in ("r", "w"):
raise ValueError("invalid mode %r" % mode)
if buffering == 0 or buffering is None:
raise ValueError("popen() does not support unbuffered streams")
import subprocess, io
if mode == "r":
proc = subprocess.Popen(cmd,
shell=True,
stdout=subprocess.PIPE,
bufsize=buffering)
return _wrap_close(io.TextIOWrapper(proc.stdout), proc)
else:
proc = subprocess.Popen(cmd,
shell=True,
stdin=subprocess.PIPE,
bufsize=buffering)
return _wrap_close(io.TextIOWrapper(proc.stdin), proc)
标记断点发现采集输出时抛出异常,猜测应该是编码问题导致
源码中os.popen直接调用了subprocess.Popen方法,在输出时抛出异常,这边也直接调用该方法并查看返回内容
popen = subprocess.Popen(['ping', 'www.baidu.com', '-n', '3'], stdout = subprocess.PIPE)
popen.wait()
lines = popen.stdout.readlines()
打上断点查看返回值:
: [b'\r\n', b'\xd5\xfd\xd4\xda Ping www.a.shifen.com [115.239.210.27] \xbe\xdf\xd3\xd0 32 \xd7\xd6\xbd\xda\xb5\xc4\xca\xfd\xbe\xdd:\r\n', b'\xc0\xb4\xd7\xd4 115.239.210.27 \xb5\xc4\xbb\xd8\xb8\xb4: \xd7\xd6\xbd\xda=32 \xca\xb1\xbc\xe4=9ms TTL=50\r\n', b'\xc0\xb4\xd7\xd4 115.239.210.27 \xb5\xc4\xbb\xd8\xb8\xb4: \xd7\xd6\xbd\xda=32 \xca\xb1\xbc\xe4=9ms TTL=50\r\n', b'\xc0\xb4\xd7\xd4 115.239.210.27 \xb5\xc4\xbb\xd8\xb8\xb4: \xd7\xd6\xbd\xda=32 \xca\xb1\xbc\xe4=9ms TTL=50\r\n', b'\r\n', b'115.239.210.27 \xb5\xc4 Ping \xcd\xb3\xbc\xc6\xd0\xc5\xcf\xa2:\r\n', b' \xca\xfd\xbe\xdd\xb0\xfc: \xd2\xd1\xb7\xa2\xcb\xcd = 3\xa3\xac\xd2\xd1\xbd\xd3\xca\xd5 = 3\xa3\xac\xb6\xaa\xca\xa7 = 0 (0% \xb6\xaa\xca\xa7)\xa3\xac\r\n', b'\xcd\xf9\xb7\xb5\xd0\xd0\xb3\xcc\xb5\xc4\xb9\xc0\xbc\xc6\xca\xb1\xbc\xe4(\xd2\xd4\xba\xc1\xc3\xeb\xce\xaa\xb5\xa5\xce\xbb):\r\n', b' \xd7\xee\xb6\xcc = 9ms\xa3\xac\xd7\xee\xb3\xa4 = 9ms\xa3\xac\xc6\xbd\xbe\xf9 = 9ms\r\n']
成功获取输出内容, 但数据类型是bytes,需要进行decode,windows的默认编码为GBK
将返回值进行decode
[line.decode('gbk') for line in lines]
: ['\r\n', '正在 Ping www.a.shifen.com [115.239.210.27] 具有 32 字节的数据:\r\n', '来自 115.239.210.27 的回复: 字节=32 时间=9ms TTL=50\r\n', '来自 115.239.210.27 的回复: 字节=32 时间=9ms TTL=50\r\n', '来自 115.239.210.27 的回复: 字节=32 时间=9ms TTL=50\r\n', '\r\n', '115.239.210.27 的 Ping 统计信息:\r\n', ' 数据包: 已发送 = 3,已接收 = 3,丢失 = 0 (0% 丢失),\r\n', '往返行程的估计时间(以毫秒为单位):\r\n', ' 最短 = 9ms,最长 = 9ms,平均 = 9ms\r\n']
成功获取正常输出。
进行简易封装:
def popen(cmd):
try:
popen = subprocess.Popen(cmd, stdout=subprocess.PIPE)
popen.wait()
lines = popen.stdout.readlines()
return [line.decode('gbk') for line in lines]
except BaseException as e:
return -1
DONE :)