Webhook Events

Laskad supports both inbound webhooks (sent by partners) and outbound webhooks (dispatched by Laskad to partner servers when P2P Escrow status changes).

Signature Verification

Outbound webhooks dispatched by Laskad include an X-Laskad-Signature header. Verify the signature by calculating HMAC-SHA256 over the raw JSON payload using your webhook secret:

// Verification Example (Node.js)
const crypto = require('crypto');

function verifyLaskadSignature(rawBody, signatureHeader, secret) {
  const expectedSignature = 'sha256=' + crypto
    .createHmac('sha256', secret)
    .update(rawBody)
    .digest('hex');

  return crypto.timingSafeEqual(
    Buffer.from(signatureHeader),
    Buffer.from(expectedSignature)
  );
}

Headers included on every outbound request: X-Laskad-Event, X-Laskad-Signature, X-Laskad-Timestamp.


P2P Escrow Outbound Webhooks

Dispatched automatically to the partner's webhookUrl whenever an escrow transaction progresses through its lifecycle.

EVENTescrow.created

Dispatched immediately when a P2P Escrow transaction is initialized and Virtual Account details are issued.

Payload

{
  "event": "escrow.created",
  "timestamp": "2026-09-12T09:40:00.000Z",
  "data": {
    "success": true,
    "escrowId": "f81d4fae-7dec-11d0-a765-00a0c91e6bf6",
    "status": "AWAITING_FUNDING",
    "groupJid": "12036398495038290@g.us",
    "inviteLink": "https://chat.whatsapp.com/ExAmPlELiNk123",
    "virtualAccount": {
      "accountNumber": "9940123456",
      "bankName": "Wema Bank / Lint",
      "expectedAmount": 150000
    }
  }
}
EVENTescrow.funded

Dispatched when buyer's bank deposit is received and confirmed in Laskad Escrow.

Payload

{
  "event": "escrow.funded",
  "timestamp": "2026-09-12T09:42:00.000Z",
  "data": {
    "escrowId": "f81d4fae-7dec-11d0-a765-00a0c91e6bf6",
    "status": "FUNDED",
    "amountFunded": 150000,
    "totalAmount": 150000,
    "groupJid": "12036398495038290@g.us"
  }
}
EVENTescrow.poll_active

Dispatched when the release approval poll is activated in the WhatsApp group.

Payload

{
  "event": "escrow.poll_active",
  "timestamp": "2026-09-12T09:43:00.000Z",
  "data": {
    "escrowId": "f81d4fae-7dec-11d0-a765-00a0c91e6bf6",
    "status": "POLL_ACTIVE",
    "pollMessageId": "3EB01234567890ABCDEF",
    "groupJid": "12036398495038290@g.us"
  }
}
EVENTescrow.completed

Dispatched when buyer approves payout release and funds are disbursed to Seller & Partner.

Payload

{
  "event": "escrow.completed",
  "timestamp": "2026-09-12T09:45:00.000Z",
  "data": {
    "escrowId": "f81d4fae-7dec-11d0-a765-00a0c91e6bf6",
    "status": "COMPLETED",
    "sellerPayoutAmount": 145500,
    "partnerCommission": 2250,
    "sellerAccountNumber": "0123456789"
  }
}
EVENTescrow.disputed

Dispatched when an escrow session is flagged as DISPUTED manually or via WhatsApp poll hold vote.

Payload

{
  "event": "escrow.disputed",
  "timestamp": "2026-09-12T09:46:00.000Z",
  "data": {
    "escrowId": "f81d4fae-7dec-11d0-a765-00a0c91e6bf6",
    "status": "DISPUTED",
    "reason": "Buyer reported damaged items",
    "groupJid": "12036398495038290@g.us"
  }
}

Inbound Webhooks (CBrilliance)

Inbound webhook events sent to Laskad via POST requests to https://api.laskad.app/webhooks/cbrilliance.

EVENTwithdrawal.completed

Sent by CBrilliance once a withdrawal has been transferred to the Laskad virtual account. Upon receipt, Laskad re-credits the group's escrow balance and sends a WhatsApp confirmation to the group.

Payload

{
  "type": "withdrawal.completed",
  "data": {
    "reference": "LSK-WD-1717228800000",
    "group_id": "cbr_abc123",
    "amount": 105000,
    "currency": "NGN",
    "timestamp": "2025-07-01T11:30:00Z"
  }
}
EVENTpayment.confirmed

Informational event sent by CBrilliance to acknowledge receipt of a Laskad settlement transfer.

Payload

{
  "type": "payment.confirmed",
  "data": {
    "reference": "LSK-STL-1717228800000",
    "group_id": "cbr_abc123",
    "amount": 100000,
    "currency": "NGN",
    "timestamp": "2025-06-01T09:15:00Z"
  }
}