What a Contract Audit Export Actually Contains
Most procurement systems (Coupa, Ariba, or a homegrown tracker) export contract data as a single flat file. That file contains at least 3 logically distinct datasets, and treating them as one is how models break.
Contracts are the approved SOW records: vendor name, contract value, start/end date, department, cost center, and rate type (T&M, fixed fee, retainer). This is your budget denominator.
Amendments capture post-signature scope changes. A contractor approved at $85K with 2 amendments totaling $34K has a true approved value of $119K. Miss amendments and you'll flag false overbills on roughly 20-30% of active vendors — every procurement team has this problem to some degree.
Invoices are the billing records: invoice date, amount, payment status, and the contract ID linking them back to the SOW. This is your actuals numerator.
Split these across 3 tabs immediately. The single-tab approach works for 20 contracts and breaks at 150.
The Sheets Architecture
| Tab | Purpose | Key columns |
|---|---|---|
Contracts | One row per SOW | ContractID, Vendor, Department, ApprovedValue, StartDate, EndDate, RateType, Status |
Amendments | One row per amendment | AmendmentID, ContractID, AmendmentValue, ApprovalDate, Department |
Invoices | One row per invoice | InvoiceID, ContractID, Vendor, InvoiceDate, InvoiceAmount, Hours, PaymentStatus |
RateCard | Approved rates by vendor/role | Vendor, Role, ApprovedRate |
Summary | All analysis | Everything calculated, nothing manually entered |
The Summary tab is the only tab your CFO ever sees. Every number there should trace back to one of the source tabs via formula.
The Formulas That Tie It Together
Total approved value per department (contracts plus amendments):
=SUMIFS(Contracts!C:C, Contracts!D:D, Summary!$A2)
+ SUMIFS(Amendments!C:C, Amendments!D:D, Summary!$A2)
Column C is ApprovedValue, column D is Department. This gives you the true committed budget inclusive of all amendments — the denominator that belongs in your utilization metrics.
YTD invoiced by department, anchored to your Assumptions tab:
=SUMIFS(Invoices!E:E,
Invoices!G:G, Summary!$A2,
Invoices!D:D, ">=" & DATE(Assumptions!$B$1, 1, 1),
Invoices!D:D, "<=" & TODAY())
Column G carries the Department field (populated via VLOOKUP from Contracts on import). Changing the year in Assumptions!$B$1 refreshes every YTD formula in the model.
SOW utilization rate per contract:
=IFERROR(
SUMIFS(Invoices!E:E, Invoices!B:B, Contracts!A2) /
(Contracts!C2 +
SUMIFS(Amendments!C:C, Amendments!B:B, Contracts!A2)),
"No Invoices")
The IFERROR handles new contracts with no invoices yet — without it you get a wall of #DIV/0! errors that make the model look broken during quarterly close.
Flagging Overbills
The overbill check is a helper column on your Contracts tab:
=IF(
SUMIFS(Invoices!E:E, Invoices!B:B, Contracts!A2) >
(Contracts!C2 + SUMIFS(Amendments!C:C, Amendments!B:B, Contracts!A2)),
"OVER",
"OK")
Conditional format "OVER" red. In a company with $3.4M in active contractor SOW value across roughly 120 vendors, you'll typically find 10-15% of contracts flagged — and about half of those have a legitimate amendment that simply wasn't entered. The flag's job is to create the conversation, not to assign blame.
Rate Card Compliance
If your company runs negotiated rate cards, you can validate every T&M invoice against approved rates. The formula checks the variance between actual billing rate (amount ÷ hours) and the approved rate for that vendor and role:
=IFERROR(
Invoices!E2 / Invoices!F2 -
INDEX(RateCard!$C:$C,
MATCH(Invoices!C2 & Invoices!H2,
RateCard!$A:$A & RateCard!$B:$B, 0)),
"Rate Not Found")
This is an array-style INDEX/MATCH — concatenating Vendor + Role to find the right rate card row — entered with Ctrl+Shift+Enter in older versions of Sheets, or wrapped in ARRAYFORMULA for a column-wide version. A $10/hr rate variance on a contractor billing 40 hours/week over 6 months is $10,400 per engagement. Across 20 active T&M contracts, rate card drift compounds fast.
The Board Pack View
The quarterly board pack needs one number per department: remaining available budget, which ties contracts, amendments, and invoices in a single formula:
=SUMIFS(Contracts!C:C, Contracts!D:D, 'Board Summary'!$A2)
+ SUMIFS(Amendments!C:C, Amendments!D:D, 'Board Summary'!$A2)
- SUMIFS(Invoices!E:E, Invoices!G:G, 'Board Summary'!$A2)
That formula reaches across 3 tabs in a single cell. Per Google's Sheets documentation, SUMIFS across separate tabs performs without notable lag for datasets up to roughly 10 million cells total — your contractor model won't get close to that limit.
For a $12M OpEx company with freelance spend running at 8% of total operating costs, the breakdown at quarter-end typically looks like: Engineering $342K invoiced against $410K approved, Marketing $187K against $240K, G&A $94K against $110K. Those numbers need to reconcile to your P&L contractor line before the board pack goes out. The formula model above makes that reconciliation a 5-minute check rather than a 2-hour exercise.
Build Committed Exposure Before Invoices Arrive
Most analysts build freelance spend analysis backward: they start with invoice data and reconcile to SOW after the fact. The more useful frame is committed exposure — the forward-looking budget obligation from all active, unexpired contracts, before invoices land.
Committed exposure drives your contractor accrual at quarter end and belongs in your quarterly forecast:
=SUMIFS(Contracts!C:C,
Contracts!D:D, Summary!$A2,
Contracts!F:F, "Active",
Contracts!G:G, ">=" & TODAY())
+ SUMIFS(Amendments!C:C,
Amendments!D:D, Summary!$A2)
- SUMIFS(Invoices!E:E,
Invoices!G:G, Summary!$A2)
Column F is Status, column G is EndDate. If you have $840K in active T&M contracts with an average of 45 days remaining and contractors billing roughly $4K/week each, you have about $285K in remaining exposure. That number belongs in your cash flow forecast, not just in a SOW tracker nobody reads.
According to SHRM's 2024 workforce benchmarking data, contingent worker engagements represent 15-25% of total workforce hours at most mid-size companies — but contract audit processes are typically far less mature than employee headcount processes. Which is exactly why the spend data ends up in a quarterly export nobody analyzes.
The Data Pipeline Problem
The model above works. The data pipeline is where it usually falls apart.
Contract audit reports come out of procurement on a monthly or weekly cadence. Invoice data comes from AP, in a different format, on a different schedule. The rate card lives in a file someone last updated 18 months ago. You can build the most elegant formula architecture and it's still wrong if the source tabs are 3 weeks stale.
Apps Script can automate the import — a triggered function that watches a Drive folder for new export files and refreshes the source tabs. The maintenance burden is real though: procurement system format changes are common, and a broken import script at quarter close is a bad time.
ModelMonkey connects directly to the underlying data sources and keeps your Sheets tabs current without script maintenance. For a monthly contractor close where timing matters, that's where the actual time savings lives.
Try ModelMonkey free for 14 days — it works in both Google Sheets and Excel.