# Webhooks API Reference The webhook receiver accepts inbound webhooks from external providers (Stripe, GitHub, Shopify, Slack, etc.) and converts them into OneHazel events that can trigger workflows. ## Endpoint ``` POST /functions/v1/webhook-receiver/:connectionId ``` **Authentication:** None required. Providers call this URL directly. Signature verification is used instead. ## How it works 1. You configure an external provider to send webhooks to your OneHazel webhook URL 2. The provider sends a POST request with the event payload 3. OneHazel verifies the signature (if a signing secret is configured) 4. The payload is stored as a OneHazel event of type `provider.webhook.` 5. The event can trigger workflows ## Setting up webhooks ### 1. Register the webhook Register your webhook in the OneHazel dashboard under your connection settings. This creates a `provider_webhooks` record with: - The connection ID - The provider name (e.g. `stripe`, `github`) - An optional signing secret for signature verification - Which events to listen for ### 2. Configure the provider Set the webhook URL in your external provider's settings: ``` https://api.onehazel.com/webhook-receiver/ ``` Replace `` with your connection ID. ### 3. Set the signing secret For secure webhook delivery, configure the same signing secret in both the external provider and your OneHazel webhook registration. ## Signature verification When a signing secret is configured, OneHazel verifies the webhook signature using provider-specific methods: ### Stripe Reads the `stripe-signature` header, extracts the timestamp (`t`) and signature (`v1`), and verifies using HMAC-SHA256 of `{timestamp}.{body}`. ### GitHub Reads the `x-hub-signature-256` header and verifies using HMAC-SHA256 of the raw request body. Expected format: `sha256=`. ### Shopify Reads the `x-shopify-hmac-sha256` header and verifies using HMAC-SHA256 of the raw request body, base64-encoded. ### Slack Reads the `x-slack-signature` and `x-slack-request-timestamp` headers. Verifies using HMAC-SHA256 of `v0:{timestamp}:{body}`. Expected format: `v0=`. ### Generic providers For other providers, OneHazel checks common signature headers (`x-signature`, `x-webhook-signature`, `x-signature-256`, `webhook-signature`, `x-hook-signature`) and tries both hex and base64 HMAC-SHA256 verification. ## Event type extraction OneHazel extracts the event type from the webhook payload based on the provider: | Provider | Event type source | |---|---| | Stripe | `body.type` (e.g. `payment_intent.succeeded`) | | GitHub | `x-github-event` header (e.g. `push`, `pull_request`) | | Shopify | `x-shopify-topic` header (e.g. `orders/create`) | | Slack | `body.event.type` or `body.type` | | Other | `body.event` or `body.type` or `{provider}.webhook` | ## OneHazel event format Verified webhooks are stored as events with the type `provider.webhook.`: ```json { "id": "evt_a1b2c3d4e5f67890", "operator_id": "op_xyz", "type": "provider.webhook.payment_intent.succeeded", "data": { "connectionId": "conn_abc123", "provider": "stripe", "originalEventType": "payment_intent.succeeded", "payload": { ... }, "registrationId": "reg_456" }, "created_at": "2026-04-06T12:00:00.000Z" } ``` ## Unregistered webhooks If a webhook arrives for a connection without an active webhook registration, it is still accepted but logged as `webhook.received.unregistered`. The response includes a warning: ```json { "received": true, "eventId": "evt_a1b2c3d4e5f67890", "warning": "No active webhook registration" } ``` ## Response ### Success ```json { "received": true, "eventId": "evt_a1b2c3d4e5f67890" } ``` HTTP status: `200` ### Signature failure ```json { "error": "Webhook signature verification failed" } ``` HTTP status: `401` ## Workflow triggers Webhook events can trigger workflows. For example: - `provider.webhook.payment_intent.succeeded` — trigger a workflow that updates the player's balance - `provider.webhook.push` — trigger a deployment pipeline - `provider.webhook.orders/create` — trigger order fulfilment Configure these triggers in the workflow builder by selecting the event type pattern. ## Error codes | HTTP Status | Error Code | Description | |---|---|---| | `400` | — | Missing `connectionId` in URL path | | `401` | — | Webhook signature verification failed | | `405` | — | Method not allowed (only POST accepted) | | `500` | — | Internal server error |