One Report. Five Systems. One Number Must Survive.
A report leaves your product as one fact and crosses five billing decisions. See how to keep its identity intact until it becomes an invoice line.
Updated 2026-08-15
The same fact, all the way to the invoice.
Report 87 completed at 10:42. By the time it reaches the invoice, five systems have had a chance to rename it, count it twice, apply the wrong plan, or lose it completely.
Billing architecture is the discipline of letting that report travel without changing its identity. The product owns what happened. The commercial model owns what it means for the bill. Confuse those two, and every future pricing change becomes a data problem.
Give the fact one identity
Report 87 produces 3 kinds of information:
| Type | Example | Can it change later? |
|---|---|---|
| Product fact | Report completed at 10:42 | No |
| Commercial decision | First 100 reports are included | Yes, in a new version |
| Financial result | The report was included and added no charge | Not after invoice finalization |
Do not rewrite the old fact to match a new rule. Preserve the action as it happened and apply the plan and price version that were effective at that time.
Let the catalog change without rewriting history
The catalog connects the product, feature, plan, price, meter, and included limit. Every material change needs a new version.
When the Growth price increases, new customers begin on the new price. Noura’s subscription still references the terms she accepted, and every old invoice remains explainable.
An event needs the customer’s commercial context
An event alone does not know whether the customer is in a trial, on Growth, or upgraded in the middle of the period. The subscription supplies the plan, effective date, status, and next scheduled change.
Represent activation, upgrade, downgrade, renewal, and cancellation as dated state changes. A single is_paid field cannot tell that story.
“Can they?” and “how much?” are different questions
The entitlement answers: can this customer use the feature now?
The meter answers: how many successful actions happened in the period?
The price answers: what does that quantity do to the invoice?
Keeping those decisions separate lets you change a limit or price without rebuilding the feature, and roll out a feature gradually without changing what the customer bought.
Retries must move the fact, not copy it
Every event needs a stable identity, timestamp, customer, and unit. If delivery fails, send it again with the same identity. The retry delivers the same fact; it does not create another unit.
The meter then aggregates events inside the billing period and applies the price, allowance, and tiers. Preserve intermediate results so support can explain the amount without rebuilding the calculation elsewhere.
The invoice is where the story becomes permanent
At the end of the period, the invoice combines the subscription price, usage, discounts, tax, and adjustments. After finalization, do not silently rewrite its lines. A later change appears as an explicit adjustment or refund.
Payment comes next. A payment attempt settles the amount; it does not define it. That separation lets you retry collection or change providers without changing commercial history.
Test the moments that make numbers disagree
- The same event arrives twice;
- an event arrives after the period closes;
- the price changes mid-month;
- the customer upgrades and payment of the difference fails;
- a finalized invoice needs a correction;
- one meter fails without affecting other customers.
The architecture is ready when you can start with any amount and identify the event, subscription, price, and decision that produced it.
Tirdad provides these pieces as one system: catalog, subscriptions, entitlements, usage metering, usage units, invoicing, and collection. Your team stays focused on the part of the product that makes it different instead of building a billing runtime around it.
See the runtime in detail: read From Product Usage to an Invoice with Tirdad