---
url: >-
  https://docs.corbitaltech.dev/products/whatsmark-saas/integrations/whatsapp-webhook-format-reference.md
description: >-
  Complete technical reference for WhatsApp webhook payload structure, event
  types, and data formats in WhatsMarkSaaS.
---

# WhatsApp Webhook Format Reference

Complete technical reference for WhatsApp webhook payloads forwarded by WhatsMarkSaaS to external endpoints like N8N, Zapier, and Make.com.

## Overview

This document provides the complete specification for WhatsApp webhook payloads in N8N format. All webhooks follow a consistent structure regardless of event type.

::: info Audience
This reference is for developers building custom integrations. If you're using N8N, Zapier, or Make.com, see the [WhatsApp Webhook Forwarding Guide](./whatsapp-webhook-forwarding.md) instead.
:::

## Base Payload Structure

All WhatsApp webhooks follow this standard structure:

```typescript
interface WhatsAppWebhookPayload {
  event: EventObject;
  tenant: TenantObject;
  data: DataObject;
  whatsapp: WhatsAppObject;
  metadata: MetadataObject;
}
```

### Complete Schema

```json
{
  "event": {
    "id": "string",              // Format: evt_{timestamp}_{random}
    "type": "string",            // Event type (see Event Types section)
    "timestamp": "string",       // ISO 8601 datetime
    "version": "string"          // Format version (currently "1.0")
  },
  "tenant": {
    "id": number,               // Tenant ID
    "name": "string"            // Tenant/company name
  },
  "data": {
    "resource": {
      "type": "string",         // Resource type: message, status, account, etc.
      "id": "string|null",      // Resource identifier (message ID, etc.)
      "attributes": object      // Resource-specific attributes
    },
    "relationships": object     // Related entities (contact, metadata, etc.)
  },
  "whatsapp": {
    "original_payload": object  // Complete original WhatsApp webhook
  },
  "metadata": {
    "source": "whatsapp_webhook_forward",
    "environment": "string",    // production, staging, etc.
    "request_id": "string"      // UUID for request tracing
  }
}
```

## Event Object

Contains event metadata and identification.

```typescript
interface EventObject {
  id: string; // Unique event identifier
  type: string; // Event type (see Event Types)
  timestamp: string; // ISO 8601 timestamp
  version: string; // Payload format version
}
```

### Event ID Format

```
evt_{unix_timestamp}_{random_string}

Example: evt_1767263928_7KGQvXqbFF
```

### Event Types

All possible event types:

```typescript
type WhatsAppEventType =
  // Message Events
  | 'whatsapp.message.received'
  | 'whatsapp.message.sent'
  | 'whatsapp.message.delivered'
  | 'whatsapp.message.read'
  | 'whatsapp.message.failed'

  // Status Events
  | 'whatsapp.status.updated'

  // Account Events
  | 'whatsapp.account.alert'
  | 'whatsapp.account.review_updated'
  | 'whatsapp.account.updated'

  // Business Events
  | 'whatsapp.business.capability_updated'
  | 'whatsapp.business.status_updated'

  // Template Events
  | 'whatsapp.template.status_updated'
  | 'whatsapp.template.quality_updated'

  // Phone Events
  | 'whatsapp.phone.quality_updated'
  | 'whatsapp.phone.name_updated'

  // Other Events
  | 'whatsapp.call.received'
  | 'whatsapp.flow.event';
```

## Tenant Object

Multi-tenancy context information.

```typescript
interface TenantObject {
  id: number; // Tenant identifier
  name: string; // Tenant/company name
}
```

**Example:**

```json
{
  "id": 3,
  "name": "Acme Corporation"
}
```

## Data Object

Contains the actual event data and relationships.

```typescript
interface DataObject {
  resource: ResourceObject;
  relationships: RelationshipsObject;
}
```

### Resource Object

```typescript
interface ResourceObject {
  type: string; // Resource type
  id: string | null; // Resource identifier
  attributes: object; // Resource-specific data
}
```

### Relationships Object

Related entities vary by resource type. Common relationships:

```typescript
interface RelationshipsObject {
  contact?: ContactRelationship;
  metadata?: MetadataRelationship;
  [key: string]: any;
}
```

## WhatsApp Object

Contains the complete original WhatsApp webhook payload.

```typescript
interface WhatsAppObject {
  original_payload: {
    object: string;
    entry: Array<{
      id: string;
      changes: Array<{
        value: object;
        field: string;
      }>;
    }>;
  };
}
```

## Metadata Object

Request tracking and environment information.

```typescript
interface MetadataObject {
  source: 'whatsapp_webhook_forward';
  environment: string; // production, staging, development
  request_id: string; // UUID for tracing
}
```

## Event Type Details

### Message Events

#### whatsapp.message.received

Incoming message from customer.

**Payload Example:**

```json
{
  "event": {
    "id": "evt_1767263928_abc123",
    "type": "whatsapp.message.received",
    "timestamp": "2026-01-01T10:38:48+00:00",
    "version": "1.0"
  },
  "tenant": {
    "id": 3,
    "name": "Acme Corp"
  },
  "data": {
    "resource": {
      "type": "message",
      "id": "wamid.HBgMOTE5OTI1MTE5Mjg0FQIAEhgWM0VCMDE1NDRCMTFBMDQ1RTlFM0NFMwA=",
      "attributes": {
        "message_id": "wamid.HBgMOTE5OTI1MTE5Mjg0FQIAEhgWM0VCMDE1NDRCMTFBMDQ1RTlFM0NFMwA=",
        "from": "919876543210",
        "timestamp": "1767263926",
        "type": "text",
        "text": "Hello, I need help!",
        "context": null
      }
    },
    "relationships": {
      "contact": {
        "wa_id": "919876543210",
        "name": "John Doe"
      },
      "metadata": {
        "phone_number_id": "339141689277134",
        "display_phone_number": "919428735270"
      }
    }
  },
  "whatsapp": {
    "original_payload": {
      /* Full WhatsApp payload */
    }
  },
  "metadata": {
    "source": "whatsapp_webhook_forward",
    "environment": "production",
    "request_id": "595bbcf8-93bf-418b-8209-3343c76ad852"
  }
}
```

**Message Types:**

* `text` - Plain text message
* `image` - Image with optional caption
* `video` - Video with optional caption
* `audio` - Audio/voice message
* `document` - Document/file
* `location` - Location coordinates
* `contacts` - Contact card
* `sticker` - Sticker
* `interactive` - Button/list responses
* `button` - Quick reply button
* `order` - Order message

\*\*Text Message Attributes:

```typescript
{
  message_id: string;
  from: string;           // Phone number with country code
  timestamp: string;      // Unix timestamp
  type: "text";
  text: string;          // Message text
  context: {             // Reply context (if replying)
    from: string;
    id: string;
  } | null;
}
```

**Image Message Attributes:**

```typescript
{
  message_id: string;
  from: string;
  timestamp: string;
  type: "image";
  image: {
    id: string;         // Media ID
    mime_type: string;
    sha256: string;
    caption?: string;
  };
  context: object | null;
}
```

**Document Message Attributes:**

```typescript
{
  message_id: string;
  from: string;
  timestamp: string;
  type: "document";
  document: {
    id: string;
    filename: string;
    mime_type: string;
    sha256: string;
    caption?: string;
  };
  context: object | null;
}
```

**Location Message Attributes:**

```typescript
{
  message_id: string;
  from: string;
  timestamp: string;
  type: "location";
  location: {
    latitude: number;
    longitude: number;
    name?: string;
    address?: string;
  };
  context: object | null;
}
```

#### whatsapp.message.sent

Message sent by your business (echo event).

**Payload Structure:**
Same as `message.received` but triggered when your business sends a message.

**Note:** The `from` field will be your business phone number.

#### whatsapp.message.delivered

Message delivered to customer's device.

**Payload Example:**

```json
{
  "event": {
    "type": "whatsapp.message.delivered",
    "timestamp": "2026-01-01T10:39:00+00:00"
  },
  "data": {
    "resource": {
      "type": "status",
      "id": "wamid.xxx",
      "attributes": {
        "status": "delivered",
        "timestamp": "1767264000",
        "recipient_id": "919876543210",
        "conversation": {
          "id": "conv_id",
          "origin": {
            "type": "user_initiated"
          }
        }
      }
    }
  }
}
```

**Status Values:**

* `sent` - Message sent from your server
* `delivered` - Delivered to customer's device
* `read` - Customer read the message
* `failed` - Delivery failed

#### whatsapp.message.read

Customer read your message (blue checkmarks).

**Payload Structure:**
Similar to `message.delivered` with `status: "read"`.

#### whatsapp.message.failed

Message delivery failed.

**Payload Example:**

```json
{
  "event": {
    "type": "whatsapp.message.failed"
  },
  "data": {
    "resource": {
      "type": "status",
      "attributes": {
        "status": "failed",
        "timestamp": "1767264000",
        "recipient_id": "919876543210",
        "errors": [
          {
            "code": 131047,
            "title": "Re-engagement message",
            "message": "Re-engagement message is outside the customer service window."
          }
        ]
      }
    }
  }
}
```

### Template Events

#### whatsapp.template.status_updated

Message template approval status changed.

**Payload Example:**

```json
{
  "event": {
    "type": "whatsapp.template.status_updated"
  },
  "data": {
    "resource": {
      "type": "template",
      "id": null,
      "attributes": {
        "event": "APPROVED",
        "message_template_id": "1234567890",
        "message_template_name": "welcome_message",
        "message_template_language": "en",
        "reason": null
      }
    }
  }
}
```

**Status Values:**

* `APPROVED` - Template approved and active
* `REJECTED` - Template rejected
* `PENDING` - Under review
* `PAUSED` - Template paused
* `DISABLED` - Template disabled

**Rejection Reasons:**
When status is `REJECTED`, `reason` field contains explanation.

#### whatsapp.template.quality_updated

Template quality score changed.

**Payload Example:**

```json
{
  "event": {
    "type": "whatsapp.template.quality_updated"
  },
  "data": {
    "resource": {
      "type": "template_quality",
      "attributes": {
        "message_template_id": "1234567890",
        "message_template_name": "welcome_message",
        "message_template_language": "en",
        "quality_score": "GREEN",
        "previous_quality_score": "YELLOW"
      }
    }
  }
}
```

**Quality Scores:**

* `GREEN` - High quality
* `YELLOW` - Medium quality
* `RED` - Low quality (at risk)
* `UNKNOWN` - Not enough data

### Account Events

#### whatsapp.account.alert

Account alert or warning.

**Payload Example:**

```json
{
  "event": {
    "type": "whatsapp.account.alert"
  },
  "data": {
    "resource": {
      "type": "account_alert",
      "attributes": {
        "alert_type": "ACCOUNT_UPDATE",
        "description": "Your phone number quality is low",
        "severity": "WARNING"
      }
    }
  }
}
```

**Alert Types:**

* `ACCOUNT_UPDATE` - Account information updated
* `ACCOUNT_REVIEW` - Account under review
* `BUSINESS_CAPABILITY_UPDATE` - Capability changed
* `TEMPLATE_QUALITY_UPDATE` - Template quality alert

**Severity Levels:**

* `INFO` - Informational
* `WARNING` - Warning
* `CRITICAL` - Critical issue

#### whatsapp.account.review_updated

Account review status changed.

**Payload Example:**

```json
{
  "event": {
    "type": "whatsapp.account.review_updated"
  },
  "data": {
    "resource": {
      "type": "account_review",
      "attributes": {
        "review_status": "APPROVED",
        "previous_status": "PENDING"
      }
    }
  }
}
```

#### whatsapp.business.capability_updated

Business account capabilities changed.

**Payload Example:**

```json
{
  "event": {
    "type": "whatsapp.business.capability_updated"
  },
  "data": {
    "resource": {
      "type": "business_capability",
      "attributes": {
        "capability": "MESSAGE_TEMPLATES",
        "status": "AVAILABLE",
        "previous_status": "RESTRICTED"
      }
    }
  }
}
```

**Capabilities:**

* `MESSAGE_TEMPLATES` - Template messaging
* `BUSINESS_INITIATED_CONVERSATIONS` - Initiate conversations
* `UNLIMITED_CONVERSATIONS` - No conversation limits

### Phone Events

#### whatsapp.phone.quality_updated

Phone number quality rating changed.

**Payload Example:**

```json
{
  "event": {
    "type": "whatsapp.phone.quality_updated"
  },
  "data": {
    "resource": {
      "type": "phone_quality",
      "attributes": {
        "phone_number": "919428735270",
        "quality_score": "GREEN",
        "previous_quality_score": "YELLOW"
      }
    }
  }
}
```

**Quality Scores:**

* `GREEN` - High quality (good)
* `YELLOW` - Medium quality (warning)
* `RED` - Low quality (at risk)
* `UNKNOWN` - Not determined

#### whatsapp.phone.name_updated

Display name updated.

**Payload Example:**

```json
{
  "event": {
    "type": "whatsapp.phone.name_updated"
  },
  "data": {
    "resource": {
      "type": "phone_name",
      "attributes": {
        "phone_number": "919428735270",
        "display_name": "Acme Corp Support",
        "previous_name": "Acme Support"
      }
    }
  }
}
```

### Other Events

#### whatsapp.call.received

Incoming WhatsApp call.

**Payload Example:**

```json
{
  "event": {
    "type": "whatsapp.call.received"
  },
  "data": {
    "resource": {
      "type": "call",
      "id": "call_id_xxx",
      "attributes": {
        "from": "919876543210",
        "timestamp": "1767264000"
      }
    },
    "relationships": {
      "contact": {
        "wa_id": "919876543210",
        "name": "John Doe"
      }
    }
  }
}
```

## HTTP Headers

All webhook requests include these headers:

```
Content-Type: application/json
Accept: application/json
User-Agent: whatsmark-Webhook/1.0
X-Webhook-Signature: <hmac-sha256-signature>
X-Webhook-Event: <event-type>
X-Webhook-Timestamp: <iso-8601-timestamp>
X-Webhook-Format: n8n
```

### Header Details

| Header                | Description           | Example                     |
| --------------------- | --------------------- | --------------------------- |
| `X-Webhook-Signature` | HMAC-SHA256 signature | `a1b2c3...`                 |
| `X-Webhook-Event`     | Event type            | `whatsapp.message.received` |
| `X-Webhook-Timestamp` | Event timestamp       | `2026-01-01T10:38:48+00:00` |
| `X-Webhook-Format`    | Payload format        | `n8n`                       |

## Signature Verification

### Algorithm

```
signature = HMAC-SHA256(payload_json, secret_key)
```

### Node.js Implementation

```javascript
const crypto = require('crypto');

function verifyWebhookSignature(payload, signature, secret) {
  const expectedSignature = crypto
    .createHmac('sha256', secret)
    .update(JSON.stringify(payload))
    .digest('hex');

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

// Usage
const payload = req.body;
const signature = req.headers['x-webhook-signature'];
const secret = process.env.WEBHOOK_SECRET;

if (!verifyWebhookSignature(payload, signature, secret)) {
  return res.status(403).json({ error: 'Invalid signature' });
}
```

### PHP Implementation

```php
<?php
function verifyWebhookSignature($payload, $signature, $secret) {
    $expectedSignature = hash_hmac(
        'sha256',
        json_encode($payload),
        $secret
    );

    return hash_equals($signature, $expectedSignature);
}

// Usage
$payload = json_decode(file_get_contents('php://input'), true);
$signature = $_SERVER['HTTP_X_WEBHOOK_SIGNATURE'];
$secret = getenv('WEBHOOK_SECRET');

if (!verifyWebhookSignature($payload, $signature, $secret)) {
    http_response_code(403);
    echo json_encode(['error' => 'Invalid signature']);
    exit;
}
```

## Testing

### Sample Payloads

**Text Message:**

```json
{
  "event": {
    "id": "evt_test_12345",
    "type": "whatsapp.message.received",
    "timestamp": "2026-01-01T10:00:00Z",
    "version": "1.0"
  },
  "tenant": {
    "id": 1,
    "name": "Test Company"
  },
  "data": {
    "resource": {
      "type": "message",
      "id": "wamid.test123",
      "attributes": {
        "message_id": "wamid.test123",
        "from": "1234567890",
        "timestamp": "1735728000",
        "type": "text",
        "text": "Test message",
        "context": null
      }
    },
    "relationships": {
      "contact": {
        "wa_id": "1234567890",
        "name": "Test User"
      },
      "metadata": {
        "phone_number_id": "1111111111",
        "display_phone_number": "1234567890"
      }
    }
  },
  "whatsapp": {
    "original_payload": {}
  },
  "metadata": {
    "source": "whatsapp_webhook_forward",
    "environment": "test",
    "request_id": "test-request-id"
  }
}
```

### cURL Test Command

```bash
curl -X POST https://your-endpoint.com/webhook \
  -H "Content-Type: application/json" \
  -H "X-Webhook-Event: whatsapp.message.received" \
  -H "X-Webhook-Timestamp: 2026-01-01T10:00:00Z" \
  -H "X-Webhook-Format: n8n" \
  -d '{
    "event": {
      "id": "evt_test_12345",
      "type": "whatsapp.message.received",
      "timestamp": "2026-01-01T10:00:00Z",
      "version": "1.0"
    },
    "tenant": {"id": 1, "name": "Test"},
    "data": {
      "resource": {
        "type": "message",
        "attributes": {
          "text": "Test message"
        }
      }
    }
  }'
```

## Related Documentation

* [WhatsApp Webhook Forwarding Guide](./whatsapp-webhook-forwarding.md) - User guide
* [N8N Webhook Integration](./n8n-webhook-integration.md) - Tenant events
* [Webhook Format Reference](./webhook-format-reference.md) - Tenant webhook format
