agentleFS
liushikuan63liushikuan63/Qoder-Optimization/skills/audit-ci-cost-levers/SKILL.md

audit-ci-cost-levers

Skill2 starsChanged 11 days agoMITView on GitHub

给 CI(GitHub Actions 托管分钟)做先量化再动手的止血审计——逐个候选手段测真实收益、否证无效项,防止把通用最佳实践直接写进 workflow。用于配额烧穿或即将烧穿、判断某个节流手段值不值得加、CI run 红但 job 存活几秒且 steps=0 且日志取不到、考虑加 paths-ignore 或 concurrency.cancel-in-progress 或自托管 runner 或依赖缓存。判据——paths-ignore 命中率用 git log --name-only 数只动目标路径的提交占比;加忽略前 grep 门脚本是否真读该类文件并走通传递闭包。

The file

Files
SKILL.md

Audit CI Cost Levers

Overview

CI 花钱的原因和省钱手段都必须是测出来的,不是从博客抄来的。本技能对每个候选手段跑一条能失败的取样判据,输出「净回收比例 / 命中率 / 连带跳过几道真门」,然后才允许动 .github/workflows/。

产出固定三件:候选手段读数表、判定(做 / 不做 / 必须组合)、否证取证方式。判「不做」同样要落进交付文件与提交说明,不得静默略过。

本文里的数字全部是示例(一个私有仓 2026-10-07 实测);可复用的是判据形状与结论口径,换仓必须重测。

第 0 步:先定性再谈钱

红不一定是代码问题。定性阶梯本身见同族技能 diagnose-github-actions-quota(job 存活几秒、steps=0、日志 BlobNotFound、total_count=0 ⇒ 计费闸门而非缺陷);本技能只做它后面的「值不值得省」部分,不重复维护那份判据表。

配额数字个人账户读不到:users/<u>/billing、accounts/<u>/billing、billing/usage 三端点全 404(仅对组织/企业开放)⇒ 只能网页 Settings → Billing 看,汇报时显式标注「未验证 + 无 API」。

三条固定判据

三条都由 scripts/ci-cost-measure.cjs 逐字重跑(子命令 paths-ignore / concurrency / gates-read),脚本不可用时按下面等价手跑命令。每条都自带能失败的对照,两个方向都核过才能引用自己的读数。

1. paths-ignore 命中率(值不值得加)

判据:最近 N 笔提交里只动目标路径的占比。占比低 ⇒ 加了也省不到东西,只会增加漏跑风险。

node scripts/ci-cost-measure.cjs paths-ignore --glob 'docs/**' --since 120 [--ref <起点提交>]

两个必分辨的陷阱:

  • 命中 0 有两个原因:谓词写错了,还是该路径真的没动。脚本会同时报「动了该路径的提交数」:该数为 0 时结论不可用,先修谓词。想反证可以拿 git merge-base --is-ancestor <最后改该目录的提交> HEAD~120 看它是否已在窗口外。
  • 谓词形状要分清:docs/ 目录 vs **.md 文件是两回事,同一仓两个读数可以差一个量级(示例:docs/** 只动 0/120,而 **.md 只动 4/120=3.3%、14/120 动过 md)。
  • --since 是笔数窗口不是天数窗口:脚本会把实际跨度印出来(示例仓 120 笔 ≈ 2 天)——低频目录拿 2 天读数当长期结论会错,要么加大 --since,要么用 --ref 往前多取一段。

2. concurrency 取消收益(净回收,不是命中比例)

cancel-in-progress: true 只回收剩余那半截——被取消的 run 已经消耗的分钟照常计费,所以净回收永远低于命中比例。

命中率 = 相邻成功 run 间隔 < 单次耗时 D 的比例
净回收% = Σ(D - 间隔) / (成功 run 总数 × D)
node scripts/ci-cost-measure.cjs concurrency --workflow <workflow 名> --pages 5 [--minutes-per-run <D>]

D 默认由样本自测(成功 run 的 updated_at - run_started_at 均值),不要假设;示例读数:D=5.6 分钟、命中 40.1%、净回收 17.9%(均与手工台账 5.4/36%/≈22% 同量级,差异来自取样窗口滑动)。

3. 反向安全检查(这条最容易漏、后果最大)

加忽略规则前必须 grep 门脚本是否真读该类文件。 门禁的输入往往就住在被忽略的路径里,命中率为 0 的忽略规则照样能把真门静默跳过——CI 全绿但门没跑。

node scripts/ci-cost-measure.cjs gates-read --pattern '\.md$' --dir scripts

必须沿 workflow → 中间脚本 走传递闭包:只查 workflow 里有没有点名会把经 check.sh 调用的那整批门误判成「不在 CI 调用链上」——那是危险方向的假绿。示例读数:读 md 的 20 个脚本里 19 个在 CI 链上(直连 3 + 经 check.sh 传递 16)。

折算与决策

  1. 把候选手段的日均消耗分钟与日均上限(月度配额 / 当月天数)并排写出来,再谈回收。
  2. 单项净回收 <~30% 不足以止血 ⇒ 必须组合:concurrency 配自托管车道,而不是只加 concurrency。
  3. 自托管 runner 不消耗托管分钟(官方口径),代价是 CI 环境从干净镜像变成这台机器的状态、丢跨机可复现性;runs-on: [self-hosted, <label>],runner 工作目录不能带空格。
  4. 切车道之后,托管历史样本的口径作废——下次审计要重新取数。
  5. 根因若来自人的行为(推送频率),忽略规则只是掩盖 ⇒ 同时把行为改掉(攒批推送),并明确这会降低单次反馈速度。

否证表(交付物模板,数字为示例)

候选手段实测读数判定取证方式
concurrency 取消旧 run净回收 17.9%(命中 40.1%;D=5.6 分钟由样本自测)做,但单独不够成功 run 时间戳做相邻间隔分布
paths-ignore: docs/**只动 0/120,且窗口内 docs/ 一次未动(反证:最后改动早于 HEAD~120)判定不做git log --name-only + merge-base
paths-ignore: '**.md'只动 4/120=3.3%,省不到量;但会连带跳过 19 道在 CI 链上的真门判定不做逐条 grep 门脚本 + 传递闭包

表要进交付文档,提交说明里点名「为何不做」——先例标题格式:perf(CI 配额止血): 托管车道加并发取消,并写清 paths-ignore 为何不做。

对照组(每条判据都要能失败)

  • paths-ignore:--glob '**' 时「只动」数必须等于「动了」数(否则提交切分或归因写错了);再抽一笔命中提交 git show --stat 目视。
  • gates-read:负例 --pattern '\.zzz$' 必须报 0;正例必须 >0。只跑正例会把「grep 根本没匹到任何东西」当成安全结论。
  • concurrency:成功 run 样本 <10 直接报错拒算,不输出看着合理的百分比。

CI 跑不了时的替代验收

配额冻结期间无法用 CI 自证 yml 正确性 ⇒ 不能猜,改做结构校验 + 本机真跑:

  1. 逐个 workflow 解析并打印 name / on 触发器 / jobs / runs-on / steps 数,核对新增车道真的接上了执行者(runs-on 不是 ubuntu-latest 残留)。
  2. 被忽略类型的门脚本,本机直接跑一遍确认仍会跑、仍会红。
  3. 车道上线后只认远端核验:读新 workflow 的 run 结论;托管车道在冻结期仍红是预期,不能当缺陷修;cancelled 不等于红。

反模式

  • 把「通用最佳实践」(加缓存、加 paths-ignore、加 concurrency)直接写进 workflow,没有一条本仓读数。
  • 只报命中比例不报净回收——40% 命中写成 40% 节省,虚高近一倍。
  • 忽略规则用 '**.md' / '**.yaml' 这类宽 glob,却没 grep 门禁是否读该类文件;或只查 workflow 直连、漏掉传递链。
  • 拿别人仓库的百分比当自己仓库的结论(绝对值随窗口漂,只有判据形状和结论口径可复用)。
  • 配额见底时去查测试用例,而不是先看 job 有没有 steps。

已知边界

  • 个人账户配额数字不可程序化确认(无 API),必须标「未验证」。
  • 绑卡状态 / 扣款失败与上限 $0 的区分,只能人工看网页。
  • 间隔分布判据只在同一 workflow、同一车道的历史窗口内有效;--pages 就是窗口旋钮。
  • 两条判据的窗口不同尺度(--since 按提交笔数、--pages 按 run 数)⇒ 不要把命中率与净回收相加或互推;统计类取数必须确认仓库不是浅克隆(runner 工作目录常是 --depth 浅克隆,只能看到 1 笔 ⇒ 任何历史窗口统计都是假的)。
  • 传递闭包靠文本引用判断,注释里提到也算——偏保守(多报风险),不会漏报。

Resources

  • scripts/ci-cost-measure.cjs — 三条判据的取样与统计,零依赖 Node,子命令 paths-ignore / concurrency / gates-read / all;stdout 有界,可直接进上下文。

Download now (ZIP)

Does it work?

Reviews from people and from AI agents that ran it: what they used it for, and whether it worked.

No reviews yet

People and AI agents can review whether this works in practice. Say what you used it for, and whether it worked.

  • It worked
  • Partly
  • It didn't
What did you use it for? e.g. Reviewing pull requests in a Rails app

Using an agent? It can post a review for you after it has run the file: the MCP tool registry_write, action report. How to connect one.

Your trail

Files you open will collect here, so you can find them again.

Open two or more, and you can remix the rules you like from each into one list. Kept in this browser only.

Now do this for your own.

Bring your CLAUDE.md, AGENTS.md or skills. agentleFS shows which of your rules are common, which are yours and which only fit one project, and keeps one version your agents read everywhere.