useCheckoutPreview shows what the customer owes today and what changes before anything is charged, and useCheckoutSession polls a hosted-form session until the PSP confirms. Both are scoped to the portal customer.
Every hook returns isLoading: boolean and error: Error | null (see Introduction); the sections below list each hook’s specific returns.
useCheckoutPreview
Returns a server-computed preview of a checkout action — amount due today, the upcoming schedule, credit impact, line items, and warnings — before anything is charged. It callsPOST /v1/checkout/sessions/preview with a discriminated input. Pass null to disable (e.g. while inputs are still being assembled). customerId is filled from context — callers omit it.
For plan-change previews, use
useSubscription(id).previewChange() instead — it returns a richer shape (proration, entitlement diffs, direction/timing).The action to preview, a discriminated union on
purpose. Pass null to hold the query inert.preview— theCheckoutPreviewResult, ornullwhile loading / when disabled. It extends the shared base shape with the per-purposedetailspayload:
Discriminated by
kind: charge_now (cents, currency), invoice_later (cents, netDays, estimatedDate), or no_charge.{ description, unitAmount, quantity, subtotal, muted? } rows.Money breakdown in minor units.
Optional
{ date, amountCents? } for the next charge.Optional wallet delta —
{ currencyName, denomination, minorUnitScale, currentBalance, delta, afterBalance, … }.{ code, params? } — e.g. trial_requires_payment_method, customer_has_no_payment_method.Echoes the purpose;
details is the per-purpose payload (e.g. details.subscription, details.creditTopup).refresh()—() => Promise<void>— refetch the preview (e.g. after the customer edits the amount).
useCheckoutSession
PollsGET /v1/checkout/sessions/:id/status and reports when a hosted-form payment resolves. Use it to await the result of a requires_form SettleOutcome — after the Elements form submits, the webhook completer flips the session to completed once the PSP confirms. Polling is tiered: ~1s for the first 30s (hot phase), then ~5s, then it stops and synthesizes expired at maxWaitMs.
Parameters
The session to poll. Pass
null to leave the hook idle (e.g. before the form step is reached). Changing the id resets the timeout.Gate polling without unmounting the hook. Set
false to hold the query inert (e.g. before the modal advances to its confirming step).Wall-clock cap on the pending window. After this elapses the hook stops polling and surfaces
status: 'expired' even if the server row is still pending.status—'idle' | 'pending' | 'completed' | 'expired':'idle'— nocheckoutSessionId, orenabledisfalse.'pending'— polling; defaults to this until the first fetch resolves.'completed'— the PSP confirmed and the session row finalized.'expired'— terminal server status, or the client-sidemaxWaitMstimeout fired.
data— theCheckoutSessionStatusrow, ornullbefore the first response:{ id, status, completedAt, subscriptionId, invoiceId }.
See also
Catalog & pricing
The plans and packages a checkout starts from.
Settlement model
Every
SettleOutcome kind and its callback, including requires_form.Credits & wallets
Top-up and package purchases that feed the preview.