Research note ยท October 2026
When a billing dry run agrees with the wrong invoice
A preview and a final invoice can agree because they share the same missing input. Agreement within one engine is not an independent check of the amount that should have been billed.
The reported failure
In Kill Bill issue #2291, the reporter describes catalog changes intended for existing subscriptions being lost when multiple changes align to one billing boundary. A later price disappears from the event set. The reporter says the invoice dry run repeated the incorrect final amount, and that one case came from a production client. Those are the reporter's observations, not a Nobulex production finding.
The same issue describes a second, distinct boundary: a catalog change effective later on a subscription's start day can be aligned back to an earlier instant on that day. The candidate then falls before the change and is discarded. The two mechanisms require separate fixes.
What we tested
We reproduced both cases in a local H2 test environment using the released Kill Bill 0.24.19 source. The added invoice regression failed against the original code and passed with each corresponding patch. The proposed fixes are PR #2320 for colliding catalog changes and PR #2321 for the same-day change. Both are open as this note is published.
These are test invoices, not customer payments. We could not run the current master build locally because its snapshot parent dependency was unavailable. The released-version results do not establish that current master CI passes.
A contrasting case: the amount alone is not enough
In an unrelated Lago report, a self-hosted user disputed the invoice period and issue date after extending a free trial. Another contributor reports reproducing the timeline: the charge of 2,884 cents matched six prorated days, while the displayed period began earlier and a late-day trial expiry shifted issuance to the next date. We have not run Lago or inspected that user's tenant. The reproduction belongs to its contributor, and the intended date semantics remain a product question.
This challenges an amount-only check. Before an independent comparison can call an invoice wrong, the operator must specify which fields are authoritative: amount, covered period, issue date, or some combination. We asked the reporter which mattered in their workflow; no answer is assumed here.
The control this suggests
The reported dry run and real invoice used the same billing logic. When that logic omitted an event, both results could agree and still miss the approved catalog price. A separate release check would start from the approved catalog versions, subscription effective instants, and target billing period, calculate the expected invoice for a small set of named scenarios, and compare those expectations with the engine's output.
This is a research hypothesis, not a deployed Nobulex feature. We have not shown that an outside team lacks such a check, would permit it in a release workflow, or would pay for it. Existing billing tests and Kill Bill's Aviate operations layer may already cover much of the need. The useful next question is where their checks end.
What would change our mind
- A billing owner shows an existing independent expected-invoice test that catches both reported paths before release.
- The mismatches are too rare or too cheap to justify another control.
- Independent replay cannot be made reliable across real catalog, tax, credit, and timing rules without becoming a second billing engine.
If you own a billing release process, we would value an async answer: what do you compare the dry run against when both the dry run and final invoice might share the same missing input? No customer data or credentials are needed to answer. Write to Nobulex.
For a team willing to test that question on one synthetic Kill Bill price change, we have a fixed-scope billing replay study offer. It is a proposed paid study, not an existing customer deployment.
Back to Nobulex →
