聚合运算符的作用
聚合运算符把多条序列合并成少数几条:输入是向量,输出是每个分组一条序列。它是控制图表可读性的主要手段,也是把明细数据转成结论的必经一步——不做聚合,上千实例的集群在图表上只会画出一团糊。
by 与 without 的差别
by 明确列出要保留的标签,其余全部丢弃;without 则相反,保留除列出标签之外的全部维度。实例级排查常用 without 保留服务与区域等维度,只去掉实例;结论型面板更适合用 by 把维度收敛到明确的几个。
基本信息
| 语法 | 聚合运算符紧跟分组子句,如 sum by (job) (...) |
|---|---|
| 等价写法 | without (instance) 与列出其余全部标签效果相同 |
| 不带分组 | 省略 by 与 without 时聚合成一个全局标量序列 |
| 适用对象 | 瞬时向量;范围向量不能直接聚合 |
| 常见运算符 | sum、avg、max、min、count、topk、quantile |
典型使用场景
- 服务级看板:按服务聚合请求速率与错误率,隐藏实例明细
- 集群级汇总:按集群聚合容量水位,支撑高层视图
- TopN 排查:用 topk 找出错误率或延迟最差的几个接口
- 维度裁剪:去掉实例标签后,多环境曲线可以叠加对比
- 去重计数:用 count 统计当前在线的目标数量
- 均值与极值:用 avg 与 max 区分整体劣化与个别实例异常
聚合写法示例
聚合写法示例
# 按 service 汇总错误速率(输出条数 = service 取值数)
sum by (service) (rate(http_requests_total{code=~"5.."}[5m]))
# 保留除实例外的所有维度,如 service、region
sum without (instance) (rate(http_requests_total[5m]))
# 找出错误速率最高的三个服务
topk(3, sum by (service) (rate(http_requests_total{code=~"5.."}[5m])))常用聚合运算符
| 运算符 | 作用 | 典型用途 |
|---|---|---|
| sum | 求和 | 总量与总速率 |
| avg | 平均 | 平均水位与平均延迟 |
| max / min | 取最大与最小 | 找出最差的实例 |
| count | 计数 | 在线目标数与样本数 |
| topk / bottomk | 取前 N 与后 N | 按维度排序取极值 |
维度裁剪的取舍
| 场景 | 推荐写法 | 原因 |
|---|---|---|
| 服务总览 | sum by (service) | 曲线数等于服务数,规模可控 |
| 实例下钻 | sum by (instance, service) | 保留实例才能定位单机问题 |
| 多环境对比 | sum without (instance) | 保留环境与区域维度 |
| 全局单值 | sum(...) | 得到一个标量,适合单值面板 |
常见的层级约定
- 主机层:按实例聚合并保留实例标签,便于定位单机
- 服务层:按服务与接口聚合,回答哪个接口出问题
- 业务层:按业务域聚合,回答用户能否顺利完成交易
- 汇总层:全局求和,仅用于总览单值面板
聚合顺序会影响结果
先过滤再聚合,与先聚合再过滤,得到的是两个不同结果:求和之后再筛条件,等于把不满足条件的部分也算进了总量。稳妥顺序是先在选择器里过滤,再对结果聚合,最后用 topk 一类函数收口,这样每一步的语义都清晰可验证。
聚合会丢弃未被保留的标签且不可恢复:如果后面还要按状态码区分,就必须把它留在分组标签里,否则只能重新查询。
按用户或请求 ID 这类高基数字段分组,会让输出序列数随流量暴涨,查询直接压垮服务端:分组维度只能取基数可控的标签。
分组标签的顺序不影响结果,但写法应保持一致:同一套看板里混用 by 与 without,会让后续维护时难以判断哪些维度被保留了。
聚合前的检查项
- 确认要保留的维度:面板上需要区分的标签必须写进分组
- 确认过滤位置:条件尽量写进选择器而不是聚合之后
- 确认输出条数:分组维度的取值数量决定曲线条数
- 确认是否需要下钻:要下钻就先按实例保留维度