Python:将控制台输出保存成文件

2022年7月31日 388点热度 0人点赞 0条评论

简介:运行python程序时,控制台会输出一些有用的信息。为了方便保存这些信息,有时需要对这些信息进行保存。


历史攻略:

Python:封装logging模块和引用

Python:subprocess模块


起源:命令行执行ping ip,需求为将ping内容过程保存到文件

ping www.baidu.com

输出结果:

正在 Ping www.baidu.com [163.177.151.110] 具有 32 字节的数据:来自 163.177.151.110 的回复: 字节=32 时间=22ms TTL=56来自 163.177.151.110 的回复: 字节=32 时间=14ms TTL=56来自 163.177.151.110 的回复: 字节=32 时间=13ms TTL=56来自 163.177.151.110 的回复: 字节=32 时间=12ms TTL=56
163.177.151.110 的 Ping 统计信息: 数据包: 已发送 = 4,已接收 = 4,丢失 = 0 (0% 丢失),往返行程的估计时间(以毫秒为单位): 最短 = 12ms,最长 = 22ms,平均 = 15ms

改造成Python脚本:

# -*- coding: utf-8 -*-# time: 2022/7/31 11:26# file: main.py# 公众号: 玩转测试开发import oscmd = "ping www.baidu.com"message = os.system(cmd)print("*" * 100)print(message)

执行脚本结果:


正在 Ping www.baidu.com [163.177.151.110] 具有 32 字节的数据:来自 163.177.151.110 的回复: 字节=32 时间=11ms TTL=56来自 163.177.151.110 的回复: 字节=32 时间=12ms TTL=56来自 163.177.151.110 的回复: 字节=32 时间=12ms TTL=56来自 163.177.151.110 的回复: 字节=32 时间=13ms TTL=56
163.177.151.110 的 Ping 统计信息: 数据包: 已发送 = 4,已接收 = 4,丢失 = 0 (0% 丢失),往返行程的估计时间(以毫秒为单位): 最短 = 11ms,最长 = 13ms,平均 = 12ms****************************************************************************************************0

产生的问题,即:需求是将控制台的数据当成变量进行保存,结果得到的结果为,星号下的结果:0,这不符合我们想要的结果。原因在于

解决方案1:通过subprocess.check_output()案例:执行命令,返回执行的结果,而不是打印

# -*- coding: utf-8 -*-# time: 2022/7/31 11:26# file: main.py# 公众号: 玩转测试开发import subprocesscmd = "ping www.baidu.com"message = subprocess.check_output(cmd)print("*" * 100)print(message.decode(encoding='gbk'))

执行结果:如遇到中文乱码,参考 - pycharm界面dos命令中文乱码问题处理

****************************************************************************************************
正在 Ping www.baidu.com [163.177.151.109] 具有 32 字节的数据:来自 163.177.151.109 的回复: 字节=32 时间=12ms TTL=56来自 163.177.151.109 的回复: 字节=32 时间=69ms TTL=56来自 163.177.151.109 的回复: 字节=32 时间=12ms TTL=56来自 163.177.151.109 的回复: 字节=32 时间=87ms TTL=56
163.177.151.109 的 Ping 统计信息: 数据包: 已发送 = 4,已接收 = 4,丢失 = 0 (0% 丢失),往返行程的估计时间(以毫秒为单位): 最短 = 12ms,最长 = 87ms,平均 = 45ms

以上情况,可以覆盖绝大部分的场景,个别命令行执行,会出现输出为空的情况,如

起源案例2:

# -*- coding: utf-8 -*-# time: 2022/7/31 11:26# file: main.py# 公众号: 玩转测试开发
import subprocesscmd = "locust -f pressure_test.py --headless --users 100 --spawn-rate 1 -H http://127.0.0.1:7890 --run-time 5s"message = subprocess.check_output(cmd)print("*" * 100)print(message.decode(encoding='gbk'))

执行结果:输出的message为空。

[2022-07-31 11:43:10,811] LAPTOP-3FI0HAN5/INFO/locust.main: Run time limit set to 5 seconds[2022-07-31 11:43:10,811] LAPTOP-3FI0HAN5/INFO/locust.main: Starting Locust 2.1.0[2022-07-31 11:43:10,811] LAPTOP-3FI0HAN5/INFO/root: Terminal was not a tty. Keyboard input disabled Name                                                                              # reqs      # fails  |     Avg     Min     Max  Median  |   req/s failures/s-------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- Aggregated                                                                             0     0(0.00%)  |       0       0       0       0  |    0.00    0.00
[2022-07-31 11:43:10,812] LAPTOP-3FI0HAN5/INFO/locust.runners: Ramping to 100 users at a rate of 1.00 per second Name # reqs # fails | Avg Min Max Median | req/s failures/s---------------------------------------------------------------------------------------------------------------------------------------------------------------- GET /hello 193 0(0.00%) | 11 7 26 10 | 0.00 0.00 GET /world 193 0(0.00%) | 4 1 13 2 | 0.00 0.00---------------------------------------------------------------------------------------------------------------------------------------------------------------- Aggregated 386 0(0.00%) | 7 1 26 9 | 0.00 0.00
Name # reqs # fails | Avg Min Max Median | req/s failures/s---------------------------------------------------------------------------------------------------------------------------------------------------------------- GET /hello 431 0(0.00%) | 14 7 29 15 | 52.50 0.00 GET /world 429 0(0.00%) | 8 1 22 9 | 52.50 0.00---------------------------------------------------------------------------------------------------------------------------------------------------------------- Aggregated 860 0(0.00%) | 11 1 29 10 | 105.00 0.00
[2022-07-31 11:43:15,079] LAPTOP-3FI0HAN5/INFO/locust.main: Time limit reached. Stopping Locust.[2022-07-31 11:43:15,081] LAPTOP-3FI0HAN5/INFO/locust.main: Running teardowns...[2022-07-31 11:43:15,081] LAPTOP-3FI0HAN5/INFO/locust.main: Shutting down (exit code 0), bye.[2022-07-31 11:43:15,081] LAPTOP-3FI0HAN5/INFO/locust.main: Cleaning up runner... Name # reqs # fails | Avg Min Max Median | req/s failures/s---------------------------------------------------------------------------------------------------------------------------------------------------------------- GET /hello 462 0(0.00%) | 15 7 34 15 | 108.48 0.00 GET /world 461 0(0.00%) | 9 1 30 9 | 108.24 0.00---------------------------------------------------------------------------------------------------------------------------------------------------------------- Aggregated 923 0(0.00%) | 12 1 34 11 | 216.72 0.00
Response time percentiles (approximated) Type Name 50% 66% 75% 80% 90% 95% 98% 99% 99.9% 99.99% 100% # reqs--------|--------------------------------------------------------------------------------|---------|------|------|------|------|------|------|------|------|------|------|------| GET /hello 15 16 17 19 23 24 29 32 34 34 34 462 GET /world 9 10 11 12 17 19 25 28 30 30 30 461--------|--------------------------------------------------------------------------------|---------|------|------|------|------|------|------|------|------|------|------|------| None Aggregated 11 15 16 17 21 24 27 30 34 34 34 923
****************************************************************************************************

升级版解决方案1:subprocess.getstatusoutput(),即接受字符串形式的命令,返回 一个元组形式的结果,第一个元素是命令执行状态,第二个为执行结果。

# -*- coding: utf-8 -*-# time: 2022/7/31 11:26# file: main.py# 公众号: 玩转测试开发
import subprocess
cmd = "locust -f pressure_test.py --headless --users 100 --spawn-rate 1 -H http://127.0.0.1:7890 --run-time 5s"message, out = subprocess.getstatusoutput(cmd)print("*" * 100)print(message)print("*" * 100)
file = "locust_test_report.txt"with open(file, "w")as f: f.write(out) print(f"进入文件{file}完毕")

执行结果:

图片

升级版解决方案2:

subprocess.Popen(shell=True, stdout=subprocess.PIPE,

stderr=subprocess.PIPE, universal_newlines=True, bufsize=1)

# -*- coding: utf-8 -*-# time: 2022/7/30 17:00# file: test1700.py# 公众号: 玩转测试开发# -*- coding: UTF8 -*-import subprocess
# 常用编码GBK = 'gbk'UTF8 = 'utf-8'
# 解码方式,一般 py 文件执行为utf-8 ,cmd 命令为 gbkcurrent_encoding = GBK
popen = subprocess.Popen( 'locust -f pressure_test.py --headless --users 100 --spawn-rate 1 -H http://127.0.0.1:7890 --run-time 20s', shell=True, stdout=subprocess.PIPE, stderr=subprocess.PIPE, universal_newlines=True, bufsize=1)# 执行out, err = popen.communicate()print('std_err: ' + err)
file = "test.txt"with open(file, "w", encoding="utf-8")as f_obj:    f_obj.write(err)

执行结果:

图片

74070Python:将控制台输出保存成文件

这个人很懒,什么都没留下

文章评论