3、吞吐测试工具:qperf安装与使用、自定义测试脚本编写、多流并发测试、丢包与延迟模拟

吞吐测试,说白了就是看看你的QUIC连接到底能跑多快。我见过不少团队,协议栈调了半天,结果一上压测就露馅。所以这一章,咱们把qperf这个工具彻底吃透。

核心思路:先单流测基准,再多流压上限,最后加丢包和延迟看韧性。三步走,稳得很。

3.1 qperf安装与基础使用

qperf是Google官方维护的QUIC性能测试工具。我个人习惯把它装在两台Linux机器上,一台当服务端,一台当客户端。

安装方式(以Ubuntu 22.04为例):

# 安装依赖
sudo apt-get update
sudo apt-get install -y cmake golang-go libssl-dev

# 克隆qperf源码
git clone https://github.com/google/qperf.git
cd qperf

# 编译
mkdir build && cd build
cmake .. -DCMAKE_BUILD_TYPE=Release
make -j$(nproc)

# 安装到系统路径
sudo make install

嗯,这里要注意:如果你用的是CentOS或老版本Ubuntu,记得先升级gcc和cmake。我曾在CentOS 7上踩过坑,cmake版本太低,编译到一半就报错。

基础用法:

服务端启动很简单:

# 服务端监听默认端口(6121)
qperf --server

客户端发起一次吞吐测试:

# 客户端连接服务端,测试10秒
qperf --host 192.168.1.100 --time 10 --cc cubic

输出结果大概长这样:

Throughput: 1.24 Gbps
Goodput: 1.18 Gbps
Retransmissions: 0.02%
RTT: 2.3 ms

小技巧:第一次测试建议加 --verbose 参数,能看到握手细节和连接状态。我排查问题时,这个参数救过我好几次。

3.2 自定义测试脚本编写

光敲命令行肯定不行,咱们得写脚本自动化。我一般用Python封装qperf,方便批量跑测试。

下面是我常用的脚本模板:

#!/usr/bin/env python3
import subprocess
import json
import time
import sys

def run_qperf_test(host, duration=10, cc="cubic", streams=1):
    """
    执行一次qperf测试,返回解析后的结果
    """
    cmd = [
        "qperf",
        "--host", host,
        "--time", str(duration),
        "--cc", cc,
        "--streams", str(streams),
        "--json"  # 输出JSON格式,方便解析
    ]
    
    try:
        result = subprocess.run(cmd, capture_output=True, text=True, timeout=duration+5)
        if result.returncode != 0:
            print(f"测试失败: {result.stderr}")
            return None
        
        # 解析JSON输出
        data = json.loads(result.stdout)
        return {
            "throughput_bps": data.get("throughput", 0),
            "goodput_bps": data.get("goodput", 0),
            "retransmit_rate": data.get("retransmit_rate", 0),
            "rtt_us": data.get("rtt", 0)
        }
    except subprocess.TimeoutExpired:
        print("测试超时,请检查网络或服务端状态")
        return None
    except json.JSONDecodeError:
        print("JSON解析失败,检查qperf版本是否支持--json")
        return None

# 批量测试示例
if __name__ == "__main__":
    targets = ["192.168.1.100", "192.168.1.101"]
    for target in targets:
        print(f"正在测试 {target}...")
        res = run_qperf_test(target, duration=30, cc="bbr")
        if res:
            print(f"  Throughput: {res['throughput_bps']/1e9:.2f} Gbps")
            print(f"  RTT: {res['rtt_us']/1000:.2f} ms")
        time.sleep(2)  # 避免同时打爆服务端

避坑指南:我曾经在脚本里忘了加 timeout 参数,结果有一次网络抖动,qperf卡住不返回,整个压测流程全堵死了。所以,所有subprocess调用都必须设timeout,这是血泪教训。

3.3 多流并发测试

单流测试只能反映一条连接的性能。但实际场景中,QUIC的优势在于多路复用。你想想看,一个视频网站同时有几千个用户,每人都开好几条流,这才是真实压力。

qperf多流测试命令:

# 同时开启16条流,测试30秒
qperf --host 192.168.1.100 --time 30 --streams 16 --cc bbr

输出结果会显示聚合吞吐:

Aggregate Throughput: 8.92 Gbps
Per-stream Throughput: 557.5 Mbps
Retransmissions: 0.15%
RTT: 3.1 ms

多流测试的关键参数对比:

参数 说明 推荐值
--streams 并发流数量 4/8/16/32/64 逐步递增
--time 测试持续时间(秒) 30~120,太短测不准
--cc 拥塞控制算法 cubic / bbr / newreno
--pacing 是否启用 pacing(平滑发送) 默认开启,建议保持

我的经验:多流测试时,别一上来就开64条流。先4条、8条、16条慢慢加,观察聚合吞吐的增速。如果16条到32条吞吐没怎么涨,说明瓶颈可能在CPU或者网卡中断上,而不是协议本身。

3.4 丢包与延迟模拟

真实网络环境哪有那么干净?丢包、抖动、延迟,一个都少不了。所以咱们得用工具模拟这些坏情况,看看QUIC到底扛不扛得住。

推荐工具: tc(Linux流量控制) + netem(网络模拟器)。

模拟延迟:

# 在服务端网卡上增加50ms延迟
sudo tc qdisc add dev eth0 root netem delay 50ms

# 测试完后记得删除
sudo tc qdisc del dev eth0 root

模拟丢包:

# 模拟1%的随机丢包
sudo tc qdisc add dev eth0 root netem loss 1%

# 同时模拟延迟+丢包
sudo tc qdisc add dev eth0 root netem delay 30ms loss 2%

模拟抖动:

# 延迟50ms ± 10ms的随机抖动
sudo tc qdisc add dev eth0 root netem delay 50ms 10ms

注意:tc命令会直接影响整个网卡的所有流量。如果你在线上机器操作,记得先确认网卡名称,或者用 --ifb 虚拟网卡做隔离。我曾经手滑在业务服务器的eth0上加了100ms延迟,结果整个业务报警炸了……嗯,从那以后我都在测试环境操作。

完整的测试流程示例:

#!/bin/bash
# 多场景对比测试脚本

SERVER_IP="192.168.1.100"
INTERFACE="eth0"
RESULTS_DIR="./results"
mkdir -p $RESULTS_DIR

# 场景1:干净网络
echo "=== 场景1: 干净网络 ==="
qperf --host $SERVER_IP --time 30 --streams 8 --json > $RESULTS_DIR/clean.json

# 场景2:50ms延迟
echo "=== 场景2: 50ms延迟 ==="
ssh $SERVER_IP "sudo tc qdisc add dev $INTERFACE root netem delay 50ms"
qperf --host $SERVER_IP --time 30 --streams 8 --json > $RESULTS_DIR/delay_50ms.json
ssh $SERVER_IP "sudo tc qdisc del dev $INTERFACE root"

# 场景3:1%丢包
echo "=== 场景3: 1%丢包 ==="
ssh $SERVER_IP "sudo tc qdisc add dev $INTERFACE root netem loss 1%"
qperf --host $SERVER_IP --time 30 --streams 8 --json > $RESULTS_DIR/loss_1pct.json
ssh $SERVER_IP "sudo tc qdisc del dev $INTERFACE root"

# 场景4:延迟+丢包混合
echo "=== 场景4: 30ms延迟 + 0.5%丢包 ==="
ssh $SERVER_IP "sudo tc qdisc add dev $INTERFACE root netem delay 30ms loss 0.5%"
qperf --host $SERVER_IP --time 30 --streams 8 --json > $RESULTS_DIR/mixed.json
ssh $SERVER_IP "sudo tc qdisc del dev $INTERFACE root"

echo "所有测试完成,结果保存在 $RESULTS_DIR"

跑完这个脚本,你就能拿到四组数据。对比一下,你会发现:

  • 干净网络下,BBR和Cubic差距不大
  • 有丢包时,BBR的吞吐下降更平缓
  • 高延迟下,多流并发能有效提升总吞吐

核心结论:QUIC在丢包环境下的表现远好于TCP,但前提是你得选对拥塞控制算法。我个人在跨国链路上,BBR几乎是必选项。

本章知识体系

下面这张图,把本章的核心逻辑串起来了:

QUIC吞吐测试知识体系 QUIC吞吐测试知识体系 基础测试 多流并发 坏境模拟 qperf安装与配置 --streams参数调优 tc + netem模拟 单流吞吐/延迟 聚合吞吐/流分布 抗丢包/抗抖动能力 性能基准数据 + 调优方向 说明:从基础测试出发,逐步增加并发和网络劣化条件,最终形成完整的性能画像 每个环节的测试结果,都是后续调优决策的依据

这张图把本章的脉络理得很清楚:从左到右,从基础到复杂,从干净环境到恶劣环境。你照着这个路径走,就能系统性地摸透QUIC的吞吐性能。