Developer · 5 min read
Get told automatically when it’s signed (webhooks)
A webhook lets your own software react automatically when a document is completed — so a result shows up in your dashboard without anyone logging into Sealed in Black.
How it works: when you send a document you include a webhook_url (an address on your website). When the document is completed (or declined), we POST an event to that address. Because you also sent an external_ref (your record id), we hand it right back so you know which record to update.
What we send you
{
"event": "document.completed",
"data": { "document": {
"id": 337,
"status": "completed",
"external_ref": "record_8842",
"signed_pdf_url": "https://sealedinblack.com/api/v1/esign/documents/337/signed-pdf"
} }
}
Every webhook also carries a signature header so you can be sure it really came from us:
X-Sealedinblack-Signature: sha256=...
Your receiver (copy-paste PHP)
Put this at the address you used for webhook_url (e.g. /hooks/sealedinblack). Set your webhook secret (from the Developer API page) as the SIB_WEBHOOK_SECRET server setting. Fill in the one “TODO” with your own update.
<?php
$secret = getenv('SIB_WEBHOOK_SECRET');
$raw = file_get_contents('php://input');
$sig = $_SERVER['HTTP_X_SEALEDINBLACK_SIGNATURE'] ?? '';
// 1. Make sure it really came from Sealed in Black.
$expected = 'sha256=' . hash_hmac('sha256', $raw, (string) $secret);
if (! $secret || ! hash_equals($expected, $sig)) {
http_response_code(400);
exit('bad signature');
}
$event = json_decode($raw, true);
$type = $event['event'] ?? '';
$doc = $event['data']['document'] ?? [];
$ref = $doc['external_ref'] ?? null; // YOUR record id
// 2. React.
if ($type === 'document.completed' && $ref) {
// TODO: update YOUR record. Example:
// mark record $ref as "active", save $doc['id'] and $doc['signed_pdf_url'].
}
// 3. Always answer 200 quickly (or we retry).
http_response_code(200);
echo 'ok';
Do not skip the signature check — it’s what stops someone from faking a “completed” event. That’s the whole receiver: verify, look up your record by external_ref, update it, answer 200.
Webhooks are optional. If you just want to watch documents get signed, the dashboard already shows live status — you don’t need a webhook at all.