系统压测案例
返回系统压测案例
一、什么是系统级压测
接口压测关注单个接口。
系统压测关注的是:
多个业务接口按照真实比例一起运行时,整个系统还能不能稳定支撑业务。
这类压测更接近生产环境。
因为线上用户不会只做一件事,而是会:
- 登录
- 浏览
- 搜索
- 下单
- 支付
二、案例背景
这里用一个简化的电商系统举例。
系统包括这些模块:
- 用户服务
- 商品服务
- 购物车服务
- 订单服务
- 支付服务
- MySQL
- Redis
业务方提出的目标:
- 活动期间支持 5000 在线用户
- 峰值下单链路稳定
- 核心接口错误率低于 0.1%
三、先做业务流量建模
系统压测不能直接拍脑袋设并发。
需要先把真实流量结构拆出来。
一个简化模型如下:
| 场景 | 行为 | 占比 |
|---|---|---|
| A | 登录 -> 浏览商品 -> 查看详情 | 70% |
| B | 登录 -> 浏览商品 -> 加入购物车 | 20% |
| C | 登录 -> 浏览商品 -> 加购 -> 下单 | 8% |
| D | 登录 -> 浏览商品 -> 加购 -> 下单 -> 支付 | 2% |
这个比例的意义在于:
- 浏览请求通常最多
- 真正走到支付的用户占比不高
- 各服务承受的压力并不相同
四、压测方案设计
本次系统压测可以拆成三个阶段:
1. 预热阶段
目标:
- 检查脚本是否正常
- 检查监控是否正常
- 提前让 JVM 进入稳定状态
2. 负载阶段
目标:
- 模拟接近日常峰值的业务流量
- 验证系统是否稳定
3. 压力阶段
目标:
- 超过预期流量继续加压
- 找到系统极限和瓶颈
五、执行结果示例
假设最终结果如下:
| 指标 | 结果 |
|---|---|
| 总 QPS | 4200 |
| 下单 TPS | 260 |
| 支付 TPS | 60 |
| 核心链路 P95 | 480ms |
| 错误率 | 0.35% |
从业务角度看,系统没有完全达标。
因为:
- 错误率高于目标
- 核心链路 P95 偏高
六、继续看各模块表现
压测时继续按模块拆数据:
| 模块 | 现象 |
|---|---|
| 用户服务 | 正常 |
| 商品服务 | 正常 |
| 购物车服务 | 轻微抖动 |
| 订单服务 | RT 明显升高 |
| 支付服务 | 偶发超时 |
这一步的作用是:
- 快速缩小范围
- 避免盲目查整个系统
七、结合监控定位问题
监控中发现:
1. 订单服务线程池积压
表现:
- 活跃线程数接近上限
- 队列长度持续增长
2. MySQL 慢 SQL 增加
表现:
- 订单查询和库存校验语句变慢
- 数据库连接池接近打满
3. Redis 命中率下降
表现:
- 商品详情大量回源数据库
4. 支付服务依赖第三方接口
表现:
- 第三方响应时间波动大
八、分析结论
这个系统案例里,真正的瓶颈不是单点,而是组合问题:
- 商品缓存命中率下降,导致数据库压力变大
- 数据库压力变大后,订单服务 RT 跟着升高
- 订单服务线程池开始积压,错误率上升
- 支付链路又叠加了第三方接口波动
这类现象在企业里非常常见。
也就是说:
系统压测常常暴露的是链路问题,而不是单点问题。
九、可以采取的优化动作
1. 商品缓存优化
- 提高热点商品缓存命中率
- 避免缓存过早过期
2. 数据库优化
- 给订单查询补索引
- 优化库存校验 SQL
- 拆分重查询和轻查询
3. 应用服务优化
- 调整线程池参数
- 限制非核心接口资源占用
- 增加熔断和降级
4. 支付链路优化
- 支付确认异步化
- 缓解第三方抖动对主流程的影响
十、系统压测和接口压测的区别
这个案例能帮助你理解两者差异:
| 维度 | 接口压测 | 系统压测 |
|---|---|---|
| 范围 | 单个接口 | 多个模块 |
| 目标 | 看单点能力 | 看整体承载 |
| 数据 | 较简单 | 更复杂 |
| 定位 | 相对容易 | 更依赖监控 |
对 Java 后端工程师来说,系统压测的价值更大,因为它更接近真实生产问题。
十一、初学者怎么做系统压测
建议循序渐进:
- 先会做单接口压测
- 再做两个接口串联
- 再做简单业务流程
- 最后做系统级比例建模
如果一开始就上复杂全链路,往往容易:
- 脚本写不稳
- 数据准备不足
- 压完也解释不清结果
十二、总结
系统压测案例的重点是四件事:
- 流量建模
- 全链路观察
- 分层定位
- 结果解释
它比单接口压测更复杂,但也更有价值。
因为你最终要回答的,不是“一个接口能不能扛”,而是“整个系统能不能稳定支撑业务”。