Webhook System Overview
TokenCashFlow sends HTTP POST requests to your configured endpoint when payment and withdrawal events occur. Each delivery is signed so you can verify it came from TokenCashFlow.
How it works
Payment event occurs
│
▼
TokenCashFlow creates webhook_delivery_job record
│
▼
Webhook worker picks up job
│
▼
Signs payload with HMAC-SHA256
│
▼
HTTP POST to your endpoint (10s timeout)
│
┌───┴────────────────────┐
│ HTTP 2xx │ Non-2xx or timeout
▼ ▼
Mark success Mark failed → schedule retryConfiguration
Go to Client Portal → Dashboard → Webhooks and configure:
| Field | Description |
|---|---|
| URL | Your HTTPS endpoint. HTTP is not accepted. |
| Secret | Used to sign payloads. Store this securely alongside your API key. |
| Events | Which event types to receive. Leave as * for all, or select specific events. |
| Active | Toggle to temporarily pause delivery without deleting config. |
Payload structure
Every webhook has the same outer structure:
{
"event": "payment.completed",
"timestamp": "2026-05-16T12:05:00Z",
"data": { ... }
}| Field | Type | Description |
|---|---|---|
event | string | Event type identifier (see Events Reference) |
timestamp | ISO 8601 | UTC timestamp when the event was generated |
data | object | Event-specific payload |
Signature header
Every delivery includes:
X-TCF-Signature: sha256={hex_digest}The hex digest is HMAC-SHA256(raw_request_body, webhook_secret). See Signature Verification for implementation examples.
Always verify the signature before processing the event. Reject any delivery that fails verification.
Delivery guarantee
Webhooks are delivered at-least-once. In rare network-partition scenarios, a delivery may be retried even after your endpoint returned 2xx. Design your handler to be idempotent:
- Use
data.payment_id+event+timestampas a natural deduplication key - Store processed event IDs and skip re-processing if already handled
Viewing delivery history
In the Client Portal → Dashboard → Webhooks → Delivery History, you can see:
- Every delivery job (per event)
- Number of attempts
- HTTP status code from your endpoint
- Timestamp of each attempt
- Response body (first 500 characters)
You can also query delivery history via the API — see Webhooks API Reference.

