Webhooks API
Get notified when envelopes and recipients change. Deliveries are signed with your endpoint secret.
On this page
List webhook endpoints
/v1/webhooksYour webhook endpoints (up to 20 per account).
Required scope:webhooks:read
Query parameters
pageintegerPage number, starting at 1.
default 1
per_pageintegerItems per page.
default 20
Response
A page of webhook endpoints.
objectstring= "list"dataarray of WebhookEndpointChild attributes (WebhookEndpoint)
objectstring= "webhook_endpoint"idstring · uuidurlstring · uridescriptionstring | nulleventsarray of stringenabledbooleanSwitched off automatically after 20 consecutive failed deliveries.
failure_countintegerConsecutive failed attempts; reset by a success.
last_success_atstring · date-time | nulllast_failure_atstring · date-time | nullcreated_atstring · date-time
pageintegerper_pageintegertotalintegerhas_morebooleanWhether another page follows.
Response headers: X-Request-Id, Signkoi-Version, X-RateLimit-Limit, X-RateLimit-Remaining.
Errors
- 401Missing, invalid, expired or revoked API key (
api_key_missing,invalid_api_key). - 403The key lacks a required scope (
insufficient_scope) or the account is suspended (account_suspended). - 429Too many requests (
rate_limited): your key's per-minute limit, or an endpoint's own limit. Wait forRetry-Afterseconds. - 500Something went wrong on our side (
internal_error). Safe to retry with the same Idempotency-Key.
Every error uses the error object.
Example request
curl https://signkoi.com/api/v1/webhooks \
-H "Authorization: Bearer $SIGNKOI_API_KEY"Example response
{
"object": "list",
"data": [
{
"object": "webhook_endpoint",
"id": "6d1e9f3a-4b2c-4a87-9e5d-0f7b3c8a2d54",
"url": "https://example.com/webhooks/signkoi",
"description": "Production CRM sync",
"events": [
"envelope.completed",
"envelope.declined",
"recipient.completed"
],
"enabled": true,
"failure_count": 0,
"last_success_at": "2026-11-14T09:31:02Z",
"last_failure_at": null,
"created_at": "2026-11-01T08:00:00Z"
}
],
"page": 1,
"per_page": 20,
"total": 1,
"has_more": false
}Create a webhook endpoint
/v1/webhooksRegisters an HTTPS URL to receive the events you choose. The response includes the signing secret — the only time it is shown. Up to 20 endpoints per account.
Required scope:webhooks:write
Headers
Idempotency-KeystringAny unique string (1–255 chars), e.g. a UUID. Retrying with the same key and body within 24 hours returns the original response instead of repeating the action.
Request body application/json
urlstring · urirequiredPublic HTTPS URL. Private, loopback and link-local addresses are refused.
max 2048 chars
descriptionstring | nullmax 255 chars
eventsarray of stringrequiredmin 1 items
enabledbooleandefault true
Response
Returned only on create and rotate-secret: the only time you see the signing secret.
objectstring= "webhook_endpoint"idstring · uuidurlstring · uridescriptionstring | nulleventsarray of stringenabledbooleanSwitched off automatically after 20 consecutive failed deliveries.
failure_countintegerConsecutive failed attempts; reset by a success.
last_success_atstring · date-time | nulllast_failure_atstring · date-time | nullcreated_atstring · date-timesecretstringSigning secret (
whsec_…). Store it securely; it is not shown again.
Response headers: X-Request-Id, Signkoi-Version, X-RateLimit-Limit, X-RateLimit-Remaining.
Errors
- 401Missing, invalid, expired or revoked API key (
api_key_missing,invalid_api_key). - 403The key lacks a required scope (
insufficient_scope) or the account is suspended (account_suspended). - 422Invalid request (
validation_failed, e.g. a private or non-HTTPSurl), or you already have 20 endpoints (webhook_limit_reached,paramurl). - 429Too many requests (
rate_limited): your key's per-minute limit, or an endpoint's own limit. Wait forRetry-Afterseconds. - 500Something went wrong on our side (
internal_error). Safe to retry with the same Idempotency-Key.
Every error uses the error object.
Example request
curl -X POST https://signkoi.com/api/v1/webhooks \
-H "Authorization: Bearer $SIGNKOI_API_KEY" \
-H "Idempotency-Key: 5f1d7c1e-0b8a-4c2e-9f3d-61a2b7e4c905" \
-H "Content-Type: application/json" \
-d '{
"url": "https://example.com/webhooks/signkoi",
"description": "Production CRM sync",
"events": [
"envelope.completed",
"envelope.declined",
"recipient.completed"
]
}'Example response
{
"object": "webhook_endpoint",
"id": "6d1e9f3a-4b2c-4a87-9e5d-0f7b3c8a2d54",
"url": "https://example.com/webhooks/signkoi",
"description": "Production CRM sync",
"events": [
"envelope.completed",
"envelope.declined",
"recipient.completed"
],
"enabled": true,
"failure_count": 0,
"last_success_at": "2026-11-14T09:31:02Z",
"last_failure_at": null,
"created_at": "2026-11-01T08:00:00Z",
"secret": "whsec_3vY9pQ2mK7tR1xW8cL5nB0dF4hJ6gS2aZ"
}Retrieve a webhook endpoint
/v1/webhooks/{id}Required scope:webhooks:read
Path parameters
idstring · uuidrequiredWebhook endpoint id.
Response
objectstring= "webhook_endpoint"idstring · uuidurlstring · uridescriptionstring | nulleventsarray of stringenabledbooleanSwitched off automatically after 20 consecutive failed deliveries.
failure_countintegerConsecutive failed attempts; reset by a success.
last_success_atstring · date-time | nulllast_failure_atstring · date-time | nullcreated_atstring · date-time
Response headers: X-Request-Id, Signkoi-Version, X-RateLimit-Limit, X-RateLimit-Remaining.
Errors
- 401Missing, invalid, expired or revoked API key (
api_key_missing,invalid_api_key). - 403The key lacks a required scope (
insufficient_scope) or the account is suspended (account_suspended). - 404No such resource, or it belongs to someone else (
resource_missing, e.g. "No such envelope." / "No such recipient."). - 429Too many requests (
rate_limited): your key's per-minute limit, or an endpoint's own limit. Wait forRetry-Afterseconds. - 500Something went wrong on our side (
internal_error). Safe to retry with the same Idempotency-Key.
Every error uses the error object.
Example request
curl https://signkoi.com/api/v1/webhooks/6d1e9f3a-4b2c-4a87-9e5d-0f7b3c8a2d54 \
-H "Authorization: Bearer $SIGNKOI_API_KEY"Example response
{
"object": "webhook_endpoint",
"id": "6d1e9f3a-4b2c-4a87-9e5d-0f7b3c8a2d54",
"url": "https://example.com/webhooks/signkoi",
"description": "Production CRM sync",
"events": [
"envelope.completed",
"envelope.declined",
"recipient.completed"
],
"enabled": true,
"failure_count": 0,
"last_success_at": "2026-11-14T09:31:02Z",
"last_failure_at": null,
"created_at": "2026-11-01T08:00:00Z"
}Update a webhook endpoint
/v1/webhooks/{id}Change the URL, description or events, or switch the endpoint on or off.
Required scope:webhooks:write
Path parameters
idstring · uuidrequiredWebhook endpoint id.
Request body application/json
urlstring · urimax 2048 chars
descriptionstring | nullmax 255 chars
eventsarray of stringmin 1 items
enabledbooleanRe-enable an endpoint that was switched off after repeated failures (resets the failure count).
Response
Returns the WebhookEndpoint object — its attributes are listed under Retrieve a webhook endpoint.
Response headers: X-Request-Id, Signkoi-Version, X-RateLimit-Limit, X-RateLimit-Remaining.
Errors
- 401Missing, invalid, expired or revoked API key (
api_key_missing,invalid_api_key). - 403The key lacks a required scope (
insufficient_scope) or the account is suspended (account_suspended). - 404No such resource, or it belongs to someone else (
resource_missing, e.g. "No such envelope." / "No such recipient."). - 422Invalid parameters (
validation_failed, withparamanderrors) or a business rule failed (e.g.missing_signature_field). - 429Too many requests (
rate_limited): your key's per-minute limit, or an endpoint's own limit. Wait forRetry-Afterseconds. - 500Something went wrong on our side (
internal_error). Safe to retry with the same Idempotency-Key.
Every error uses the error object.
Example request
curl -X PATCH https://signkoi.com/api/v1/webhooks/6d1e9f3a-4b2c-4a87-9e5d-0f7b3c8a2d54 \
-H "Authorization: Bearer $SIGNKOI_API_KEY" \
-H "Content-Type: application/json" \
-d '{
"events": [
"envelope.completed",
"envelope.declined",
"envelope.voided"
],
"enabled": true
}'Example response
{
"object": "webhook_endpoint",
"id": "6d1e9f3a-4b2c-4a87-9e5d-0f7b3c8a2d54",
"url": "https://example.com/webhooks/signkoi",
"description": "Production CRM sync",
"events": [
"envelope.completed",
"envelope.declined",
"envelope.voided"
],
"enabled": true,
"failure_count": 0,
"last_success_at": "2026-11-14T09:31:02Z",
"last_failure_at": null,
"created_at": "2026-11-01T08:00:00Z"
}Delete a webhook endpoint
/v1/webhooks/{id}Stops all deliveries to the endpoint and deletes it with its delivery history.
Required scope:webhooks:write
Path parameters
idstring · uuidrequiredWebhook endpoint id.
Response
Response headers: X-Request-Id, Signkoi-Version, X-RateLimit-Limit, X-RateLimit-Remaining.
Errors
- 401Missing, invalid, expired or revoked API key (
api_key_missing,invalid_api_key). - 403The key lacks a required scope (
insufficient_scope) or the account is suspended (account_suspended). - 404No such resource, or it belongs to someone else (
resource_missing, e.g. "No such envelope." / "No such recipient."). - 429Too many requests (
rate_limited): your key's per-minute limit, or an endpoint's own limit. Wait forRetry-Afterseconds. - 500Something went wrong on our side (
internal_error). Safe to retry with the same Idempotency-Key.
Every error uses the error object.
Example request
curl -X DELETE https://signkoi.com/api/v1/webhooks/6d1e9f3a-4b2c-4a87-9e5d-0f7b3c8a2d54 \
-H "Authorization: Bearer $SIGNKOI_API_KEY"Rotate the signing secret
/v1/webhooks/{id}/rotate-secretReplaces the signing secret. The new secret is returned once; deliveries are signed with it from now on, so update your receiver straight away.
Required scope:webhooks:write
Path parameters
idstring · uuidrequiredWebhook endpoint id.
Headers
Idempotency-KeystringAny unique string (1–255 chars), e.g. a UUID. Retrying with the same key and body within 24 hours returns the original response instead of repeating the action.
Response
Returns the WebhookEndpointWithSecret object — its attributes are listed under Create a webhook endpoint.
Response headers: X-Request-Id, Signkoi-Version, X-RateLimit-Limit, X-RateLimit-Remaining.
Errors
- 401Missing, invalid, expired or revoked API key (
api_key_missing,invalid_api_key). - 403The key lacks a required scope (
insufficient_scope) or the account is suspended (account_suspended). - 404No such resource, or it belongs to someone else (
resource_missing, e.g. "No such envelope." / "No such recipient."). - 429Too many requests (
rate_limited): your key's per-minute limit, or an endpoint's own limit. Wait forRetry-Afterseconds. - 500Something went wrong on our side (
internal_error). Safe to retry with the same Idempotency-Key.
Every error uses the error object.
Example request
curl -X POST https://signkoi.com/api/v1/webhooks/6d1e9f3a-4b2c-4a87-9e5d-0f7b3c8a2d54/rotate-secret \
-H "Authorization: Bearer $SIGNKOI_API_KEY"Example response
{
"object": "webhook_endpoint",
"id": "6d1e9f3a-4b2c-4a87-9e5d-0f7b3c8a2d54",
"url": "https://example.com/webhooks/signkoi",
"description": "Production CRM sync",
"events": [
"envelope.completed",
"envelope.declined",
"recipient.completed"
],
"enabled": true,
"failure_count": 0,
"last_success_at": "2026-11-14T09:31:02Z",
"last_failure_at": null,
"created_at": "2026-11-01T08:00:00Z",
"secret": "whsec_3vY9pQ2mK7tR1xW8cL5nB0dF4hJ6gS2aZ"
}Send a test event
/v1/webhooks/{id}/testSends a signed ping event to the endpoint right away (no retries) and returns the delivery, so you can check your receiver and signature verification. Limited to 10 calls a minute.
Required scope:webhooks:write
Path parameters
idstring · uuidrequiredWebhook endpoint id.
Headers
Idempotency-KeystringAny unique string (1–255 chars), e.g. a UUID. Retrying with the same key and body within 24 hours returns the original response instead of repeating the action.
Response
objectstring= "webhook_delivery"idstring · uuideventstringstatusstringpending: not attempted yet;delivered: your endpoint returned 2xx;retrying: the last attempt failed and another is scheduled (next_retry_at);failed: every retry failed.One of
pendingdeliveredretryingfailedattemptsintegerresponse_statusinteger | nullHTTP status your endpoint returned on the last attempt.
response_excerptstring | nullFirst 1,000 characters of your response body, or why the request could not be sent.
max 1000 chars
delivered_atstring · date-time | nullnext_retry_atstring · date-time | nullcreated_atstring · date-time
Response headers: X-Request-Id, Signkoi-Version, X-RateLimit-Limit, X-RateLimit-Remaining.
Errors
- 401Missing, invalid, expired or revoked API key (
api_key_missing,invalid_api_key). - 403The key lacks a required scope (
insufficient_scope) or the account is suspended (account_suspended). - 404No such resource, or it belongs to someone else (
resource_missing, e.g. "No such envelope." / "No such recipient."). - 429More than 10 tests a minute (
rate_limited), or your key's rate limit. - 500Something went wrong on our side (
internal_error). Safe to retry with the same Idempotency-Key.
Every error uses the error object.
Example request
curl -X POST https://signkoi.com/api/v1/webhooks/6d1e9f3a-4b2c-4a87-9e5d-0f7b3c8a2d54/test \
-H "Authorization: Bearer $SIGNKOI_API_KEY"Example response
{
"object": "webhook_delivery",
"id": "a2c5e8f1-6b3d-4d9a-8c7e-1f4b0a9d3e62",
"event": "ping",
"status": "delivered",
"attempts": 1,
"response_status": 200,
"response_excerpt": "ok",
"delivered_at": "2026-11-14T10:05:00Z",
"next_retry_at": null,
"created_at": "2026-11-14T10:05:00Z"
}List deliveries
/v1/webhooks/{id}/deliveriesRecent delivery attempts to the endpoint, newest first.
Required scope:webhooks:read
Path parameters
idstring · uuidrequiredWebhook endpoint id.
Query parameters
pageintegerPage number, starting at 1.
default 1
per_pageintegerItems per page.
default 20
Response
Recent deliveries, newest first.
objectstring= "list"dataarray of WebhookDeliveryChild attributes (WebhookDelivery)
objectstring= "webhook_delivery"idstring · uuideventstringstatusstringpending: not attempted yet;delivered: your endpoint returned 2xx;retrying: the last attempt failed and another is scheduled (next_retry_at);failed: every retry failed.One of
pendingdeliveredretryingfailedattemptsintegerresponse_statusinteger | nullHTTP status your endpoint returned on the last attempt.
response_excerptstring | nullFirst 1,000 characters of your response body, or why the request could not be sent.
max 1000 chars
delivered_atstring · date-time | nullnext_retry_atstring · date-time | nullcreated_atstring · date-time
pageintegerper_pageintegertotalintegerhas_morebooleanWhether another page follows.
Response headers: X-Request-Id, Signkoi-Version, X-RateLimit-Limit, X-RateLimit-Remaining.
Errors
- 401Missing, invalid, expired or revoked API key (
api_key_missing,invalid_api_key). - 403The key lacks a required scope (
insufficient_scope) or the account is suspended (account_suspended). - 404No such resource, or it belongs to someone else (
resource_missing, e.g. "No such envelope." / "No such recipient."). - 429Too many requests (
rate_limited): your key's per-minute limit, or an endpoint's own limit. Wait forRetry-Afterseconds. - 500Something went wrong on our side (
internal_error). Safe to retry with the same Idempotency-Key.
Every error uses the error object.
Example request
curl https://signkoi.com/api/v1/webhooks/6d1e9f3a-4b2c-4a87-9e5d-0f7b3c8a2d54/deliveries \
-H "Authorization: Bearer $SIGNKOI_API_KEY"Example response
{
"object": "list",
"data": [
{
"object": "webhook_delivery",
"id": "a2c5e8f1-6b3d-4d9a-8c7e-1f4b0a9d3e62",
"event": "envelope.completed",
"status": "delivered",
"attempts": 1,
"response_status": 200,
"response_excerpt": "ok",
"delivered_at": "2026-11-15T14:02:43Z",
"next_retry_at": null,
"created_at": "2026-11-15T14:02:42Z"
}
],
"page": 1,
"per_page": 20,
"total": 1,
"has_more": false
}List event types
/v1/webhook-eventsEvery event a webhook endpoint can subscribe to (the ping test event is not listed).
Required scope:webhooks:read
Response
Every event you can subscribe to.
objectstring= "list"dataarray of WebhookEventChild attributes (WebhookEvent)
objectstring= "webhook_event"namestringdescriptionstring
Response headers: X-Request-Id, Signkoi-Version, X-RateLimit-Limit, X-RateLimit-Remaining.
Errors
- 401Missing, invalid, expired or revoked API key (
api_key_missing,invalid_api_key). - 403The key lacks a required scope (
insufficient_scope) or the account is suspended (account_suspended). - 429Too many requests (
rate_limited): your key's per-minute limit, or an endpoint's own limit. Wait forRetry-Afterseconds. - 500Something went wrong on our side (
internal_error). Safe to retry with the same Idempotency-Key.
Every error uses the error object.
Example request
curl https://signkoi.com/api/v1/webhook-events \
-H "Authorization: Bearer $SIGNKOI_API_KEY"Example response
{
"object": "list",
"data": [
{
"object": "webhook_event",
"name": "envelope.sent",
"description": "The envelope was sent and the first recipients were invited."
},
{
"object": "webhook_event",
"name": "envelope.completed",
"description": "Every recipient finished; the signed PDF and certificate are ready to download."
},
{
"object": "webhook_event",
"name": "envelope.declined",
"description": "A recipient declined to sign, which closes the envelope."
},
{
"object": "webhook_event",
"name": "envelope.voided",
"description": "The sender voided the envelope."
},
{
"object": "webhook_event",
"name": "recipient.sent",
"description": "A recipient was invited (it is their turn in the routing order)."
},
{
"object": "webhook_event",
"name": "recipient.viewed",
"description": "A recipient opened the envelope."
},
{
"object": "webhook_event",
"name": "recipient.completed",
"description": "A recipient signed, approved or viewed as required."
},
{
"object": "webhook_event",
"name": "recipient.declined",
"description": "A recipient declined to sign."
},
{
"object": "webhook_event",
"name": "recipient.delegated",
"description": "A recipient handed their part to someone else (see data.delegated_to)."
}
]
}