← API DocumentationWEBHOOKS
Webhook events
Real-time HTTP callbacks when something happens in your Konomic account — sign requests, async tasks, and more.
Getting started
Webhooks let Konomic notify your application in real time when events happen. Instead of polling our API, you give us an endpoint URL and we POST event data to it whenever something interesting occurs.
Webhooks are available on the Business tier. To configure:
- Sign in to your dashboard
- Go to Settings → Webhooks
- Click Add endpoint
- Enter your HTTPS URL (e.g.
https://api.yourapp.com/konomic/webhook) - Select which events you want to receive
- Save — you'll get a signing secret to verify authenticity
Event types
sign_request.sentA sign request was successfully sent to the recipient
sign_request.viewedThe recipient opened the signing link and loaded the document
sign_request.signedThe recipient completed the signature and submitted
sign_request.declinedThe recipient declined to sign the document
sign_request.expiredThe sign request expired before being signed
sign_request.cancelledThe sender cancelled the sign request
task.completedAn async PDF operation finished successfully
task.failedAn async PDF operation failed
Payload structure
Every webhook request uses the same envelope:
# POST https://your-endpoint.com/
# Content-Type: application/json
# Konomic-Signature: t=1712750000,v1=abc123...
{
"id": "evt_1TKopAAjjOtSbCYD",
"type": "sign_request.signed",
"created": 1712750000,
"livemode": true,
"api_version": "2026-04-11",
"data": {
"object": {
"id": "sr_abc123",
"status": "signed",
"recipient_email": "client@example.com",
"recipient_name": "Jane Client",
"signed_at": "2026-04-11T14:30:00Z",
"signed_file_url": "https://konomic.io/files/...",
"audit_trail": {
"ip_address": "203.0.113.42",
"user_agent": "Mozilla/5.0...",
"viewed_at": "2026-04-11T14:28:00Z",
"signed_at": "2026-04-11T14:30:00Z"
}
}
}
}
Signature verification
Every webhook request includes a Konomic-Signatureheader. You should verify this header to confirm the request actually came from Konomic and wasn't forged.
The header has the format t=TIMESTAMP,v1=SIGNATURE. To verify:
- Extract timestamp and signature from the header
- Build the signed payload:
TIMESTAMP + "." + REQUEST_BODY - Compute HMAC-SHA256 using your endpoint secret as the key
- Compare to the
v1 value from the header (constant-time comparison) - Reject if the timestamp is older than 5 minutes (prevents replay attacks)
Python example
import hmac, hashlib, time
def verify_webhook(payload: bytes, header: str, secret: str) -> bool:
parts = dict(p.split("=") for p in header.split(","))
timestamp, signature = parts["t"], parts["v1"]
if abs(time.time() - int(timestamp)) > 300:
return False # too old
signed = f"{timestamp}.{payload.decode()}".encode()
expected = hmac.new(secret.encode(), signed, hashlib.sha256).hexdigest()
return hmac.compare_digest(expected, signature)
Node.js example
import crypto from "crypto";
function verifyWebhook(payload, header, secret) {
const parts = Object.fromEntries(
header.split(",").map((p) => p.split("="))
);
const [t, sig] = [parts.t, parts.v1];
if (Math.abs(Date.now() / 1000 - Number(t)) > 300) return false;
const signed = `${t}.${payload}`;
const expected = crypto.createHmac("sha256", secret)
.update(signed).digest("hex");
return crypto.timingSafeEqual(
Buffer.from(expected), Buffer.from(sig)
);
}
Retries & delivery
When your endpoint returns a 2xx response, the webhook is considered delivered. Any other status code (or a timeout) triggers a retry.
Retry schedule (exponential backoff):
- 1st retry: 1 minute after initial attempt
- 2nd retry: 5 minutes
- 3rd retry: 30 minutes
- 4th retry: 2 hours
- 5th retry: 12 hours
- 6th retry: 24 hours
After 6 failed attempts, the webhook is marked as failed and no more retries happen. You can inspect failed deliveries and manually retry from the dashboard.
Response time limit: Your endpoint must respond within 10 seconds. If your processing takes longer, return 2xx immediately and do the work asynchronously (job queue, background worker).
Best practices
- Always verify the signature — don't trust incoming webhook payloads without checking the signature header
- Be idempotent — we may deliver the same event multiple times due to retries. Use the
id field to dedupe. - Return 2xx fast — acknowledge the event quickly, process asynchronously if needed
- Log everything — keep at least 30 days of webhook logs for debugging
- Whitelist our IPs — if you have strict firewall rules, our webhook requests come from a fixed set of EU IPs (available on request)
- Rotate your secret — if you suspect a leak, rotate the endpoint secret from the dashboard
Available on Business tier
Webhook events plus full API access — $14.99/month.
See pricing