第4章:压测工具选型与部署

做交易网关压测这么多年,我经常被问到:「到底该用哪个压测工具?」

说实话,没有银弹。每个工具都有自己的脾气。今天我就把几个主流工具掰开揉碎了讲讲,顺便聊聊我踩过的坑。

4.1 主流压测工具横向对比

先看一张对比表,心里有个底:

工具 协议支持 并发模型 脚本语言 学习成本 适合场景
wrk HTTP/HTTPS 多线程 + epoll Lua 快速压测、基准测试
JMeter HTTP、TCP、JDBC等 多线程 GUI配置 + BeanShell 复杂业务场景、分布式压测
Locust HTTP、自定义 协程(gevent) Python 灵活定制、持续集成
自研工具 任意 自定义 Go/Java/C++ 特定协议、极致性能

4.2 逐个聊聊

wrk:轻量级利器

我个人最常用 wrk。为什么?因为它够快、够简单。

wrk 底层用的是 epoll(Linux 下)或 kqueue(macOS 下),加上多线程模型。说白了,它把操作系统的高性能 I/O 复用机制用到了极致。你想想看,一个单机工具能轻松压出几十万 QPS,这还不够香吗?

不过 wrk 也有短板——它只支持 HTTP/HTTPS。如果你要压 TCP 自定义协议,那它帮不上忙。

适用场景:快速验证网关的 HTTP 接口性能、做基准测试、对比不同配置下的吞吐量。

JMeter:老牌全能选手

JMeter 我接触得最早。记得刚入行那会儿,公司压测全用 JMeter。它的插件生态确实丰富,JDBC、JMS、FTP 都能压。

但说实话,JMeter 的并发模型有点「重」。每个虚拟用户就是一个线程,压到几千并发时,JMeter 自己先扛不住了。我曾经在压测一个金融网关时,JMeter 客户端 CPU 跑满,但目标服务器才用了 30% 的资源。嗯,这就是典型的「压测工具成了瓶颈」。

避坑指南:我曾经用 JMeter 压 5000 并发,结果 JMeter 自己 OOM 了。后来改用 wrk,同样的机器轻松压到 2 万并发。所以,高并发场景慎用 JMeter。

Locust:Python 党的最爱

Locust 用协程(gevent)来处理并发,比 JMeter 的线程模型轻量得多。如果你团队里 Python 熟手多,Locust 是个好选择。

我个人觉得 Locust 最大的优势是「可编程性」。你可以用 Python 写出非常复杂的用户行为——比如先登录、再查询、再下单,每一步之间还有随机等待。这在模拟真实用户场景时特别有用。

但 Locust 的 Web UI 在压测过程中会消耗不少资源。我建议压测时关掉 UI,用命令行模式跑。

自研工具:终极方案

当上面这些工具都满足不了你时,就该考虑自研了。

我在上一家公司就自研过一个压测工具。原因很简单——我们的网关用的是自定义的二进制协议,wrk 不支持,JMeter 要写插件太麻烦,Locust 的性能又不够极致。

自研工具的好处是:

  • 完全掌控协议细节
  • 可以针对硬件做极致优化(比如 CPU 亲和性、大页内存)
  • 能精确控制发包时序

但代价也很大:开发周期长、维护成本高。说白了,不是万不得已,别轻易走这条路。

4.3 我的选型建议

根据不同的场景,我一般这样选:

  • 快速验证:wrk,5 分钟搞定
  • 复杂业务流程:JMeter,GUI 配置方便
  • 持续集成 + 灵活定制:Locust,Python 脚本好维护
  • 自定义协议 / 极致性能:自研工具

小技巧:我经常先用 wrk 做一轮快速压测,找到大概的性能瓶颈。然后再用 JMeter 或 Locust 做详细的场景压测。这样效率最高。

4.4 wrk 的安装与基本使用

好了,工具选型聊完了。接下来咱们动手装 wrk。

安装 wrk

Linux 上安装最简单:

# Ubuntu / Debian
sudo apt-get install wrk

# CentOS / RHEL(需要先装 EPEL)
sudo yum install epel-release
sudo yum install wrk

# macOS
brew install wrk

如果你喜欢从源码编译,也可以:

git clone https://github.com/wg/wrk.git
cd wrk
make
sudo cp wrk /usr/local/bin/

编译时注意:wrk 依赖 OpenSSL 和 LuaJIT。如果报错,先装这两个库。

基本使用

装好后,跑一个最简单的压测:

wrk -t12 -c400 -d30s http://localhost:8080/api/ping

这条命令的意思是:

  • -t12:用 12 个线程
  • -c400:保持 400 个并发连接
  • -d30s:压测持续 30 秒

输出结果长这样:

Running 30s test @ http://localhost:8080/api/ping
  12 threads and 400 connections
  Thread Stats   Avg      Stdev     Max   +/- Stdev
    Latency    12.34ms    8.56ms 123.45ms   75.23%
    Req/Sec     3.45k   456.78     5.67k    68.90%
  1234567 requests in 30.00s, 1.23GB read
  Socket errors: connect 0, read 0, write 0, timeout 0
Requests/sec:  41152.33
Transfer/sec:     41.99MB

几个关键指标:

  • Latency:延迟分布,看 Avg 和 Max 就能判断响应速度
  • Req/Sec:每个线程每秒处理的请求数
  • Requests/sec:总 QPS,这是最核心的指标
  • Socket errors:如果有非零值,说明网络或服务端有问题

注意:我第一次用 wrk 时,看到 Socket errors 里有 timeout,以为是服务端扛不住了。后来发现是 wrk 的线程数开太多,超过了 CPU 核心数。把 -t 改成 CPU 核数后,问题就解决了。

常用参数速查

参数 说明 示例
-t 线程数 -t12
-c 并发连接数 -c400
-d 压测时长 -d30s
-s 加载 Lua 脚本 -s script.lua
-H 自定义请求头 -H "Authorization: Bearer xxx"
--latency 输出延迟分布详情 --latency
--timeout 超时时间(默认无限) --timeout 5s

4.5 本章知识体系

下面这张图帮你理清思路:

压测工具选型决策树 压测需求 快速验证 / 基准测试 复杂业务流程 自定义协议 / 极致性能 推荐:wrk 推荐:JMeter / Locust 推荐:自研工具 多线程 + epoll,性能极高 仅支持 HTTP/HTTPS Lua 脚本扩展,学习成本低

这张图的核心逻辑很简单:先明确你的压测场景,再选工具。别一上来就搞自研,也别拿 wrk 去压自定义协议——工具用对了,事半功倍。


好了,这一章就到这里。工具选好了,下一章咱们就开始动手压测了。记住:工具只是手段,理解背后的原理才是关键。

专注资料整理