Skip to content

Webhook Trigger

Exposes a unique URL (https://<...>.supabase.co/functions/v1/webhook-receiver/wh_...) that external systems — Stripe, GitHub, HubSpot, anything — can POST JSON to. Every POST that validates triggers one execution of your workflow.

When to use

  • A third-party service supports webhooks and you want their events to drive a workflow.
  • You need to accept inbound data from a custom integration you don't have a connector for yet.
  • Any "when X happens in their system, do Y in ours" use case.

Configuration

FieldRequiredWhat it does
expectedPayloadNoExample JSON. Used only by the data picker so downstream nodes have something to drill into. It is not validated against incoming requests.
verificationSecretNoShared secret for HMAC signature verification. When set, incoming requests must include a matching X-OneHazel-Signature header or the request is rejected with 401.

The webhookId (the wh_... part of the URL) is managed internally by OneHazel and displayed in the node configuration drawer. It is stable — you can paste it into the third-party system's webhook settings and it won't change unless you delete the node.

Signature verification

When verificationSecret is set, the receiver computes HMAC-SHA256(secret, raw_body) hex-lowercased, and compares against the X-OneHazel-Signature header. Requests without a matching signature get a 401 and the workflow does not fire.

If the third-party system supports HMAC-SHA256 signatures with the same scheme (Stripe and GitHub both do a variation), set the secret and they'll be verified automatically. If not, leave it blank — the URL is still unguessable enough that unauthenticated POSTs are rare.

Deduplication

Every incoming request is deduplicated by X-Request-Id header for 24 hours. If a sender retries without bumping the ID, the receiver returns 200 but does NOT re-fire the workflow. If the sender doesn't set the header, a hash of the body is used.

What it outputs

The entire parsed JSON body is exposed to downstream nodes as {{trigger.data.*}}. Request headers are available at {{trigger.headers.*}}.

Gotchas

  • Body must be valid JSON. Non-JSON bodies are rejected with 400.
  • POST only — GET/PUT/DELETE are rejected.
  • Webhook URL is per-node — if you delete and recreate the node you get a new URL and have to update the third-party system.