waiaconnect

Documentation / Essential

Receive messages by webhook

You register an HTTPS endpoint (panel → Webhooks, or POST /webhook-endpoints) and Connect POSTs you a versioned envelope for every event. ⚠ Your endpoint must accept POST with a JSON body (n8n/Make/Zapier default their trigger to GET — switch it to POST). The envelope is not Meta's raw payload: if Meta changes their shape, your integration does not break. Signature headers: X-Connect-Signature-256, X-Connect-Timestamp, X-Connect-Delivery-Id (stable across retries → deduplicate on it), X-Connect-Event.

The envelope we POST to your endpoint

{
  "id": "evt_7f3a1b2c9d4e5f6a7b8c9d0e1f2a3b4c",
  "type": "message.received",
  "version": "1",
  "createdAt": "2026-08-06T00:31:22.461Z",
  "connection": {
    "id": "conn_4eede070e5a84d1590bdce2ea1d837bc",
    "phoneNumber": "+5493510000000",
    "externalId": "farmacia-lopez"
  },
  "sequence": 12345,
  "data": {
    "message": {
      "id": "wamid.HBgL…",
      "from": "5493511234567",
      "type": "text",
      "text": {
        "body": "hola"
      }
    },
    "contacts": [
      {
        "wa_id": "5493511234567",
        "profile": {
          "name": "Ana"
        }
      }
    ]
  }
}

Headers

HeaderWhat it is
X-Connect-EventThe event type (e.g. message.received) — branch on this.
X-Connect-Delivery-IdStable across retries → deduplicate on it.
X-Connect-TimestampUnix seconds; part of the HMAC. Reject deliveries older than ~5 min.
X-Connect-Signature-256sha256=HMAC(secret, timestamp + '.' + rawBody). Verify before trusting the body.
X-Connect-TokenOptional static header (if you enabled one) — your tool's native Header Auth checks it.

connection is ALWAYS an object, but its fields are null for account-wide events (usage.threshold_reached) and for webhook.test.

How to AUTHENTICATE the delivery (static header vs signature): see the 'Authenticate the webhook' module. Using n8n? The importable workflow is under Integrations.