Webhook Events
Webhooks allow you to receive real-time notifications when events occur in your Stewart Sign account. Instead of polling the API for updates, webhooks proactively send event data to your application as soon as something happens.
Getting Started with Webhooks
To enable webhooks for your account, you'll need to request webhook configuration from the Stewart Sign team.
Request Webhook Setup
- Contact Support: Reach out to the Stewart Sign support team at support@stewart.com
- Provide Your Webhook URL: Share the HTTPS endpoint where you want to receive webhook notifications
- Select Events: Specify which events you want to subscribe to from the available events list
- Authentication (Optional): If your endpoint requires authentication, provide those details
Requirements for Your Webhook Endpoint
- Must be accessible via HTTPS
- Should respond with a
200 OKstatus code within 5 seconds - Should process webhook payloads asynchronously to avoid timeouts
Webhook Payload Structure
All webhook events follow a consistent JSON structure:
{
"event": "event-name",
"entity": "entity-type",
"eventTimestamp": "2026-04-07T18:25:43.511Z",
"data": {
"notificationId": "unique-notification-id",
"entity_id": "related-entity-id",
"transaction_id": "related-transaction-id"
// Additional event-specific fields
}
}
Common Fields
| Field | Type | Description |
|---|---|---|
event | string | The type of event that occurred (e.g., "transaction-created") |
entity | string | The entity type this event relates to (e.g., "transaction", "document", "participant") |
eventTimestamp | string (ISO 8601) | UTC timestamp representing when the event was generated by the system (not when the webhook was delivered). Format: YYYY-MM-DDTHH:mm:ss.sssZ. Use this field to determine the chronological order of events. This value remains the same across retries. |
data | object | Event-specific data containing details about what happened |
data.notificationId | string (UUID) | Unique identifier for this webhook notification - use for idempotency |
data.entity_id | string (UUID) | ID of the primary entity related to this event |
data.transaction_id | string (UUID) | ID of the transaction this event belongs to |
Event-Specific Fields
Some events include additional fields in the data object:
| Field | Events | Description |
|---|---|---|
status | document-status-changed, esign-status-updated | The new status value (e.g., "completed") |
document_id | revision-saved-by-participant, revision-completed-by-participant | ID of the document being revised |
participant_id | revision-saved-by-participant, revision-completed-by-participant | ID of the participant making the revision |
Sample Payload
{
"event": "transaction-created",
"entity": "transaction",
"eventTimestamp": "2026-04-07T18:25:43.511Z",
"data": {
"notificationId": "415e30a1-a71f-467d-bde1-85fb21d64269",
"entity_id": "8d976a23-b865-4fcd-9165-ddc0aedaf614",
"transaction_id": "8d976a23-b865-4fcd-9165-ddc0aedaf614"
}
}
Available Webhook Events
The following events are available for webhook subscriptions:
Transaction Events
| Event | Description | Entity | Triggered When |
|---|---|---|---|
transaction-created | New transaction created | transaction | A new eSignature transaction is initiated |
eSign Events
| Event | Description | Entity | Triggered When |
|---|---|---|---|
esign-created | eSign session created | esign | A new eSignature session is started |
esign-status-updated | eSign status changed | esign | The status of an eSign session changes |
esign-completed | eSign session completed | esign | All participants have completed the eSign session |
Document Events
| Event | Description | Entity | Triggered When |
|---|---|---|---|
document-created | Document uploaded | document | A new document is uploaded to the system |
document-status-changed | Document status updated | document | A document's status changes |
Participant Events
| Event | Description | Entity | Triggered When |
|---|---|---|---|
participant-created | New participant added | participant | A new participant is added to a transaction |
participant-updated | Participant information changed | participant | Participant details are modified |
participant-set-auth | Participant authentication set | participant | Authentication method is configured for a participant |
participant-set-signature-and-initials | Signature and initials configured | participant | Participant's signature and initials are set |
participant-accepted-terms-and-conditions | Terms accepted | participant | Participant accepts terms and conditions |
participant-emailed-completed-esign | Completion email sent | participant | Completion confirmation email is sent to participant |
participant-completed-esign | Participant finished signing | participant | A participant has finished all documents in an eSign session |
Revision Events
| Event | Description | Entity | Triggered When |
|---|---|---|---|
revision-saved-by-participant | Participant saved document draft | revision | A participant has saved a document but hasn't finished - there are still incomplete or unskipped tags remaining |
revision-completed-by-participant | Participant completed document | revision | A participant has completed signing a document - all their tags have been filled or skipped |
Event Details & Examples
Transaction Events
transaction-created
Triggered when a new eSignature transaction is initiated in the system.
{
"event": "transaction-created",
"entity": "transaction",
"eventTimestamp": "2026-04-07T18:25:43.511Z",
"data": {
"notificationId": "415e30a1-a71f-467d-bde1-85fb21d64269",
"entity_id": "8d976a23-b865-4fcd-9165-ddc0aedaf614",
"transaction_id": "8d976a23-b865-4fcd-9165-ddc0aedaf614"
}
}
eSign Events
esign-created
Triggered when a new eSignature session has been added to the transaction.
{
"event": "esign-created",
"entity": "esign",
"eventTimestamp": "2026-04-07T18:25:43.511Z",
"data": {
"notificationId": "b2c3d4e5-f6a7-8901-bcde-f12345678901",
"entity_id": "8d976a23-b865-4fcd-9165-ddc0aedaf614",
"transaction_id": "8d976a23-b865-4fcd-9165-ddc0aedaf614"
}
}
esign-status-updated
Triggered when the eSign status has changed (e.g., from "pending" to "in-progress" or "completed").
{
"event": "esign-status-updated",
"entity": "esign",
"eventTimestamp": "2026-04-07T18:26:12.834Z",
"data": {
"notificationId": "c3d4e5f6-a7b8-9012-cdef-123456789012",
"status": "completed",
"entity_id": "8d976a23-b865-4fcd-9165-ddc0aedaf614",
"transaction_id": "8d976a23-b865-4fcd-9165-ddc0aedaf614"
}
}
esign-completed
Triggered when all participants have completed their eSignatures for all documents. This indicates that the entire eSign session is complete.
{
"event": "esign-completed",
"entity": "esign",
"eventTimestamp": "2026-04-07T18:30:01.205Z",
"data": {
"notificationId": "a8b9c7d6-e5f4-3210-9876-543210fedcba",
"entity_id": "8d976a23-b865-4fcd-9165-ddc0aedaf614",
"transaction_id": "8d976a23-b865-4fcd-9165-ddc0aedaf614"
}
}
Document Events
document-created
Triggered when a new document has been added to an eSign session.
{
"event": "document-created",
"entity": "document",
"eventTimestamp": "2026-04-07T18:25:44.102Z",
"data": {
"notificationId": "d4e5f6a7-b8c9-0123-4567-89abcdef0123",
"entity_id": "8d976a23-b865-4fcd-9165-ddc0aedaf614",
"transaction_id": "8d976a23-b865-4fcd-9165-ddc0aedaf614"
}
}
document-status-changed
Triggered when a document's status has changed (e.g., from "pending" to "completed").
{
"event": "document-status-changed",
"entity": "document",
"eventTimestamp": "2026-04-07T18:28:15.773Z",
"data": {
"notificationId": "b2c3d4e5-f6a7-8901-bcde-f12345678901",
"status": "completed",
"entity_id": "8d976a23-b865-4fcd-9165-ddc0aedaf614",
"transaction_id": "8d976a23-b865-4fcd-9165-ddc0aedaf614"
}
}
Participant Events
participant-created
Triggered when a participant has been added to a transaction.
{
"event": "participant-created",
"entity": "participant",
"eventTimestamp": "2026-04-07T18:25:44.320Z",
"data": {
"notificationId": "e4f5a6b7-c8d9-0123-4567-89abcdef0123",
"entity_id": "8d976a23-b865-4fcd-9165-ddc0aedaf614",
"transaction_id": "8d976a23-b865-4fcd-9165-ddc0aedaf614"
}
}
participant-updated
Triggered when the participant entity has been updated (e.g., email address, name, role changes).
{
"event": "participant-updated",
"entity": "participant",
"eventTimestamp": "2026-04-07T18:25:50.891Z",
"data": {
"notificationId": "f5a6b7c8-d9e0-1234-5678-9abcdef01234",
"entity_id": "8d976a23-b865-4fcd-9165-ddc0aedaf614",
"transaction_id": "8d976a23-b865-4fcd-9165-ddc0aedaf614"
}
}
participant-set-auth
Triggered when the participant has successfully set their authentication method.
{
"event": "participant-set-auth",
"entity": "participant",
"eventTimestamp": "2026-04-07T18:26:05.442Z",
"data": {
"notificationId": "a6b7c8d9-e0f1-2345-6789-abcdef012345",
"entity_id": "8d976a23-b865-4fcd-9165-ddc0aedaf614",
"transaction_id": "8d976a23-b865-4fcd-9165-ddc0aedaf614"
}
}
participant-set-signature-and-initials
Triggered when the participant has set their signature and initials.
{
"event": "participant-set-signature-and-initials",
"entity": "participant",
"eventTimestamp": "2026-04-07T18:26:10.118Z",
"data": {
"notificationId": "b7c8d9e0-f1a2-3456-789a-bcdef0123456",
"entity_id": "8d976a23-b865-4fcd-9165-ddc0aedaf614",
"transaction_id": "8d976a23-b865-4fcd-9165-ddc0aedaf614"
}
}
participant-accepted-terms-and-conditions
Triggered when the participant has accepted the terms and conditions.
{
"event": "participant-accepted-terms-and-conditions",
"entity": "participant",
"eventTimestamp": "2026-04-07T18:26:08.556Z",
"data": {
"notificationId": "c8d9e0f1-a2b3-4567-89ab-cdef01234567",
"entity_id": "8d976a23-b865-4fcd-9165-ddc0aedaf614",
"transaction_id": "8d976a23-b865-4fcd-9165-ddc0aedaf614"
}
}
participant-emailed-completed-esign
Triggered when the participant was emailed the completed document for an eSign session.
{
"event": "participant-emailed-completed-esign",
"entity": "participant",
"eventTimestamp": "2026-04-07T18:30:05.667Z",
"data": {
"notificationId": "e5f6a7b8-c9d0-1234-5678-9abcdef01234",
"entity_id": "8d976a23-b865-4fcd-9165-ddc0aedaf614",
"transaction_id": "8d976a23-b865-4fcd-9165-ddc0aedaf614"
}
}
participant-completed-esign
Triggered when a participant has finished all the documents in an eSign session.
{
"event": "participant-completed-esign",
"entity": "participant",
"eventTimestamp": "2026-04-07T18:29:55.334Z",
"data": {
"notificationId": "d4e5f6a7-b8c9-0123-4567-89abcdef0123",
"entity_id": "8d976a23-b865-4fcd-9165-ddc0aedaf614",
"transaction_id": "8d976a23-b865-4fcd-9165-ddc0aedaf614"
}
}
Revision Events
revision-saved-by-participant
Triggered when a participant has saved a document in an eSignature session but has not finished completing it. There are still tags on the document for this participant that have not been completed and have not been skipped. A revision has been saved with the current XFDF data that includes what tags need to be completed as well as annotations applied by the user.
Note: This event includes additional fields: document_id and participant_id.
{
"event": "revision-saved-by-participant",
"entity": "revision",
"eventTimestamp": "2026-04-07T18:27:30.912Z",
"data": {
"notificationId": "f6a7b8c9-d0e1-2345-6789-abcdef012345",
"entity_id": "8d976a23-b865-4fcd-9165-ddc0aedaf614",
"document_id": "8d976a23-b865-4fcd-9165-ddc0aedaf614",
"transaction_id": "8d976a23-b865-4fcd-9165-ddc0aedaf614",
"participant_id": "8d976a23-b865-4fcd-9165-ddc0aedaf614"
}
}
revision-completed-by-participant
Triggered when a participant has completed signing a document. All tags on the document that are for this participant have either been filled in or (if they weren't required) have been skipped. A revision has been saved with all of their changes flattened onto the document, instead of as XFDF.
Note: This event includes additional fields: document_id and participant_id.
{
"event": "revision-completed-by-participant",
"entity": "revision",
"eventTimestamp": "2026-04-07T18:29:45.201Z",
"data": {
"notificationId": "a7b8c9d0-e1f2-3456-789a-bcdef0123456",
"entity_id": "8d976a23-b865-4fcd-9165-ddc0aedaf614",
"document_id": "8d976a23-b865-4fcd-9165-ddc0aedaf614",
"transaction_id": "8d976a23-b865-4fcd-9165-ddc0aedaf614",
"participant_id": "8d976a23-b865-4fcd-9165-ddc0aedaf614"
}
}
Best Practices
1. Respond Quickly
Always respond with a 200 OK status code as soon as you receive the webhook. Process the webhook data asynchronously to avoid timeouts.
// Example: Express.js webhook handler
app.post('/webhooks/stewart-sign', (req, res) => {
// Immediately respond with 200 OK
res.status(200).send('OK');
// Process the webhook asynchronously
processWebhook(req.body).catch(err => {
console.error('Error processing webhook:', err);
});
});
2. Implement Idempotency
Use the notificationId field to prevent processing the same event multiple times. Store processed notification IDs and check before processing.
async function processWebhook(payload) {
const { notificationId } = payload.data;
// Check if already processed
const alreadyProcessed = await db.notifications.exists(notificationId);
if (alreadyProcessed) {
return; // Skip duplicate
}
// Process the event
await handleEvent(payload);
// Mark as processed
await db.notifications.create({ id: notificationId, processedAt: new Date() });
}
3. Use eventTimestamp for Chronological Ordering
Webhooks may arrive out of order due to network conditions or retries. Use the eventTimestamp field to determine the correct chronological sequence of events rather than relying on delivery order.
async function processWebhook(payload) {
const { eventTimestamp, event } = payload;
const { entity_id } = payload.data;
// Get the last processed event for this entity
const lastEvent = await db.entityEvents.findOne({ entity_id });
// Only process if this event is newer than the last one we processed
if (lastEvent && lastEvent.eventTimestamp >= eventTimestamp) {
console.log(`Skipping out-of-order event: ${event} (${eventTimestamp})`);
return;
}
// Process the event
await handleEvent(payload);
// Store the timestamp of the last processed event
await db.entityEvents.upsert({
entity_id,
event,
eventTimestamp,
processedAt: new Date().toISOString(),
});
}
Key details about eventTimestamp:
- Format: ISO 8601 UTC (e.g.,
2026-04-07T18:25:43.511Z) - Represents: The time the event was generated by the system, not when the webhook was delivered
- Consistent across retries: If a webhook is retried, the
eventTimestampremains the same as the original event - Always present: This field is never null or omitted
- Sortable: ISO 8601 timestamps are lexicographically sortable — you can compare them as strings
4. Use Entity IDs for Detailed Information
The webhook payload provides the entity_id and transaction_id of the affected resources. Use these IDs to fetch full details via the API if needed.
async function handleTransactionCreated(payload) {
const { transaction_id } = payload.data;
// Fetch full transaction details
const transaction = await stewartSignAPI.getTransaction(transaction_id);
// Process with full context
await processTransaction(transaction);
}
Troubleshooting
Webhook Not Received
- Verify your endpoint is accessible via HTTPS
- Check firewall rules and network configurations
- Ensure your server responds within the timeout period (5 seconds)
- Contact Stewart Sign support to verify webhook configuration
Duplicate Webhooks
- Implement idempotency using
notificationId - Check for retry logic triggering duplicates
- Review your endpoint response codes
Out-of-Order Webhooks
- Use the
eventTimestampfield to determine the correct chronological order of events - Do not rely on webhook delivery order — network conditions and retries can cause events to arrive out of sequence
- Compare
eventTimestampvalues to determine which event occurred first
Missing Event Data
- Different events have different data fields (e.g., revision events include
document_idandparticipant_id) - Status change events include a
statusfield - Use the
entity_idandtransaction_idto fetch complete details via the API - Contact support if specific fields are needed in webhook payloads
Support
For help with webhook configuration or troubleshooting contact Stewart Sign support team.