Webhooks Overview

The business webhook system delivers real-time event notifications to your configured endpoint. This page explains the delivery model, verification, and operational expectations shared by all webhook types.

Supported Events

Delivery Model

  1. An event occurs in the platform.
  2. A webhook job is queued for your configured webhook URL.
  3. The platform sends a POST request with a signed JSON payload.
  4. Your server verifies the signature and processes the event.
  5. If your endpoint does not return 200 OK, delivery is retried.

Headers

Every webhook request includes these headers:

  • Content-Type: application/json
  • User-Agent: Transfaar-Business-API/1.0
  • X-Transfaar-Signature: <hmac_signature>

Signature Verification

All webhooks are signed with HMAC-SHA256 using the secret associated with your business API key.

To verify a webhook correctly:

  1. Read the raw request body before JSON parsing.
  2. Compute HMAC-SHA256 over the raw body bytes using your stored secret key.
  3. Hex-encode the digest.
  4. Compare your computed digest with X-Transfaar-Signature using a constant-time comparison.

If the signatures do not match, reject the webhook and do not process the payload.

Python Example

python
import hmacimport hashlib
def verify_webhook_signature(body: bytes, signature: str, secret_key: str) -> bool:    expected_signature = hmac.new(        secret_key.encode('utf-8'),        body,        hashlib.sha256    ).hexdigest()
    return hmac.compare_digest(expected_signature, signature.lower())

Node.js Example

javascript
const crypto = require('crypto');
function verifyWebhookSignature(body, signature, secretKey) {  const expectedSignature = crypto    .createHmac('sha256', secretKey)    .update(body)    .digest('hex');
  const normalizedExpected = expectedSignature.toLowerCase();  const normalizedReceived = signature.toLowerCase();
  if (normalizedExpected.length !== normalizedReceived.length) {    return false;  }
  return crypto.timingSafeEqual(    Buffer.from(normalizedExpected, 'utf8'),    Buffer.from(normalizedReceived, 'utf8')  );}

Use raw-body middleware such as express.raw() for webhook routes. If you parse JSON first, signature verification can fail because the raw bytes have changed.

Retries And Delivery Semantics

Webhook delivery is asynchronous and non-blocking.

  • Delivery jobs are queued in the background.
  • Retries use exponential backoff.
  • Retries happen when your endpoint does not return 200 OK, including network failures and non-200 responses.
  • Failed deliveries are logged for inspection.

Best Practices

  1. Respond quickly with 200 OK after validation.
  2. Process heavy downstream work asynchronously in your own system.
  3. Make handlers idempotent because retries can happen.
  4. Log received events for support and reconciliation.
  5. Reject invalid signatures immediately.

Configuration

To receive webhooks, you must:

  1. Create a business API key through the business API key management endpoints
  2. Configure a webhook URL when creating or updating your API key
  3. Ensure your webhook endpoint is publicly accessible and can accept POST requests
  4. Implement webhook signature verification in your endpoint

Testing

Use the mock and sandbox tooling in your non-production environment to validate:

  1. signature verification
  2. retry handling
  3. idempotent processing
  4. event-specific payload handling

Related Pages