Agent Substrate 遥测容量测试一篇讲清:OTel Collector 压力评估完整方法
【免费下载链接】substrateAgent Substrate: the core system项目地址: https://gitcode.com/GitHub_Trending/substrate7/substrate
Agent Substrate 是一个安全优先的智能体执行运行时(agent substrate),专为高密度沙箱场景设计。围绕它的遥测容量测试(telemetry capacity testing)体系,可以一次性回答两个关键问题:系统到底发出多少遥测,以及这些遥测给 OTel Collector 带来多大压力。本文带你完整看懂它的场景阶梯、流量计量器(Telemetry Meter)和压力评估的判定标准——无需自己拼凑压测工具,仓库里的 benchmarking/ 目录已经准备好了全套方案。
🐙 一、遥测容量测试为什么重要
在大规模 Agent 系统中,OTel Collector 是所有遥测(traces / metrics / logs)的汇聚点。它一旦被压垮,会出现两类"静默"的数据丢失:
- Collector 侧丢弃:队列写满、内存超限,数据直接被拒;
- 客户端侧丢弃:SDK 本地队列溢出(
queue_full),数据根本没发出去。
更隐蔽的是,客户端丢弃看起来和"遥测量平稳"一模一样。Agent Substrate 的遥测容量测试体系就是为了让这类问题无处遁形:它把"加载压测 → 计量遥测 → 判定容量"沉淀为一条可复现的流水线,覆盖从空闲基线到长时间浸泡(soak)的完整场景。
💡 核心理念:容量结论不靠猜测,靠测量。每个版本的仪表都会变化,仓库因此只保留方法、不固化结果数字(见 benchmarking/observability.md 开头的说明)。
📊 二、测试体系全景:三层工具链
整个体系由三层组成,各司其职:
| 层次 | 职责 | 关键位置 |
|---|---|---|
| 🏋️ 负载生成 | Locust 编排 + Go 负载器 boomer / 消耗型负载 glutton | benchmarking/locust/、internal/benchmarking/boomer/、internal/benchmarking/glutton/ |
| 🔢 遥测计量 | Telemetry Meter(旁路"流量表",按服务计数) | benchmarking/telemetry/meter.yaml |
| 📈 结果读取 | Prometheus 抓取 + 现成 PromQL 查询表 | benchmarking/monitoring.yaml |
配套的容量模型与部署选型指南(体积模型、Deployment vs DaemonSet 决策)单独成文:docs/dev/best-practices/otel-collector.md。
🪜 三、四步场景阶梯:S0–S3 一次跑完整个扫描
场景阶梯(scenario ladder)定义在 benchmarking/automation/tests.yaml 中,四个以observability_开头的测试构成完整的容量扫描:
| 编号 | 测试 | 时长 | 做什么 |
|---|---|---|---|
| S0 | observability_s0_idle_floor | 5 分钟 | 无负载,测空闲控制面的"遥测地板" |
| S1 | observability_s1_user_sweep | 每步 3 分钟 | 并发用户 5 → 10 → 15 递增,采样率 0.1 |
| S2 | observability_s2_sample_rate_sweep | 每步 3 分钟 | 10 用户不变,采样率 0 → 0.1 → 1.0 |
| S3 | observability_s3_soak | 10 分钟 | 12 用户(S1 峰值的 80%)长时间浸泡 |
三条值得新手记住的设计细节:
- 每一步不少于 3 分钟。指标推送间隔是 60 秒,短于 3 分钟的步骤凑不满 3 个数据点,无法区分趋势和噪声;
- S1 的上限是 15 用户而非更多。因为压测池是 10 个 worker,再往上测到的是调度器排队时间,不是遥测本身。想更高就同步调大
workerCount; - 负载来自 boomer(Go 工作器)而非 Python。Python 与 gRPC 在高并发下会互相拖累,让压测器自己的延迟混进测量结果。
阶梯的"爬楼"行为由 benchmarking/locust/shapes/ladder_shape.py 驱动:一次运行完成整个扫描,只需部署一次、采集一份基线。
🔍 四、Telemetry Meter:给遥测装上一台"流量计"
托管 Collector 只上报自己的自指标,看不出"每个服务各发了多少数据"。Agent Substrate 的解法是一个旁路 Collector——Meter,配置见 benchmarking/telemetry/meter.yaml:
kubectl apply -f benchmarking/telemetry/meter.yaml METER=http://telemetry-meter.benchmarking.svc.cluster.local:4317 ./hack/install-ate.sh --deploy-ate-system --otlp-endpoint "${METER}"Meter 是一个tee(分支器):先按service.name计数 spans 和数据点,再把数据原样转发给托管 Collector。一次运行因此同时得到两份测量——各服务的遥测量(来自 Meter)和这份负载的成本(来自托管 Collector)。
读数通过 Prometheus 完成(配置:benchmarking/monitoring.yaml),常用查询:
| 想知道什么 | 查询 |
|---|---|
| 各服务 spans/秒 | sum by (service_name) (rate(substrate_spans_total[5m])) |
| 各服务数据点/分钟 | 60 * sum by (service_name) (rate(substrate_datapoints_total[5m])) |
| 数据是否到达 | sum(rate(otelcol_receiver_accepted_spans[5m])) |
| Collector 是否拒收 | sum(rate(otelcol_receiver_refused_spans[5m])) |
⚠️三个使用 Meter 的隐藏陷阱(详见 benchmarking/telemetry/README.md):
- 转发后数据会被归属到 Meter 本身,按 pod 分组会失真——要按 resource 里的
service.name分组; - tee 后只剩"一个大批发送方",连接粘性的负载分布效应会消失;
- Meter 自己是单副本,它也可能先成为瓶颈。所以要把
refused、queue_size等指标也加进判定标准。
此外,Meter 只能看到"到达的数据"。要看客户端是否本地丢弃,需打开 SDK 的可观测开关(如OTEL_GO_X_OBSERVABILITY=true),再读otel_sdk_processor_span_processed_total{error_type="queue_full"}这类计数器。
🌱 本地 kind 集群则不需要Meter:自带的 Collector(manifests/ate-install/kind/otel-collector.yaml)内置了同样的计数连接器,
install-ate-kind.sh还会顺手装好 Prometheus。
✅ 五、压力评估的 6 个判定标准
跑完一轮,怎么判断"Collector 扛住了"?benchmarking/observability.md 给出了明确的通过标准:
| # | 指标 | 标准 | 含义 |
|---|---|---|---|
| 1 | otelcol_receiver_refused_* | 必须为 0 | Collector 未拒收数据 |
| 2 | otelcol_exporter_enqueue_failed_* | 必须为 0 | 下游导出队列未写满 |
| 3 | 客户端queue_full | 必须为 0 | 数据不在源头丢失 |
| 4 | Collector 副本数 | 低于maxReplicas | 弹性扩容未被打满 |
| 5 | S3 中 working set 与otelcol_exporter_queue_size的斜率 | 趋近于 0 | 浸泡期内无持续增长 |
| 6 | otelcol_receiver_accepted_*(阳性对照) | 必须大于 0 | 确认数据真的在流动 |
两条容易被忽略的读数技巧:
- 📏内存要看 working set,不要用
kubectl top——后者是窗口平均值,会掩盖短促峰值; - ⚖️
deltatocumulative超限是无声故障:超过max_streams后新流被直接丢弃、连日志都不打。要全程盯住otelcol_deltatocumulative_datapoints{error="limit"}为 0、且streams_tracked / streams_limit低于 1。
第 6 条"阳性对照"最关键:一个什么都不发的导出器,和一个完美运行的导出器,在纯负向指标上长得一模一样。
⚖️ 六、遥测量体积模型:两条独立的轴
容量评估不能只盯压测数字。docs/dev/best-practices/otel-collector.md 给出了 Substrate 遥测量的体积模型——两个驱动因素沿不同轴增长:
Metrics 随"运行中的组件数"增长(与业务负载量关系不大):
datapoints/min ≈ nodes×atelet + ateapi副本×ateapi + router副本×router + worker_pods×ateom + 已插桩 actors×actorTraces 随"操作速率"增长:
spans/sec ≈ (生命周期操作/秒 + 请求/秒) × P(root被采样) × 每操作span数采样默认值采用ParentBased:ateapi、atelet、ateom-*为 0.1,atenet-router与 Envoy 为 0.01(见 internal/serverboot/serverboot.go 的初始化逻辑)。
由此得出两条实操规则:
- 组件多的集群,瓶颈在 metrics;负载重的集群,瓶颈在 traces——取两者中更大的那个来定容;
- Collector 吃紧时,优先降低 trace 采样率,而不是加机器。
🏗️ 七、部署选型:Deployment 还是 DaemonSet?
这是新手最容易问错的问题:"吞吐量到多少该换成 DaemonSet?" 官方答案很干脆:吞吐量是错的坐标轴。
真正的限制变量是集群里的 pod 数量——因为它决定了k8sattributes缓存的大小:
| 部署模式 | 每实例缓存 | 集群变大时 |
|---|---|---|
| Deployment | O(全集群 pod 数) | 无上限增长,HPA 无法化解 |
| DaemonSet + 节点作用域过滤 | O(本节点 pod 数) | 有界,因为节点 pod 数天然有限 |
正确的决策顺序是:
- 是否需要 trace 完整性处理?(尾采样要求一条 trace 的所有 span 落在同一实例,DaemonSet 会破坏这一点)——这一条常常直接定胜负;
- 数集群 pod 数,测量每个副本内存随 pod 数的增长曲线,找到自己的拐点;
- 最后才看节点内的遥测集中度。
⚠️ 特别提醒:DaemonSet 方案必须配合node_from_env_var作用域过滤(官方 DaemonSet 清单里已内置),否则每个节点都会缓存全集群元数据,反而更差。
🚀 八、快速上手:本地 kind 一键测量
没有 GKE 也没关系,kind 集群就是现成的遥测量测量环境:
hack/create-kind-cluster.sh hack/install-ate-kind.sh --deploy-ate-system # 自动装好 Collector + Prometheus kubectl port-forward -n otel-system svc/prometheus 9090:9090然后打开 Prometheus,用上面"四、遥测计量"里的查询表读数即可。kind 的差异只有两点:命名空间是otel-system(而非benchmarking)、指标推送间隔是 10 秒(查询窗口用[1m]就够)。
📌 注意:kind 单节点、单副本、无 HPA,只能测"量",测不出"成本"——内存和副本数结论不能外推到真实集群,成本类评估要放到 GKE 上跑 Meter。
📚 九、延伸阅读与文件清单
- docs/observability.md — Actor 可观测性模型:跨 suspend/resume 的日志、指标与追踪
- docs/dev/best-practices/otel-collector.md — Collector 部署最佳实践(GKE 托管 / DaemonSet / kind 三种拓扑)
- benchmarking/observability.md — 场景阶梯与判定标准(本文第三、五节出处)
- benchmarking/telemetry/README.md — Meter 安装、读数与陷阱清单
- benchmarking/automation/tests.yaml — 全部基准测试(含 S0–S3)的自动化定义
- benchmarking/locust/ 与 internal/benchmarking/glutton/ — 负载生成器与可配置资源消耗负载
一句话总结:Agent Substrate 的遥测容量测试 = 场景阶梯造压 + Meter 计量 + 六条判定标准 + 两条轴的体积模型。把这套方法搬到自己的集群,Collector 的容量问题就从"玄学"变成了"读数"。
【免费下载链接】substrateAgent Substrate: the core system项目地址: https://gitcode.com/GitHub_Trending/substrate7/substrate
创作声明:本文部分内容由AI辅助生成(AIGC),仅供参考