Running Locust in Step Load Mode
If you want to monitor your service performance with different user load and probe the max tps that can be achieved, you can run Locust with Step Load enabled with --step-load:

如果你想分阶段递增并发用户数压测,找到系统最大的QPS,你可以用--step-load --step-users XX --step-time XX命令,不用再手动去增加用户数和压测时间。

譬如:

locust -f D:\api_locust\fm_api\locust_api\XXX.py  --master  --master-bind-port 9800 --headless -u 800 -r 50 --expect-workers 10 -t 50m -s 10  --step-load --step-users 200 --step-time 10m --csv D:\locustlog\

总共发起800并发请求,每秒启动50个用户,当启动到200用户数时,持续运行10分钟,运行步骤大致如下:

(1)4s启动到200

(2)200用户数:10分钟

(3)4s启动到400

(4)400用户数:10分钟

(5)4s启动到600

(6)600用户数:10分钟

(7)4s启动到800

(8)800用户数:10分钟

(9)800用户数:50-40=10分钟(小于10分钟)

压测结果如图:

可以得出系统qps最大也就550左右,后边随着并发数提升没有提升,唯一提升是平均响应时间。

通过 --step-load --step-users这样的命令就不用再折腾弄命令了。

关于压测结果图的生成,也很简单的,上面的压测命令会把压测的历史记录写到csv文件里,

读取csv文件再生成报表即可:

python用到的模块pyecharts

pyecharts文档地址:http://pyecharts.org/#/zh-cn/intro

贴个代码示例:

 1 # -*- coding = utf-8 -*-
2 # ------------------------------
3 # @time: 2020/8/15 16:05
4 # @Author: drew_gg
5 # @File: deal_csv.py
6 # @Software: api_locust
7 # ------------------------------
8
9 import os
10 import time
11 import csv
12 import datetime
13 from pyecharts.charts import Line
14 from pyecharts import options as opts
15 from pyecharts.globals import ThemeType
16
17 """
18 # pyecharts使用文档
19 # http://pyecharts.org/#/zh-cn/intro
20 """
21
22 pl = os.getcwd().split('api_locust')
23 path_html = pl[0] + 'api_locust\\resource\\html\\'
24
25
26 def report(interface_name, history_csv, stats_csv):
27 """
28 locust生成报表
29 :param interface_name:
30 :param history_csv:
31 :param stats_csv:
32 :return:
33 """
34 tm = []
35 uc = []
36 qps = []
37 fps = []
38 avg_time = []
39 all_r = ''
40 all_qps = ''
41 all_avg_time = ''
42 with open(history_csv, 'r') as f:
43 hc = csv.reader(f)
44 for x, i in enumerate(list(hc)):
45 if i:
46 if x != 0:
47 tm.append(time.strftime('%H:%M:%S', time.localtime(int(i[0]))))
48 uc.append(str(round(float(i[1]), 2)))
49 qps.append(str(round(float(i[4]), 2)))
50 fps.append(str(round(float(i[5]), 2)))
51 avg_time.append(str(round(float(i[20]), 2)))
52 with open(stats_csv, 'r') as f:
53 sc = csv.reader(f)
54 for x, i in enumerate(list(sc)):
55 if x != 0 and len(i) != 0:
56 all_r = str(i[2])
57 all_qps = str(round(float(i[9]), 2))
58 all_avg_time = str(round(float(i[5]), 2))
59 locust_title = "[{0}]压测情况:[ARC:{1}, QPS: {2}, AVT: {3}]".format(interface_name, all_r, all_qps, all_avg_time)
60 locust_html_name = path_html + interface_name + str(datetime.datetime.now().strftime('%m%d%H%M%S')) + '.html'
61 line = (
62 Line(init_opts=opts.InitOpts(theme=ThemeType.CHALK, width="1800px", height="800px"))
63 .add_xaxis(tm)
64 .add_yaxis('user', uc, is_smooth=True)
65 .add_yaxis('qps', qps, is_smooth=True)
66 .add_yaxis('fps', fps, is_smooth=True)
67 .add_yaxis('avg_t', avg_time, is_smooth=True)
68 .set_global_opts(
69 title_opts=opts.TitleOpts(title=locust_title),
70 tooltip_opts=opts.TooltipOpts(trigger="axis"),
71 toolbox_opts=opts.ToolboxOpts(is_show=True, orient="vertical", pos_left="1%", pos_top="10%"),
72 xaxis_opts=opts.AxisOpts(type_="category", boundary_gap=False,),
73 )
74 )
75 line.render(locust_html_name)
76
77
78 if __name__ == "__main__":
79 stats = "D:\\api_locust\\resource\\csv\\locust_exhibition_home.py0826095139_stats.csv"
80 history = "D:\\api_locust\\resource\\csv\\locust_exhibition_home.py0826095139_stats_history.csv"
81 report('a', history, stats)

关于报表的生成,不懂的自行去文档地址仔细研究研究,挺全的,各种报表样式都有。

另外,如果是分布式压测的话,不要手动去启动命令,自己写个py去自动创建生成多好:

 1 # -*- coding = utf-8 -*-
2 # ------------------------------
3 # @time: 2020/8/15 16:05
4 # @Author: drew_gg
5 # @File: locust_main.py
6 # @Software: api_locust
7 # ------------------------------
8
9 import datetime
10 import subprocess
11
12
13 class CoverLocust:
14 """
15 封面压测封装类
16 """
17 def __init__(self, ltp):
18 """
19 初始化压测参数
20 :param ltp: 参数字典
21 """
22 self.user = ltp['user']
23 self.r = ltp['r']
24 self.slave = ltp['slave']
25 self.m_time = ltp['m_time']
26 self.port = ltp['port']
27 self.master_host = ltp['master_host']
28 self.csv = ltp['csv']
29 self.master_script = ltp['master_script']
30 self.slave_script = ltp['slave_script']
31 self.step_u = ltp['step_u']
32 self.step_t = ltp['step_t']
33 # 定义csv文件名称
34 self.csv_name = ltp["master_script"].split('\\')[-1] + str(datetime.datetime.now().strftime('%m%d%H%M%S'))
35 self.csv_path = ltp['csv'] + self.csv_name
36 # 输出压测结果目录文件
37 self.stats_history_csv = self.csv_path + '_stats_history.csv'
38 self.stats_csv = self.csv_path + '_stats.csv'
39 self.failures_csv = self.csv_path + '_failures.csv'
40
41 # 生成master命令
42 def locust_master(self):
43 """
44 运行master指令
45 :return:
46 """
47 master_cmd = "locust -f %s --master --master-bind-port %s --headless " % (self.master_script, self.port)
48 master_pra = "-u %s -r %s --expect-workers %s -t %s -s 10 --step-load --step-users %s --step-time %s --csv %s "\
49 % (self.user, self.r, self.slave, self.m_time, self.step_u, self.step_t, self.csv_path)
50 master_cmd = master_cmd + master_pra
51 print(master_cmd)
52 subprocess.Popen(master_cmd, creationflags=subprocess.CREATE_NEW_CONSOLE)
53 return self.stats_history_csv, self.stats_csv, self.failures_csv, self.csv_name
54
55 # 生成slave命令
56 def locust_slave(self, slave_num):
57 """
58 运行slave指令
59 :param slave_num:
60 :return:
61 """
62 slave_cmd = "locust -f %s --master-host %s --master-port %s --headless --worker" % (self.slave_script, self.master_host, self.port)
63 print(slave_cmd)
64 for i in range(slave_num):
65 subprocess.Popen(slave_cmd, creationflags=subprocess.CREATE_NEW_CONSOLE)
66
67 # 杀掉压测进程
68 @classmethod
69 def close_process(cls):
70 """
71 杀掉命令进程
72 :return:
73 """
74 import os
75 os.system('taskkill /IM locust.exe /F')
 1 # -*- coding = utf-8 -*-
2 # ------------------------------
3 # @time: 2020/8/18 20:36
4 # @Author: drew_gg
5 # @File: locust_run.py
6 # @Software: api_locust
7 # ------------------------------
8
9 import os
10 import time
11 from run_locust import locust_main as locust_m
12 from locust_common.common_excel import deal_csv as report
13
14 pl = os.getcwd().split('api_locust')
15 path_csv = pl[0] + 'api_locust\\resource\\csv\\'
16 path_script = pl[0] + 'api_locust\\locust_view\\kbh_api\\locust_api\\'
17 script_name = "locust_exhibition_home.py"
18
19 # ************************************需维护更改的参数****************************#
20 # 并发数
21 user = 1400
22 # 每秒启动用户数
23 rate = 200
24 # 分布式压测启动的slave数量
25 num_slave = 10
26 # 本次压测执行的时长:h,m,s
27 run_time = '25m'
28 # master所在host/ip
29 master_host = "10.111.53.123"
30 # master 执行脚本
31 master_script = path_script + script_name
32 # slave 执行脚本
33 slave_script = path_script + script_name
34 # # csv存储文件的目录
35 # csv_path = path_csv + script_name.split('.')[0] + '_log\\'
36 # 递压用户数
37 step_user = 400
38 # 递压持续时间
39 step_time = '5m'
40 # ************************************需维护更改的参数****************************#
41
42
43 locust_p = {
44 'user': user,
45 "r": rate,
46 "slave": num_slave,
47 "m_time": run_time,
48 "port": 9800,
49 "master_host": master_host,
50 "csv": path_csv,
51 "master_script": master_script,
52 "slave_script": slave_script,
53 "step_u": step_user,
54 "step_t": step_time
55 }
56
57 if __name__ == "__main__":
58
59 # *****************执行脚本标识*******************#
60 sign = "master"
61 # sign = "slave"
62 # *****************执行脚本标识*******************#
63 lm = locust_m.CoverLocust(locust_p)
64 lm.close_process()
65 if sign == "master":
66 # 启动master
67 history_csv, stats_csv, failures_csv, csv_name = lm.locust_master()
68 sleep_time = int(run_time[:-1])
69 # 延迟30s读取csv文件
70 if run_time[-1] == 'h':
71 sleep_time = sleep_time * 60 * 60 + 30
72 if run_time[-1] == 'm':
73 sleep_time = sleep_time * 60 + 30
74 if run_time[-1] == 's':
75 sleep_time = sleep_time + 30
76 time.sleep(sleep_time)
77 # 生成报表
78 report.report(script_name.split('.')[0], history_csv, stats_csv)
79 if sign == "slave":
80 # 启动slave 分多台跑的话需要用num_slave除以台数
81 slave_num = int(num_slave/2)
82 lm.locust_slave(slave_num)
这样要修改啥,直接修改就行,也可以自己写个页面,点一下按钮就可以压测。

上面的这个压测结果图:

这个说明QPS还有升高的空间,目前的并发数还没到达瓶颈,还得再提升并发数【平均响应时间没有急剧提升】。当然,这个地方设置的between(0,0.5),

所以会出现800的并发结果qps达到960以上。

Locust QQ 群:

locust分布式压测的Step Load及no web模式下的报表自动生成的更多相关文章

  1. wrk,ab,locust,Jmeter 压测结果比较

    背景: 项目需要对一批接口进行压测,要求是接口的QPS(Quest Per Second每秒请求数)达到6万以上由于楼主一直使用的压力测试工具是jmeter,但是jmeter单台电脑无法达到6万的QP ...

  2. 案例 | 荔枝微课基于 kubernetes 搭建分布式压测系统

    王诚强,荔枝微课基础架构负责人.热衷于基础技术研发推广,致力于提供稳定高效的基础架构,推进了荔枝微课集群化从0到1的发展,云原生架构持续演进的实践者. 本文根据2021年4月10日深圳站举办的[腾讯云 ...

  3. jmeter分布式压测

    stop.sh需要跑Jmeter的服务器上安装Jmeteryum install lrzsz 安装rz.sz命令rz jemter的压缩包 拷贝到/usr/local/tools下面unzip apa ...

  4. jmeter 分布式压测(Linux)

    之前一篇博文写的是如何在Linux上使用jmeter压测,这篇介绍下Linux上jmeter的分布式压测. 和windows上的分布式类似,需要配置agent节点和控制机 一.Agent节点配置 1. ...

  5. jmeter 分布式压测(windows)

    单台压测机通常会遇到客户端瓶颈,受制于客户机的性能.可能由于网络带宽,CPU,内存的限制不能给到服务器足够的压力,这个时候你就需要用到分布式方案来解决客户机的瓶颈,压测的结果也会更加接近于真实情况. ...

  6. Jmeter 在linux下的分布式压测

    Jmeter 在linux下的分布式压测 0.将 windows机器作为master 控制机(同时也兼做负载机slave), linux机器作为 负载机 slave. 1.linux环境安装 : (1 ...

  7. 分布式压测系列之Jmeter4.0第一季

    1)Jmeter4.0介绍 jmeter是个纯java编写的开源压测工具,apache旗下的开源软件,一开始是设计为web测试的软件,由于发展迅猛,现在可以压测许多协议比如:http.https.so ...

  8. JMeter在linux上分布式压测步骤(二)

    哈喽,我又来了~ 前提:三台linux虚拟机,一台作为master,另外两台作为slave. 一.server端 1.修改1099端口,client和server通信的端口,可以不修改,默认就是109 ...

  9. jmeter实现分布式压测步骤

    环境说明:安装与控制机相同版本的jdk与jmeter 1.修改控制机中的jmeter.properties文件 将<remote_hosts=127.0.0.1>改为<remote_ ...

  10. Linux环境下进行分布式压测踩过的坑

    背景:公司为了满足大并发的情况,需要测试组配合,就需要分布式压测,这里我把我踩过坑都记录下来: 环境:Linux + jmeter-v.5.1.1;使用3台2核4G的压力机: Q1: Server f ...

随机推荐

  1. Codeforces Round 169 (Div. 2)C. Little Girl and Maximum Sum(差分、贪心)

    目录 题面 链接 题意 题解 代码 总结 题面 链接 C. Little Girl and Maximum Sum 题意 给q个[l,r]将所有这些区间里面的数相加和最大. 可以进行的操作是任意排列数 ...

  2. MySQL学习之初识数据库

    •数据库的相关概念 DB : 数据库,保存一组有组织的数据的容器 DBMS : 数据库管理系统,又称为数据库软件(产品),用于管理 DB 中的数据 SQL : 结构化查询语言,用于和 DBMS 通信的 ...

  3. electron fiddle 下载 镜像 下载不下来 已解决 electron-api-demos 安装

    fiddle 官网 https://www.electronjs.org/fiddle 一共3步 1. npm config set registry https://registry.npm.tao ...

  4. Python使用os模块创建带时间戳的文件

    直接上源码: import os import time # 定义函数名:在py文件路径下创建cache的txt文件 def txt(name, text): # os.getcwd() 获取当前的工 ...

  5. html添加css样式的两种方法

      html添加css样式有三种方法,分别为行内式(使用style属性,在特定的HTML标签内使用).内嵌式(style标签把css代码放在特定页面的head部分中).外联式(使用link标签,将外部 ...

  6. 键鼠共享工具使用(软KVM)-barrier(symless开源版)

    作用:通过软件方式,实现KVM,即一套键盘鼠标可以控制多台电脑,并可以进行粘贴板共享. 1.安装 打开https://github.com/debauchee/barrier,进releases下载对 ...

  7. 使用zxing来生成二维码

    使用zxing来生成二维码 二维码已经成为了现代生活中不可或缺的一部分,无论是商业还是个人使用,二维码都有着广泛的应用.而在二维码的生成过程中,zxing是一款非常优秀的开源库,它提供了一系列的API ...

  8. 文心一言 VS 讯飞星火 VS chatgpt (216)-- 算法导论16.2 3题

    三.假定在 0-1 背包问题中,商品的重量递增序与价值递减序完全一样.设计一个高效算法求此背包问题的变形的最优解,证明你的算法是正确的.如果要写代码,请用go语言. 文心一言: 在0-1背包问题中,如 ...

  9. 记录--vue3的宏到底是什么东西?

    这里给大家分享我在网上总结出来的一些知识,希望对大家有所帮助 前言 从vue3开始vue引入了宏,比如defineProps.defineEmits等.我们每天写vue代码时都会使用到这些宏,但是你有 ...

  10. C# Mat Bitmap互转

    var mat = OpenCvSharp.Extensions.BitmapConverter.ToMat(source);//bitmap转mat Cv2.CvtColor(mat, mat, C ...