← FinOpsAid blog

Can I just get this monthly? Building a GitHub cost report an executive will read — FinOpsAid blog

Can I just get this monthly? Building a GitHub cost report an executive will read

"Send me this every month" sounds like the easiest request in the world, and it's where most cost programs quietly die. Here's what belongs in an executive GitHub spend report, what belongs in the other two reports nobody tells you to write, and why the manual rebuild always wins in the end.

You finally show someone the numbers. Spend by product, the teams driving it, the seats nobody's touched since February. It goes well — well enough that you get the sentence that sounds like success: this is great, can you send it to me every month?

That request is harder than it sounds, and not for the reason you'd expect. Producing the report once is a good afternoon. Producing it every month, at a consistent quality, through reorganisations and holidays and the month you're heads-down on something else, is a commitment most cost programs don't survive. The report that actually gets read is designed for that constraint from the start.

A report is a product, and it has exactly one user

The first mistake is writing one report for everybody. You end up with fourteen pages that the executive skims, the engineering lead finds too shallow, and finance can't reconcile — a document that serves its author's sense of thoroughness and nobody else's decision.

Before writing anything, answer two questions: who reads this, and what do they do differently because they read it? If there's no plausible decision on the other end, you're producing a newsletter. Newsletters are fine, but they should be honest about being optional, because a report with no decision attached teaches its recipients to stop opening it — and that habit generalises to the reports that do matter.

Three audiences, three different documents

In practice you need three, and they share a data layer rather than a format.

The executive report is one page. Total spend, the trend against prior periods, variance against budget or forecast, the top two or three things that moved it, one unit economic, and the savings currently identified. That's the whole thing. Its job is to answer "is this under control, and is anything about to surprise me?" in ninety seconds. Anything that doesn't serve that question belongs in a different document.

The engineering leadership report is about attribution. Spend by team and by repository, period over period, with the drivers named — the workflow that expanded, the runner label that changed, the seats assigned during onboarding. This is the one that produces action, because it lands next to the people who can act, which is the whole case for showback before chargeback.

The finance report is about reconciliation. What the invoice says, what your metering says, and a documented explanation of the gap. That gap is not a defect. AI credits are a usage signal, billing periods and your reporting periods rarely align perfectly, and some of your per-team figures are allocations. The reconciliation is the deliverable — finance doesn't need your numbers to match theirs, they need to understand precisely why they don't.

Three reporting audiences sharing one data layer The executive report is one page answering whether spend is under control. The engineering leadership report carries attribution by team and repository with named drivers. The finance report reconciles the invoice against metered figures and documents the gap. All three are generated from the same warehouse using the same definitions. EXECUTIVE One page. Ninety seconds. Total, and its trend Variance vs expectation Top drivers, as causes One unit economic Anything about to surprise me? ENGINEERING Attribution, not totals. Spend by team and repo Period over period The workflow that expanded The seats assigned in bulk What do we change on Monday? FINANCE Reconciliation. Invoice vs metered The gap, documented Modeled figures flagged Period boundaries stated Why don't these match? ONE WAREHOUSE · ONE SET OF DEFINITIONS · GENERATED ON A SCHEDULE A trend built on a denominator that shifts between months is not a trend.
Three documents, one pipeline. They differ in what they surface, never in how a number was computed — which is exactly what hand-assembly can't guarantee once the definitions live in someone's spreadsheet.

What actually earns space on the executive page

Ruthlessness here is the difference between a page that gets read and one that gets filed.

Include the total and its trend, because that's the question being asked. Include variance against expectation, because that's the question behind the question. Include the top drivers, expressed as causes rather than categories — "the platform team's nightly matrix expanded to five runtimes" beats "Actions increased 22%" every time, since only one of those two sentences suggests what to do. Include one unit economic, such as cost per active developer, so growth in the total is legible instead of alarming.

Leave out anything the reader can't act on and won't be asked about. Leave out the second decimal place. And leave out every chart that exists because it looked good rather than because it changed a mind.

The manual rebuild is what kills it

Here is the failure mode, and it's almost universal. The first report is hand-assembled from exports. So is the second. By the fourth, the person who built it has a folder of spreadsheets and a personal method, and the report has quietly become their side job. Then they take a fortnight off, or change teams, and the series stops. Nobody chases it, because a report that skipped a month has already lost the thing that made it valuable — comparability.

The insidious part is that manual reports also drift. The definition of "active developer" shifts slightly between months because it's being recomputed by hand. Trends built on a moving definition aren't trends. So the reporting layer has to be generated from the same pipeline every time, on a schedule, whether or not anybody remembers — and its definitions have to live in the pipeline rather than in someone's head.

Say what's modeled, in the report itself

A report is a durable artefact in a way a dashboard isn't. It gets forwarded, pasted into a board deck, quoted back to you eleven months later by someone who wasn't in the original conversation and has no idea which figures were allocations.

That's why the labelling has to travel with the number rather than sit in a methodology appendix nobody forwards. Per-repo Copilot cost, self-hosted runner cost, most per-person dollars: these are modeled, and the report should say so on the same line. Every report carries an as-of timestamp and the period boundaries it used. It costs you one line of text and buys you the ability to defend the document in a room you're not in.

Cadence, and the boring detail that ruins it

Align the reporting period to the close, not to the calendar's convenience. A monthly report generated on the 1st, before the invoice lands, will disagree with finance every single month, and you'll spend a year explaining the same gap.

Pick the date after the billing data is final, keep it fixed, and keep the period definition stable even when a shorter month makes the trend look bad. Reporting cadence is also the natural home for everything that didn't deserve an interrupt — the drift, the long tail, the low-severity signals that have no business in an alert channel.

Worth doing

FinOpsAid produces these on a schedule from the same nightly warehouse the dashboards read: Reports generates a consolidated executive payload with trend, drivers, unit economics, and identified savings, with modeled figures flagged as modeled and every period stamped with the sync it was built from — so the monthly report keeps arriving whether or not anyone remembers to build it.

Frequently asked questions

What should a monthly GitHub cost report contain?

Position, trajectory and accountability: current month with its change, year to date, projected year end, and budget against actual. Add one or two legible waste metrics trending over time — wasted seats and idle environments — because those falling is the clearest evidence the programme is working.

Why do monthly cost reports stop happening?

The manual rebuild. A report that takes a person half a day to assemble survives about three months of enthusiasm and then quietly stops. If it cannot be regenerated with the same numbers and no reassembly, it will not last, regardless of how good the first edition was.

Should a cost report say which numbers are estimates?

Yes, in the report itself rather than in a footnote nobody reads. The first time a stakeholder discovers that a figure they have been quoting was modeled, you lose the report — and every other number in it. Labelling costs a sentence and buys the document's credibility.

Want the monthly GitHub spend report without the monthly spreadsheet? Connect your GitHub org — read-only and free during beta — or explore the demo dashboard first.