4. 流水线成功率 SLI:定义流水线成功/失败的标准,计算口径

流水线成功率(Pipeline Success Rate)是衡量 CI/CD 交付质量最核心的 SLI 之一。它直接反映代码从提交到产出制品的整体健康度,也是故障排查和告警降噪的第一道防线。如果成功率持续低于阈值,说明交付管道存在系统性缺陷,需要立即介入。

4.1 成功与失败的标准定义

在 GitLab CI 中,一条流水线的最终状态由所有 Job 的聚合结果决定。但并非所有“非成功”状态都代表故障,需要区分业务失败与系统失败。

流水线状态 是否计入“失败” 说明
passed 否 所有 Job 均成功完成,视为成功流水线。
failed 是 至少一个 Job 返回非零退出码,属于业务逻辑失败。
canceled 是(按需) 手动取消。若因上游失败自动取消,应计入失败;若人为主动取消(如停止无效提交),可排除。
skipped 否 因 rules / only / except 条件未触发,不计入总流水线数。
manual 否 等待手动触发,未执行完成,不计入统计窗口。
running / pending 否 进行中或排队中,不参与当前时间窗口的统计。
建议口径:在计算成功率 SLI 时,只将 passed 视为成功,将 failed 和因失败自动 canceled 的流水线视为失败。手动取消和 skipped 流水线应从分母中剔除,避免稀释指标。

4.2 计算口径:总流水线数 vs 成功流水线数

成功率 SLI 的标准计算公式为:

流水线成功率 (%) = (成功流水线数 / 有效总流水线数) × 100%

其中:
- 成功流水线数 = 状态为 'passed' 的流水线数量
- 有效总流水线数 = 状态为 'passed' + 'failed' + 因失败自动 'canceled' 的流水线数量

以下通过一个实际场景说明口径差异:

统计维度 口径 A(宽松) 口径 B(严格) 口径 C(推荐)
总触发流水线 100 100 100
passed 80 80 80
failed 10 10 10
canceled(自动) 5 5 5
canceled(手动) 3 3 3
skipped 2 2 2
分母取值 100(全部) 95(排除 skipped) 95(排除 skipped + 手动取消)
成功率 80% 84.2% 84.2%

口径 A 将 skipped 和手动取消纳入分母,会低估真实交付能力;口径 B 和 C 更准确,其中口径 C 进一步排除了人为干预因素,适合作为 SLO 的基准。

4.3 流水线成功率计算流程

下图展示了从 GitLab API 采集原始数据到产出 SLI 指标的完整链路:

流水线成功率 SLI 计算流程 GitLab API 采集 原始数据清洗 状态分类映射 计算口径聚合 SLI 指标输出 关键过滤规则 • 排除 skipped 流水线 • 排除手动取消流水线 • 保留因失败自动取消 聚合窗口 • 按小时 / 按天 / 按部署 • 滚动窗口 vs 固定窗口

4.4 告警降噪:避免误报的过滤策略

直接对原始成功率设置告警会产生大量误报。以下策略可有效降噪:

  • 最小样本量过滤:在 5 分钟窗口内,若总流水线数 < 3 条,不触发告警,避免小样本波动。
  • 连续失败窗口:只有连续 N 条(如 3 条)流水线失败,才产生告警,容忍偶发抖动。
  • 排除已知故障窗口:在基础设施变更窗口(如 K8s 集群升级)内,自动抑制成功率告警。
  • 按分支分级:对 main 分支使用严格阈值(如 99%),对功能分支使用宽松阈值(如 90%)。
常见陷阱:不要将 canceled 状态全部视为失败。如果 CI 配置了“上游失败自动取消下游”,这些自动取消的流水线应计入失败分母;但如果是运维人员手动取消的重复提交,则应排除。建议在 GitLab Webhook 或 API 回调中增加 pipeline.canceled_by 判断逻辑。

4.5 成功率 SLI 的典型阈值参考

环境 / 分支 目标 SLO 告警阈值 说明
生产部署(main) ≥ 99.5% < 99% 持续 10 分钟 任何失败都应立即排查
预发布(release/*) ≥ 98% < 95% 持续 30 分钟 允许少量环境配置问题
功能开发(feature/*) ≥ 90% < 80% 持续 1 小时 容忍开发过程中的调试失败
合并请求(MR) ≥ 95% < 90% 持续 30 分钟 MR 流水线失败应快速反馈
实践要点:成功率 SLI 必须与“失败根因分类”联动。建议在 GitLab 流水线中为每个 Job 注入 failure_reason 标签(如 test_failure、build_error、infra_timeout),以便在告警时直接定位故障类型,避免每次都需要人工查看日志。