> ## Documentation Index
> Fetch the complete documentation index at: https://docs.reachedapp.com/llms.txt
> Use this file to discover all available pages before exploring further.

# Create a Webhook

> Register an HTTPS endpoint to receive real-time event deliveries.

# Create a Webhook

Registers an HTTPS endpoint to receive event deliveries. The signing secret is returned **once** in the response — store it securely to verify the `X-Reached-Signature` header on incoming deliveries.

## Request

`POST /v1/webhooks`

### Body Parameters

| Parameter | Type   | Required | Description                                                                       |
| --------- | ------ | -------- | --------------------------------------------------------------------------------- |
| `name`    | string | Yes      | Human-readable label for this webhook                                             |
| `url`     | string | Yes      | HTTPS endpoint to deliver events to                                               |
| `events`  | array  | No       | Event types to subscribe to. Defaults to `["call.completed", "transcript.ready"]` |

### Available Events

| Event              | Description                                                                                                                 |
| ------------------ | --------------------------------------------------------------------------------------------------------------------------- |
| `call.completed`   | Fired when a call ends and its log is finalized                                                                             |
| `transcript.ready` | Fired when transcription and AI summary are both complete. The payload includes a truncated transcript and the full summary |

<Note>
  When you receive a `transcript.ready` event, the call log already has both the `transcript` and `summary` fields populated. You can fetch the full call log via `GET /v1/call-logs/:id` to retrieve the complete transcript and summary.
</Note>

## Example

<CodeGroup>
  ```bash cURL theme={null}
  curl -X POST \
    "https://kdjmltmhxvvmiuehafgl.supabase.co/functions/v1/api-gateway/v1/webhooks" \
    -H "Authorization: Bearer rchd_live_xxxxxxxxxxxx" \
    -H "Content-Type: application/json" \
    -d '{
      "name": "Data pipeline",
      "url": "https://api.yourcompany.com/reached/webhook",
      "events": ["call.completed", "transcript.ready"]
    }'
  ```

  ```javascript JavaScript theme={null}
  const response = await fetch(
    "https://kdjmltmhxvvmiuehafgl.supabase.co/functions/v1/api-gateway/v1/webhooks",
    {
      method: "POST",
      headers: {
        "Authorization": "Bearer rchd_live_xxxxxxxxxxxx",
        "Content-Type": "application/json"
      },
      body: JSON.stringify({
        name: "Data pipeline",
        url: "https://api.yourcompany.com/reached/webhook",
        events: ["call.completed", "transcript.ready"]
      })
    }
  );
  const { data } = await response.json();
  // Store data.secret securely — it is only returned once
  ```
</CodeGroup>

## Response

```json theme={null}
{
  "data": {
    "id": "wh-uuid-1",
    "name": "Data pipeline",
    "url": "https://api.yourcompany.com/reached/webhook",
    "events": ["call.completed", "transcript.ready"],
    "is_active": true,
    "secret": "whsec_xxxxxxxxxxxx",
    "created_at": "2026-07-18T15:00:00.000Z",
    "updated_at": "2026-07-18T15:00:00.000Z"
  }
}
```

### Response Fields

| Field        | Type     | Description                                                                   |
| ------------ | -------- | ----------------------------------------------------------------------------- |
| `id`         | uuid     | Webhook unique identifier                                                     |
| `name`       | string   | Human-readable label                                                          |
| `url`        | string   | HTTPS endpoint URL                                                            |
| `events`     | array    | Subscribed event types                                                        |
| `is_active`  | boolean  | Whether the webhook is active                                                 |
| `secret`     | string   | Signing secret for HMAC verification (returned only once — store it securely) |
| `created_at` | datetime | Creation timestamp                                                            |
| `updated_at` | datetime | Last update timestamp                                                         |

### Verifying Webhook Signatures

Each delivery includes an `X-Reached-Signature` header containing an HMAC-SHA256 hash of the request body, computed using your webhook's signing secret. Verify it before processing the payload:

```javascript theme={null}
const crypto = require("crypto");

const expected = crypto
  .createHmac("sha256", webhookSecret)
  .update(rawRequestBody)
  .digest("hex");

if (expected !== request.headers["x-reached-signature"]) {
  return res.status(401).send("Invalid signature");
}
```
