Webhook Reference
PrivaBase uses webhooks for two purposes: receiving Stripe billing events and sending monitoring alerts to your systems.
Stripe Billing Webhooks
PrivaBase's billing webhook at /api/v1/billing/webhook receives events from Stripe. These are configured in your Stripe dashboard — you don't need to do anything unless you're self-hosting.
Handled Stripe Events
| Event | What Happens |
|---|---|
checkout.session.completed | Subscription activated, user account updated to paid tier |
customer.subscription.updated | Plan change processed (upgrade/downgrade) |
customer.subscription.deleted | Subscription cancelled, account reverts to free tier |
invoice.payment_succeeded | Payment recorded, usage counters reset |
invoice.payment_failed | Payment failed notification sent to user |
ℹ️ Stripe Signature Verification
All Stripe webhooks are verified using the Stripe-Signature header with HMAC-SHA256. Invalid signatures are rejected with 400.
Monitoring Webhooks
You can register your own webhook URLs to receive compliance monitoring alerts. See the Monitoring API for registration endpoints.
Monitoring Event Types
| Event | Description |
|---|---|
check.failed | A scheduled compliance check had failures |
check.degraded | Compliance score dropped below threshold |
check.passed | A previously failing check now passes |
schedule.error | A scheduled check failed to run (system error) |
Webhook Payload Format
{
"event": "check.failed",
"timestamp": "2026-03-13T12:00:00Z",
"data": {
"scheduleId": "sched-uuid",
"frameworkId": "gdpr",
"frameworkName": "GDPR",
"score": 45,
"previousScore": 78,
"failedChecks": [
{
"checkId": "gdpr-check-005",
"rule": "Data Protection Officer",
"severity": "required"
}
]
}
}
Webhook Security
When registering a webhook, you provide a secret. PrivaBase includes an HMAC-SHA256 signature in the X-PrivaBase-Signature header. Verify it server-side:
const crypto = require('crypto');
function verifyWebhook(payload, signature, secret) {
const expected = crypto
.createHmac('sha256', secret)
.update(payload)
.digest('hex');
return crypto.timingSafeEqual(
Buffer.from(signature),
Buffer.from(expected)
);
}
Retry Policy
- PrivaBase retries failed webhook deliveries up to 3 times
- Retry intervals: 1 minute, 5 minutes, 30 minutes
- A delivery is considered failed if it doesn't return a 2xx status within 10 seconds
- After 3 failures, the webhook is disabled and an email notification is sent