Every webhook delivery carries an HMAC signature you must verify before trusting the payload. The SDK does the work in one call — you pass the raw body, the signature header, and your webhook secret; it returns a typed event or throws.Documentation Index
Fetch the complete documentation index at: https://docs.vibefollow.com/llms.txt
Use this file to discover all available pages before exploring further.
How verification works
The full pattern
- Express
- Hono
- Next.js App Router
- Raw fetch / HTTP
The header format
Verification is constant-time. The SDK uses
crypto.timingSafeEqual so an attacker cannot derive the secret by timing your responses.Why the raw body
Framework-specific notes:Express
Express
Mount
express.raw({ type: '*/*' }) on the webhook route only — not globally, or every other route loses JSON parsing.Hono / Cloudflare Workers
Hono / Cloudflare Workers
Call
await request.text() and pass the string.Next.js App Router
Next.js App Router
Read
request.text() inside the route handler. Pin the route to runtime = 'nodejs'.Fastify
Fastify
Use the
addContentTypeParser API to capture the raw buffer.Replay protection
The header includes a Unix-seconds timestampt. The SDK rejects any delivery whose timestamp is more than ±5 minutes from local time, which neutralises replay attacks against stale captured payloads.
Override the tolerance if your environment has known clock drift:
Don’t widen it past necessity. Five minutes is the Stripe-standard window for the same reason — it balances clock drift against replay risk.
Errors you should handle
WebhookSignatureError — missing header
WebhookSignatureError — missing header
The
X-Vibefollow-Signature header wasn’t on the request. Return 401.WebhookSignatureError — malformed header
WebhookSignatureError — malformed header
The header didn’t parse as
t=…,v1=…. Return 401.WebhookSignatureError — timestamp outside tolerance
WebhookSignatureError — timestamp outside tolerance
The
t is more than ±5 minutes from now. Return 401.WebhookSignatureError — signature mismatch
WebhookSignatureError — signature mismatch
The HMAC didn’t match. Either the secret is wrong, the body was modified in transit, or it’s a forgery. Return
401.SyntaxError
SyntaxError
The (verified) body was not valid JSON. This shouldn’t happen — return
500 and investigate.WebhookSignatureError cases, return 401. Do not retry on your side — Vibefollow’s retry will pick it up if the failure was transient.
Edge-runtime caveats
Webhook verification usesnode:crypto for HMAC. On Cloudflare Workers, enable the nodejs_compat flag in wrangler.toml:
Pure-edge runtimes without Node compatibility cannot use the SDK’s verifier in v1. Track this issue for a Web Crypto fallback.
Testing locally
Use the Vibefollow CLI’swebhook:send command (coming soon) or curl with a hand-computed signature: