Webhook events.
Subscribe to real-time Care events. Every incident, resolution, playbook completion, and health score change can be pushed to any HTTPS endpoint.
01 / Setup
Add a webhook endpoint
In the Liulum dashboard, go to Settings > Integrations > Webhooks. Click Add webhook. Paste the HTTPS URL of your endpoint and select the events you want to receive. Care will send a POST request to this URL for each selected event.
02 / Setup
Verify the HMAC signature
Care signs every webhook request with an HMAC-SHA256 signature using your webhook secret. Verify this signature before processing the payload to prevent spoofed requests. The signature is in the X-Liulum-Signature header.
import crypto from 'crypto';
function verifyWebhook(payload: string, secret: string, sig: string) {
const expected = crypto
.createHmac('sha256', secret)
.update(payload)
.digest('hex');
return crypto.timingSafeEqual(
Buffer.from(expected),
Buffer.from(sig.replace('sha256=', '')),
);
}03 / Setup
Respond quickly, process async
Care expects a 2xx response within 5 seconds. If your endpoint needs more time to process, respond with 200 immediately and process the payload asynchronously (e.g. enqueue a background job). If Care receives a non-2xx or times out, it retries up to 3 times with exponential backoff.
// Respond immediately, then process
export async function POST(req: Request) {
const body = await req.text();
// Queue for async processing
await queue.add({ body });
return new Response('ok', { status: 200 });
}04 / Setup
Send a test event
After saving your webhook, click Send test event in the Liulum dashboard. Care sends a sample incident.opened payload to your endpoint. Use this to verify your handler, inspect the payload structure, and confirm the HMAC signature check passes.
05 / Setup
Monitor delivery
In Settings > Webhooks, click your webhook to see the delivery log — every request Care has sent, the response status, response time, and the full request body and response. If a delivery failed, you can replay it from the log.
Request headers
Headers sent with every webhook
X-Liulum-SignatureHMAC-SHA256 signature of the raw request body. Format: sha256=<hex>
X-Liulum-EventThe event name, e.g. incident.opened
X-Liulum-DeliveryUnique delivery ID for this webhook request
Content-TypeAlways application/json
Event payloads
Available events
incident.openedFired when Care detects a new incident — a monitored path fails its assertion.
{
"event": "incident.opened",
"site": {
"id": "proj_xxx",
"name": "My Store",
"url": "https://your-store.com"
},
"incident": {
"id": "inc_xxx",
"severity": "high",
"title": "Checkout returned 500",
"path": "/checkout",
"status_code": 500,
"latency_ms": 3200,
"body_snippet": "Internal Server Error",
"started_at": "2025-01-15T10:23:00Z"
}
}incident.resolvedFired when a previously open incident resolves — the monitored path passes its assertion again.
{
"event": "incident.resolved",
"site": {
"id": "proj_xxx",
"name": "My Store",
"url": "https://your-store.com"
},
"incident": {
"id": "inc_xxx",
"severity": "high",
"title": "Checkout returned 500",
"path": "/checkout",
"started_at": "2025-01-15T10:23:00Z",
"resolved_at": "2025-01-15T10:31:00Z",
"duration_seconds": 480
}
}playbook.completedFired when an auto-repair playbook finishes. Includes the action taken and whether it succeeded.
{
"event": "playbook.completed",
"site": {
"id": "proj_xxx",
"name": "My Store"
},
"playbook": {
"id": "run_xxx",
"name": "cache-flush",
"status": "success",
"actions_taken": [
"Flushed object cache",
"Purged CDN edge cache"
],
"completed_at": "2025-01-15T10:25:30Z"
}
}health.degradedFired when a site health score drops below the configured threshold (default: below 80).
{
"event": "health.degraded",
"site": {
"id": "proj_xxx",
"name": "My Store",
"url": "https://your-store.com"
},
"health": {
"previous_score": 94,
"current_score": 71,
"threshold": 80,
"degraded_at": "2025-01-15T10:23:00Z"
}
}Ready to wire up webhooks?
Add your site to Liulum Care and create your first webhook in Settings.