A platform team proposes an architecture-test suite - 30 automated checks on layering and dependency rules - run on every pull request across 40 repositories. The repositories see about 600 pull requests a month in total and each check run takes about 90 seconds of runner time. Roughly what does this cost a year, and what does the number decide?
Show the full answer Hide the answer
The assumptions, stated
- 600 pull requests a month across all 40 repositories.
- Each pull request runs the suite once per push; assume 2 pushes per pull request on average, so about 1,200 suite runs a month.
- 90 seconds of runner time per run, as given.
The arithmetic
1,200 runs a month × 90 seconds = 108,000 seconds a month = 30 runner-hours a month. Twelve months gives about 360 runner-hours a year at two pushes per pull request, or about 180 at one push. Call it 150 to 400 runner-hours a year, order of magnitude a few hundred.
At a typical cloud runner rate on the order of a few cents per minute in 2026, a few hundred hours is roughly a few hundred to about a thousand currency units a year. That is a rounding error against one engineer-week.
The assumption that dominates the error is pushes per pull request, not the 90 seconds. A team that pushes fifteen times per pull request multiplies the whole figure by seven, and that is the number to measure before optimising anything.
What the number rules in and out
It rules in the suite, immediately, without a cost discussion. It rules out the two arguments usually made against this kind of work: that CI cost is the obstacle, and that the checks should run nightly rather than per pull request. Nightly is strictly worse: it finds the violation after the author has moved on, which is the difference between a 30-second fix and a conversation.
It also rules out the optimisation in the second option. Running checks only on affected repositories is good engineering for a 55-minute pipeline; for a 90-second check it saves a few hundred hours a year and costs a change-detection mechanism that will itself be wrong occasionally. Do not build selective execution for a check that is cheaper than the mechanism to skip it.
Why the other options fail
1,500 runner-hours, material, needs selective execution. This is the right answer at ten times the volume or ten times the check duration, and the reflex to optimise CI is usually correct. Here it over-estimates by about 4x and prescribes machinery that costs more than it saves.
15,000 runner-hours, unaffordable. Off by roughly two orders of magnitude. The mistake is multiplying by pull requests per repository rather than in total, or by assuming the suite runs per check rather than per run. Worth noticing because it is the arithmetic error that kills useful proposals in review.
The runner cost is irrelevant; only maintenance matters. Half right, and the half that is wrong matters. Maintenance is indeed the dominant cost, and the specific failure is a check that keeps passing after it stopped examining anything — a rule whose glob no longer matches the moved directory. But "the cost is irrelevant" is how a proposal gets approved without anyone measuring pushes per pull request, which is the one input that could make it expensive.
What to do with the maintenance cost
Budget it explicitly: every check needs a test that the check fails on a known violation, run in the same suite. Thirty checks is thirty negative tests. That is the real annual cost, measured in engineer-days, and it is the number worth arguing about.
When not to run them on every pull request
When a single check is slow rather than cheap. An architecture check that builds the whole dependency graph of a large monorepo can take 8 to 15 minutes, and at 600 pull requests a month that is the difference between a rounding error and a visible line on the bill — plus 10 minutes added to every engineer's feedback loop. Past roughly 2 minutes per run, move the expensive checks to a merge-queue stage or to a scheduled run against trunk, and keep only the fast ones per pull request. The rule flips on duration, not on repository count.