Overview
Webhooks allow your application to receive real-time notifications when events occur in Superbank. Instead of polling the API, Superbank pushes events to your endpoint.
How Webhooks Work
- An event occurs (e.g., payment completed)
- Superbank sends a POST request to your webhook URL
- Your application processes the event
- Return
200 OK to acknowledge receipt
Setting Up Webhooks
Create a Webhook Endpoint
curl -X POST https://api-sandbox.superbank.com/v1/webhooks \
-H "X-Api-Key: your-api-key" \
-H "Content-Type: application/json" \
-d '{
"url": "https://your-app.com/webhooks/superbank",
"events": ["payment.completed", "payment.failed"]
}'
Response
{
"id": "wh_abc123",
"url": "https://your-app.com/webhooks/superbank",
"events": ["payment.completed", "payment.failed"],
"secret": "whsec_xyz789...",
"status": "ACTIVE",
"created_at": "2024-01-15T10:00:00Z"
}
Store the secret securely - it’s only shown once and is required for signature verification.
Event Types
Payment Events
| Event | Description |
|---|
payment.created | Payment was created |
payment.processing | Payment transfer started |
payment.completed | Payment successfully completed |
payment.failed | Payment failed |
payment.expired | Payment expired before notification |
Account Events
| Event | Description |
|---|
account.balance.low | Account balance dropped below threshold |
Webhook Payload
All webhooks follow this structure:
{
"id": "evt_abc123",
"type": "payment.completed",
"created_at": "2024-01-15T10:05:30Z",
"data": {
"id": "pay_xyz789",
"type": "LIQUIDITY",
"status": "COMPLETED",
"amount": 100.00,
"currency_code": "USDC",
"chain": "SOLANA",
"destination_wallet": "7xKXtg2CW87d97TXJSDpbD5jBkheTqA83TZRuJosgAsU",
"transaction_hash": "5wHu1qwD7q4..."
}
}
| Field | Description |
|---|
id | Unique event identifier |
type | Event type |
created_at | When the event occurred |
data | Event-specific payload |
Signature Verification
Every webhook includes a signature header for verification. Always verify signatures to ensure the webhook came from Superbank.
X-Superbank-Signature: t=1705312530,v1=5d4c...
The header contains:
t: Timestamp when the webhook was sent
v1: HMAC-SHA256 signature
Verification Process
import crypto from 'crypto';
function verifyWebhook(payload, signature, secret) {
const parts = signature.split(',');
const timestamp = parts[0].split('=')[1];
const receivedSig = parts[1].split('=')[1];
// Compute expected signature
const signedPayload = `${timestamp}.${payload}`;
const expectedSig = crypto
.createHmac('sha256', secret)
.update(signedPayload)
.digest('hex');
// Compare signatures
if (!crypto.timingSafeEqual(
Buffer.from(receivedSig),
Buffer.from(expectedSig)
)) {
throw new Error('Invalid signature');
}
return true;
}
Handling Webhooks
Best Practices
- Return 200 quickly: Process asynchronously if needed
- Verify signatures: Always validate webhook authenticity
- Handle duplicates: Use event IDs for idempotency
- Process in order: Events may arrive out of order
Example Handler
app.post('/webhooks/superbank', express.raw({ type: 'application/json' }), (req, res) => {
const signature = req.headers['x-superbank-signature'];
const payload = req.body.toString();
try {
verifyWebhook(payload, signature, process.env.WEBHOOK_SECRET);
} catch (err) {
return res.status(400).send('Invalid signature');
}
const event = JSON.parse(payload);
// Handle event asynchronously
handleEvent(event).catch(console.error);
// Acknowledge receipt immediately
res.status(200).send('OK');
});
async function handleEvent(event) {
switch (event.type) {
case 'payment.completed':
await processCompletedPayment(event.data);
break;
case 'payment.failed':
await handleFailedPayment(event.data);
break;
}
}
Retry Policy
If your endpoint doesn’t respond with 2xx, Superbank retries with exponential backoff:
| Attempt | Delay |
|---|
| 1 | Immediate |
| 2 | 1 minute |
| 3 | 5 minutes |
| 4 | 15 minutes |
| 5 | 1 hour |
| 6 | 1 day |
| 7 | 2 days |
| 8 | 4 days |
| 9 | 1 week |
| 10 | 2 weeks |
After 10 failed attempts, the webhook is marked as failed. Check the Dashboard for failed deliveries.
Managing Webhooks
List Endpoints
curl https://api-sandbox.superbank.com/v1/webhooks \
-H "X-Api-Key: your-api-key"
Update Endpoint
curl -X PATCH https://api-sandbox.superbank.com/v1/webhooks/wh_abc123 \
-H "X-Api-Key: your-api-key" \
-H "Content-Type: application/json" \
-d '{
"events": ["payment.completed", "payment.failed", "payment.expired"]
}'
Delete Endpoint
curl -X DELETE https://api-sandbox.superbank.com/v1/webhooks/wh_abc123 \
-H "X-Api-Key: your-api-key"
Testing Webhooks
Local Development
Use Svix Play to test webhooks during development. It provides a unique URL to receive and inspect webhook payloads without exposing your local server.
- Go to play.svix.com
- Copy your unique webhook URL
- Use it as your webhook endpoint in Superbank
- View incoming webhooks in real-time
Test Events
From the Dashboard, you can send test events to verify your endpoint is working correctly.
Next Steps