Skip to main content

Why Use Webhooks?

ApproachLatencyComplexityUse Case
PollingSeconds to minutesSimpleLow-volume, non-critical
WebhooksSub-secondModerateReal-time updates, high-volume

Configure Webhooks

Configure in Hub: WebhooksAdd Webhook Endpoint URL: e.g., https://api.yourgame.com/webhooks/immutable Events: Mints, transfers, orders, trades

Webhook Payload

{
  "event_name": "imtbl_zkevm_mint_request_updated",
  "event_id": "evt_123abc",
  "timestamp": "2024-01-15T10:30:00Z",
  "data": {
    "contract_address": "0x...",
    "token_id": "123",
    "status": "succeeded"
  }
}

Verify Webhook Signatures

import crypto from 'crypto';

function verifyWebhookSignature(
  payload: string,
  signature: string,
  secret: string
): boolean {
  const expectedSignature = crypto
    .createHmac('sha256', secret)
    .update(payload)
    .digest('hex');
  
  return crypto.timingSafeEqual(
    Buffer.from(signature),
    Buffer.from(expectedSignature)
  );
}

// In your webhook handler
app.post('/webhooks/immutable', (req, res) => {
  const signature = req.headers['x-immutable-signature'];
  const isValid = verifyWebhookSignature(
    JSON.stringify(req.body),
    signature,
    process.env.WEBHOOK_SECRET
  );
  
  if (!isValid) {
    return res.status(401).send('Invalid signature');
  }
  
  // Process the webhook
  handleWebhookEvent(req.body);
  res.status(200).send('OK');
});

Retry Policy

Exponential backoff on errors:
AttemptDelay
1Immediate
21 minute
35 minutes
430 minutes
52 hours
After 5 failed attempts, view and retry in Hub.

Best Practices

Return a 200 response immediately, then process the event asynchronously. Webhook requests timeout after 30 seconds.
Use the event_id to deduplicate events. The same event may be delivered more than once.
Always verify the webhook signature. Use HTTPS for your endpoint.

Next Steps

Indexer API

Query blockchain data directly

Minting Events

Handle minting webhooks