The SDK uses an event-driven architecture. Subscribe to events to react to payment state changes, errors, and telemetry data.
Subscribing to Events
// Listen to an event
pos.on('payment.confirmed', (event) => {
console.log('Paid!', event.session.id);
});
// Listen once
pos.once('payment.created', (event) => {
console.log('Session started:', event.session.id);
});
// Unsubscribe
const handler = (event) => console.log(event);
pos.on('payment.failed', handler);
pos.off('payment.failed', handler);
Payment Events
These are the primary events you should handle in your integration.
payment.created
Fired when a payment session is opened and the deposit address is ready.
pos.on('payment.created', (event) => {
// event.session: POSSession — full session with address and QR code
// event.correlationId: string — unique ID for this payment flow
});
payment.received
Fired when crypto has been received on-chain but the fiat payout is still processing.
pos.on('payment.received', (event) => {
// event.sessionId: string
// event.correlationId: string
});
payment.confirmed
Fired when payout is complete. This is the signal to fulfill the order.
pos.on('payment.confirmed', (event) => {
// event.session: POSSession — includes final amounts, rate used
// event.correlationId: string
});
Always verify payment status from your backend API before fulfilling.
Use this event to trigger a server-side check, not to directly deliver goods.
payment.failed
Fired when payment processing fails.
pos.on('payment.failed', (event) => {
// event.sessionId: string
// event.reason: string — human-readable failure reason
// event.code: string — machine-readable error code
// event.correlationId: string
});
payment.expired
Fired when the payment session times out before crypto is received.
pos.on('payment.expired', (event) => {
// event.sessionId: string
// event.correlationId: string
});
payment.cancelled
Fired when the customer closes the checkout modal.
pos.on('payment.cancelled', (event) => {
// event.sessionId: string
// event.correlationId: string
});
payment.status_changed
Fired on every status transition during polling. Useful for updating UI state.
pos.on('payment.status_changed', (event) => {
// event.result: SessionStatusResult — { sessionId, status, polledAt }
// event.previousStatus: SessionStatus | null
// event.correlationId: string
});
SDK Lifecycle Events
sdk.initialized
Fired after pos.init() completes successfully.
pos.on('sdk.initialized', (event) => {
// event.merchantId: string
// event.sdkVersion: string
// event.timestamp: string
});
sdk.terminated
Fired after pos.terminate() completes.
pos.on('sdk.terminated', (event) => {
// event.reason: string
// event.timestamp: string
});
state.transition
Fired on every state machine transition. Useful for debugging.
pos.on('state.transition', (event) => {
// event.from: SDKState
// event.to: SDKState
// event.timestamp: string
// event.correlationId: string
});
Fraud Events
fraud.review_started
Fired when the fraud engine begins evaluating a payment.
pos.on('fraud.review_started', (event) => {
// event.sessionId: string
// event.signals: FraudSignal[] — detected fraud indicators
// event.correlationId: string
});
fraud.review_completed
Fired when the fraud evaluation finishes.
pos.on('fraud.review_completed', (event) => {
// event.sessionId: string
// event.score: number — 0-100 fraud score
// event.action: 'allow' | 'block' | 'review'
// event.correlationId: string
});
API & Infrastructure Events
These events are useful for debugging and observability.
api.request / api.response / api.error
pos.on('api.request', (event) => {
// event.method, event.url, event.correlationId, event.attempt
});
pos.on('api.response', (event) => {
// event.status, event.url, event.correlationId, event.durationMs
});
pos.on('api.error', (event) => {
// event.url, event.status, event.message, event.correlationId, event.attempt
});
circuit_breaker.opened / circuit_breaker.closed
Fired when the API client circuit breaker trips or recovers.
pos.on('circuit_breaker.opened', (event) => {
// event.service: string — which service tripped
// event.failureCount: number
});
pos.on('circuit_breaker.closed', (event) => {
// event.service: string
});
Session Status Values
The SessionStatus type represents where a payment is in its lifecycle:
| Status | Description |
|---|
pending | Session created, waiting for crypto |
paid | Crypto received on-chain |
payout_pending | Fiat payout is being processed |
paid_out | Fiat payout completed successfully |
payout_failed | Fiat payout failed |
expired | Session timed out |
cancelled | Session cancelled by customer or merchant |
refunded | Payment was refunded |
SDK States
The internal state machine tracks the SDK’s lifecycle:
| State | Description |
|---|
BOOTSTRAPPING | SDK is initializing |
INITIALIZED | init() completed, ready for use |
CONFIG_VALIDATED | Configuration has been validated |
PAYMENT_CREATING | Creating a payment session |
ADDRESS_GENERATED | Deposit address ready |
WAITING_FOR_PAYMENT | Polling for crypto arrival |
PAYMENT_RECEIVED | Crypto detected on-chain |
FRAUD_REVIEW | Fraud engine is evaluating |
CONFIRMED | Payment confirmed and payout complete |
FAILED | Payment failed |
EXPIRED | Session expired |
CANCELLED | Session cancelled |
TERMINATED | SDK shut down |
Check the current state at any time:
const state = pos.getState(); // e.g. 'INITIALIZED'