How it works
Register an endpoint
Add a webhook endpoint in Settings > Webhooks in the tenant console. Provide a publicly reachable HTTPS URL and choose which event types you want to receive.
Receive events
When a matching event occurs, Truthlocks sends an HTTP POST request to your URL with a JSON payload describing the event.
Verify the signature
Each request includes an HMAC-SHA256 signature in the
X-Truthlocks-Signature header. Verify it using the endpoint secret to confirm the request came from Truthlocks.Event types
Events are grouped into categories. You can subscribe to individual events or use a wildcard (attestation.*) to receive all events in a category.
| Category | Event | Trigger |
|---|---|---|
| Attestations | attestation.created | A new attestation is minted |
attestation.revoked | An attestation is revoked | |
attestation.expired | An attestation reaches its expiry date | |
attestation.superseded | An attestation is replaced by a newer version | |
| Verification | verification.completed | A verification check succeeds |
verification.failed | A verification check fails | |
| Issuers | issuer.created | A new issuer is registered |
issuer.updated | An issuer’s profile or settings change | |
issuer.suspended | An issuer is suspended | |
| Keys | key.created | A signing key is registered |
key.rotated | A signing key is rotated | |
key.revoked | A signing key is revoked | |
key.compromised | A key is reported as compromised | |
| Team | team.member_invited | A team invitation is sent |
team.member_joined | A team member accepts an invitation | |
team.member_removed | A team member is removed | |
team.role_changed | A team member’s role is updated | |
| Billing | billing.subscription.created | A new subscription is created |
billing.subscription.updated | A subscription is modified | |
billing.invoice.created | A new invoice is generated | |
billing.usage.threshold | A usage threshold is reached | |
| Consumer | consumer.content.protected | A consumer protects new content |
| Security | security.password_changed | A user changes their password |
security.api_key_compromised | An API key is flagged as compromised | |
security.suspicious_activity | Suspicious account activity is detected |
Wildcard filters
Usecategory.* to subscribe to every event in a category. For example, attestation.* matches attestation.created, attestation.revoked, attestation.expired, and attestation.superseded.
Endpoint limits by plan
The number of webhook endpoints you can create depends on your plan tier:| Plan | Endpoint limit |
|---|---|
| Free | 1 |
| Starter | 3 |
| Business | 10 |
| Enterprise | 25 |
Creating an endpoint
- In the tenant console, go to Settings > Webhooks.
- Click Add endpoint.
- Enter a name, your HTTPS destination URL, and select the event types you want to receive.
- Click Create.
Via the API
Request
Response
Listing endpoints
Retrieve all webhook endpoints for your tenant:Request
Verifying signatures
Every webhook request includes a signature header for verification. Always verify signatures before processing events. Signature format:t is the Unix timestamp and v1 is the HMAC-SHA256 hex digest.
Verification steps:
- Extract
t(timestamp) andv1(signature) from the header. - Reject the request if the timestamp is more than 5 minutes old.
- Concatenate
{timestamp}.{raw_request_body}to form the signing string. - Compute HMAC-SHA256 of the signing string using your endpoint secret.
- Compare the computed digest to
v1using a constant-time comparison.
Request headers
Every webhook delivery includes these headers:| Header | Description |
|---|---|
Content-Type | application/json |
User-Agent | Truthlock-Webhook-Service/1.0 |
X-Truthlocks-Event-Id | Unique identifier for the event |
X-Truthlocks-Event-Type | Event type (e.g., attestation.created) |
X-Truthlocks-Timestamp | Unix timestamp of the delivery attempt |
X-Truthlocks-Signature | HMAC-SHA256 signature for verification |
Retry behavior
If your endpoint returns a non-2xx status code or doesn’t respond within 5 seconds, Truthlocks retries the delivery with exponential backoff:| Attempt | Approximate delay |
|---|---|
| 1st retry | ~1 second |
| 2nd retry | ~2 seconds |
| 3rd retry | ~4 seconds |
| 4th retry | ~16 seconds |
| 5th retry | ~1 minute |
| 6th retry | ~2 minutes |
| 7th retry | ~5 minutes (max) |
Request
Rotating secrets
If your webhook secret is compromised, rotate it immediately:- In the tenant console, go to Settings > Webhooks and click on the endpoint.
- Click Rotate secret.
- Copy the new secret — the old secret stops working immediately.
Request
Testing webhooks
Send a test event to verify your endpoint is working:- In the tenant console, go to Settings > Webhooks and click on the endpoint.
- Click Send test.
- A
webhook.testevent is sent to your URL using the full signing and delivery pipeline.
Request
event_type and payload fields are optional — they default to webhook.test and a basic status payload if omitted.
Best practices
- Verify every signature. Never skip signature verification, even in development.
- Use a message queue. Enqueue incoming events and process them in a worker to avoid blocking the HTTP response.
- Handle duplicates. Use the
X-Truthlocks-Event-Idheader to deduplicate events in case of retries. - Monitor delivery failures. Check the deliveries tab in the console regularly for failed or dead deliveries.
- Keep secrets secure. Store your webhook secret in environment variables, not in source code.
