Locust 分布式负载测试教程
Locust 是一款基于 Python 的开源负载测试工具,使用纯 Python 代码定义用户行为,支持分布式测试和实时 Web UI 监控。与传统的 JMeter 不同,Locust 的测试脚本就是普通的 Python 代码,灵活度极高。在搬瓦工 VPS 上部署 Locust 可以对你的 Web 应用进行性能压测,找出系统瓶颈。
一、系统要求
- 操作系统:Ubuntu 20.04+(推荐 Ubuntu 22.04)。
- 内存:至少 512MB,分布式模式建议 1GB 以上。
- Python:3.8 以上版本。
二、安装 Locust
apt update && apt upgrade -y
apt install python3 python3-pip python3-venv -y
mkdir -p /opt/locust-project && cd /opt/locust-project
python3 -m venv venv
source venv/bin/activate
pip install locust
验证安装:
locust --version
三、编写测试脚本
3.1 基础测试脚本
创建 locustfile.py:
from locust import HttpUser, task, between
class WebsiteUser(HttpUser):
# 每次请求之间等待 1-3 秒
wait_time = between(1, 3)
@task(3)
def view_homepage(self):
self.client.get('/')
@task(2)
def view_article(self):
self.client.get('/article/1')
@task(1)
def view_about(self):
self.client.get('/about')
@task 装饰器的参数表示权重,数值越大执行频率越高。上面的例子中,访问首页的频率是访问关于页的 3 倍。
3.2 带登录的测试脚本
from locust import HttpUser, task, between
class AuthenticatedUser(HttpUser):
wait_time = between(1, 5)
def on_start(self):
"""登录操作,在每个虚拟用户启动时执行"""
response = self.client.post('/api/login', json={
'username': 'testuser',
'password': 'testpass'
})
if response.status_code == 200:
self.token = response.json().get('token')
else:
self.token = None
@task(5)
def get_dashboard(self):
headers = {'Authorization': f'Bearer {self.token}'} if self.token else {}
self.client.get('/api/dashboard', headers=headers)
@task(3)
def get_profile(self):
headers = {'Authorization': f'Bearer {self.token}'} if self.token else {}
self.client.get('/api/profile', headers=headers)
@task(1)
def create_post(self):
headers = {'Authorization': f'Bearer {self.token}'} if self.token else {}
self.client.post('/api/posts', headers=headers, json={
'title': 'Test Post',
'content': 'This is a load test post.'
})
3.3 多场景测试
from locust import HttpUser, task, between, SequentialTaskSet
class BrowseFlow(SequentialTaskSet):
"""模拟用户浏览流程"""
@task
def view_homepage(self):
self.client.get('/')
@task
def search_product(self):
self.client.get('/search?q=test')
@task
def view_product(self):
self.client.get('/product/123')
@task
def add_to_cart(self):
self.client.post('/cart/add', json={'product_id': 123, 'quantity': 1})
class BrowsingUser(HttpUser):
wait_time = between(2, 5)
tasks = [BrowseFlow]
四、运行 Locust
4.1 Web UI 模式
locust -f locustfile.py --host=https://your-target-site.com
Locust 默认在 8089 端口启动 Web UI,通过浏览器访问 http://YOUR_VPS_IP:8089 即可进入控制面板。在面板中可以设置并发用户数和每秒新增用户数。
4.2 命令行模式(无 UI)
# 100 个虚拟用户,每秒增加 10 个,运行 5 分钟
locust -f locustfile.py --host=https://your-target-site.com \
--headless -u 100 -r 10 --run-time 5m \
--csv=results/test
测试完成后会生成 CSV 报告文件。
4.3 防火墙设置
如需从外部访问 Web UI,需要开放 8089 端口:
ufw allow 8089/tcp
五、分布式测试
Locust 原生支持分布式负载测试,由一个 Master 节点和多个 Worker 节点组成。
5.1 启动 Master 节点
locust -f locustfile.py --master --host=https://your-target-site.com
5.2 启动 Worker 节点
在同一台 VPS 上启动多个 Worker(充分利用多核 CPU):
# 启动 4 个 Worker
for i in $(seq 1 4); do
locust -f locustfile.py --worker --master-host=127.0.0.1 &
done
如果是多台 VPS 组建集群,将 --master-host 改为 Master 节点的 IP 地址。
5.3 使用 Docker 部署分布式集群
mkdir -p /opt/locust-cluster && cd /opt/locust-cluster
cat > docker-compose.yml <<'EOF'
version: '3.8'
services:
master:
image: locustio/locust
ports:
- "8089:8089"
volumes:
- ./locustfile.py:/mnt/locust/locustfile.py
command: -f /mnt/locust/locustfile.py --master -H https://your-target-site.com
worker:
image: locustio/locust
volumes:
- ./locustfile.py:/mnt/locust/locustfile.py
command: -f /mnt/locust/locustfile.py --worker --master-host master
deploy:
replicas: 4
EOF
docker compose up -d
六、结果分析
Locust 的 Web UI 提供实时统计图表,包括:
- RPS(每秒请求数):衡量系统吞吐量。
- 响应时间:包括中位数、95 分位和 99 分位。
- 失败率:请求失败的百分比。
- 用户数:当前活跃的虚拟用户数。
命令行模式生成的 CSV 文件可以导入 Excel 或其他工具进行详细分析。
七、高级配置
7.1 自定义形状
通过 LoadTestShape 可以定义复杂的负载曲线:
from locust import HttpUser, task, between, LoadTestShape
class StagesShape(LoadTestShape):
stages = [
{'duration': 60, 'users': 10, 'spawn_rate': 2},
{'duration': 120, 'users': 50, 'spawn_rate': 5},
{'duration': 180, 'users': 100, 'spawn_rate': 10},
{'duration': 240, 'users': 50, 'spawn_rate': 5},
{'duration': 300, 'users': 0, 'spawn_rate': 10},
]
def tick(self):
run_time = self.get_run_time()
for stage in self.stages:
if run_time < stage['duration']:
return (stage['users'], stage['spawn_rate'])
return None
7.2 事件监听
from locust import events
@events.request.add_listener
def on_request(request_type, name, response_time, response_length, exception, **kwargs):
if exception:
print(f'请求失败: {name} - {exception}')
elif response_time > 5000:
print(f'慢请求: {name} - {response_time}ms')
八、常见问题
连接数限制
调整系统文件描述符限制以支持更多并发连接:
ulimit -n 65535
echo "* soft nofile 65535" >> /etc/security/limits.conf
echo "* hard nofile 65535" >> /etc/security/limits.conf
内存不足
大量虚拟用户会消耗较多内存,建议使用分布式模式将负载分散到多个 Worker 节点。
总结
Locust 是灵活且强大的负载测试工具,其 Python 脚本编写方式让测试场景的定义变得简单直观。在搬瓦工 VPS 上可以快速搭建分布式压测环境,对你的 Web 应用进行全面的性能评估。选购搬瓦工 VPS 请参考 全部方案,购买时使用优惠码 NODESEEK2026 可享受 6.77% 折扣。更多负载测试工具请参考 Artillery 教程 和 Vegeta 教程。