fix(api): revert deterministic retry billing id (free-scan on redelivery)

Merged
TO
3mo ago
+12-12

Follow-up to #3400. The deterministic pending:retry:<parent> billing reservation id it introduced has a realistic bug, so this reverts it to a unique random id.

The bug

Billing consumption is idempotent on sourceResourceId, and a refund creates a separate refund event while leaving the original consume event in place (billing-included-usage-refunds.ts). With a deterministic per-parent reservation id:

  1. A retry reserves (debits) pending:retry:<parent>.
  2. The Maced create fails transiently → we refund it (net zero, but the consume idempotency key remains).
  3. Standard webhook redelivery re-runs the retry → reserves the same id → billing sees the existing consume key → returns "consumed" without debiting → the scan runs for free.

This is the normal sequential retry-on-failure path, so it's realistic — a worse trade than the (unverified, concurrent-only) over-charge the deterministic id was meant to prevent.

Fix

Revert to a unique random reservation id per create call, so a redelivered retry re-debits correctly. Concurrent duplicate scans are still deduped by the Maced idempotency key (unchanged); the residual concurrent-only reservation over-charge requires Maced to deliver duplicate webhooks concurrently (unverified) and isn't worth reintroducing a realistic free-scan to close.

Testing

npx jest src/security-penetration-tests → 154 green, typecheck + prettier clean.


Summary by cubic

Reverts the retry billing reservation id to a unique random id to prevent free scans on webhook redelivery after a refunded failure. Concurrent duplicate scans are still deduped by the Maced idempotency key, and billing now re-debits on redelivery.

  • Bug Fixes
    • Always generate a unique pending:<uuid> sourceResourceId; remove pending:retry:<parent>.
    • Avoids idempotency skip when a refund leaves the original consume event in place.
    • Updated tests to expect a non-deterministic billing id while keeping the same Maced idempotency behavior.