Guides · § 2.2
2.2Webhooks
Receive signed events from Relay and verify them in one line.
Relay pushes events to endpoints you register: deploy finished, route errored, quota warning, and more. Webhooks went GA in 1.2.0.
Registering an endpoint
Add endpoints in relay.toml or in the dashboard:
[webhooks]
endpoints = [
{ url = "https://ops.example.com/hooks/relay", events = ["deploy.finished"] },
]Leaving events out subscribes the endpoint to everything.
Verifying signatures
Every delivery includes an X-Relay-Signature header, an HMAC-SHA256 of the raw body using the endpoint secret shown in the dashboard:
import { relay } from '@relay/sdk';
export default async function handler(req: Request) {
const body = await req.text();
const ok = relay.webhooks.verify(
body,
req.headers.get('X-Relay-Signature'),
process.env.RELAY_WEBHOOK_SECRET,
);
if (!ok) return new Response('bad signature', { status: 401 });
const event = JSON.parse(body);
// handle event.type ...
return new Response('ok');
}Secrets rotate without downtime: after rotation, both old and new secrets validate for 24 hours.
Delivery and retries
- Respond with any
2xxwithin 10 seconds to acknowledge. - Failures retry with exponential backoff and jitter, up to 8 attempts over 24 hours.
- One
3xxredirect is followed; further redirects count as a failure. - The dashboard's delivery inspector keeps 30 days of history with request and response bodies, and a one-click redeliver button.
Event types
| Event | Fired when |
|---|---|
deploy.finished | A deploy or promotion completes |
deploy.failed | A build or swap fails |
route.errored | A route's error rate crosses 5 percent |
quota.warning | Usage passes 80 percent of the plan limit |