Skip to Content
GuidesInvoices

Invoices

A TxNod invoice is a request for a specific crypto amount, addressed to a pool address derived from your wallet’s xpub. Once created, the invoice transitions through a small set of states as the chain-watcher observes on-chain activity. The state machine is documented in the Webhook Event Types reference; this guide focuses on the single concept that most often surprises operators: reorg safety.

Reorg safety

A blockchain reorganization (reorg) happens when a temporarily-orphaned block, including its transactions, is replaced by a different block on the canonical chain. If the reorg replaces a block that contained a payment for one of your invoices, that payment effectively un-happens — until and unless the same transaction lands on the canonical chain at sufficient depth.

TxNod handles this by not transitioning an invoice to paid the instant a matching transaction is observed. Instead, the chain-watcher waits for a configurable number of confirmations — the finalization threshold — past the block that included the transaction. The default thresholds, sourced verbatim from CONFIRMATION_FLOORS in packages/shared/src/schemas/project-config.ts, are:

ChainDefault confirmations
BTC2
ETH12
TRON19
Cardano15
Polygon PoS128
BNB Smart Chain15

These are floors, not ceilings: per-project configuration can raise a threshold but cannot lower it below the default. The dashboard surfaces the active threshold on each invoice’s detail page so you can see exactly how many more confirmations are required before detected → paid.

If an invoice has already transitioned to paid and a deep reorg later orphans the confirming block, TxNod emits a single invoice.reverted event, resets the invoice to detected, and re-runs the wait-for-confirmations loop. If the same transaction (or a functionally equivalent replacement, e.g. an RBF replacement on Bitcoin) re-lands at sufficient depth, TxNod re-emits invoice.paid with a stable, deterministic event_id derived from (invoice_id, terminal_status) — so your consumer’s UNIQUE(event_id) dedupe naturally treats the re-emit as already-processed work.

The Polygon PoS threshold of 128 blocks is the highest in the table because that is the Heimdall checkpoint depth: Polygon PoS commits a bor-layer checkpoint to Ethereum every ~256 blocks; 128 is the halfway mark, which gives deep-reorg safety without waiting a full checkpoint cycle. BTC’s 2-block default reflects small-amount gateway practice (the six-block convention is conservative for small invoices); operators expecting larger payments should raise the per-project threshold.

Troubleshooting

Invoice stuck in detected

  1. Open the invoice detail in the dashboard. Read the confirmations count.
  2. If confirmations is below the finalization threshold for that coin (see the table above), the system is working correctly — wait.
  3. If confirmations is at or above the threshold but status has not transitioned, the chain-watcher may be lagging. Wait a few minutes; if the issue persists, file a support issue with the invoice id and the current confirmations value.