Skip to Content
API ReferenceWebhook event catalog

Webhook event catalog

Every webhook event uses the same envelope. The event field identifies the event; data contains the event-specific payload. The body is the event object as-is — there is no separate event wrapper or event ID inside the body.

{ "event": "<event-type>", "timestamp": "2026-06-01T14:00:00Z", "data": { ... } }

The delivery ID and event name travel in request headers, not in the body — read X-VoxBurst-Delivery-Id and X-VoxBurst-Event from the request. All delivery requests include the headers documented in Delivery Headers. Always verify X-VoxBurst-Signature before processing.

Exception: the test delivery (POST /v1/webhooks/test) uses a different shape — see test.webhook below.


post.created

Fires when: A post is successfully created (draft or scheduled) via POST /v1/posts or POST /v1/posts/bulk.

{ "event": "post.created", "timestamp": "2026-06-01T10:00:00Z", "data": { "postId": "post_abc123", "status": "DRAFT", "scheduledFor": null, "platforms": ["TWITTER", "INSTAGRAM"], "createdById": "usr_creator1" } }
FieldTypeDescription
postIdstringPost ID
statusstring"DRAFT" or "SCHEDULED"
scheduledForstring | nullISO 8601 scheduled time, or null if draft
platformsstring[]Platform constants this post targets — UPPERCASE (e.g. "TWITTER")
createdByIdstring | nullUser ID who created the post, or null if system-created

post.scheduled

Fires when: A post transitions to scheduled status — either created with a scheduledFor time, or updated from draft to scheduled.

{ "event": "post.scheduled", "timestamp": "2026-06-01T10:05:00Z", "data": { "id": "post_abc123", "content": "Check out our new launch! 🚀", "status": "SCHEDULED", "scheduledFor": "2026-06-15T14:00:00Z", "accountIds": ["acc_abc123"], "contentType": "TEXT" } }

Note: post.scheduled uses a different data shape from post.created — it carries the full post (id, content) plus accountIds (social account IDs scheduled to publish) and contentType ("TEXT" for text posts). scheduledFor is always set.


post.published

Fires when: Publishing completes — all platforms succeeded ("PUBLISHED") or at least one succeeded with at least one failed ("PARTIAL").

There is no separate post.partial event. Check data.status in every post.published handler to detect partial failures. Always inspect data.platforms for per-platform outcomes.

All platforms succeeded (status: "PUBLISHED")

{ "event": "post.published", "timestamp": "2026-06-15T14:00:05Z", "data": { "id": "post_abc123", "workspaceId": "ws_xyz", "content": "Check out our new launch! 🚀", "status": "PUBLISHED", "publishedAt": "2026-06-15T14:00:05Z", "platforms": [ { "platform": "TWITTER", "status": "PUBLISHED", "platformPostId": "1234567890123456789", "platformPostUrl": "https://x.com/user/status/1234567890123456789", "publishedAt": "2026-06-15T14:00:04Z" }, { "platform": "INSTAGRAM", "status": "PUBLISHED", "platformPostId": "17854360229135492", "platformPostUrl": "https://www.instagram.com/p/ABC123/", "publishedAt": "2026-06-15T14:00:05Z" } ] } }

Partial failure (status: "PARTIAL")

{ "event": "post.published", "timestamp": "2026-06-15T14:00:06Z", "data": { "id": "post_abc123", "workspaceId": "ws_xyz", "content": "Check out our new launch! 🚀", "status": "PARTIAL", "publishedAt": "2026-06-15T14:00:06Z", "platforms": [ { "platform": "TWITTER", "status": "PUBLISHED", "platformPostId": "1234567890123456789", "platformPostUrl": "https://x.com/user/status/1234567890123456789", "publishedAt": "2026-06-15T14:00:04Z" }, { "platform": "INSTAGRAM", "status": "FAILED", "error": { "code": "MEDIA_REJECTED", "message": "Media format not supported: image must be JPEG" } } ] } }
FieldTypeDescription
idstringPost ID
workspaceIdstringWorkspace ID
contentstringPost text
statusstring"PUBLISHED" (all succeeded) or "PARTIAL" (some failed)
publishedAtstringISO 8601 completion timestamp
platforms[]arrayPer-platform publish results
platforms[].platformstringPlatform constant — UPPERCASE (e.g. "TWITTER")
platforms[].statusstring"PUBLISHED" or "FAILED" — UPPERCASE
platforms[].platformPostIdstring | undefinedPlatform’s native post ID (success only)
platforms[].platformPostUrlstring | undefinedPublic URL of the post (success only)
platforms[].publishedAtstring | undefinedISO 8601 timestamp (success only)
platforms[].errorobject | undefined{ code, message } — failure only

Platform and status strings in webhook payloads are always UPPERCASE. This differs from REST API responses, which use lowercase.


post.failed

Fires when: Publishing completed and all platforms failed.

{ "event": "post.failed", "timestamp": "2026-06-15T14:00:08Z", "data": { "id": "post_abc123", "workspaceId": "ws_xyz", "content": "Check out our new launch! 🚀", "status": "FAILED", "publishedAt": "2026-06-15T14:00:08Z", "platforms": [ { "platform": "TWITTER", "status": "FAILED", "error": { "code": "ACCOUNT_DISCONNECTED", "message": "OAuth token expired or revoked" } }, { "platform": "INSTAGRAM", "status": "FAILED", "error": { "code": "PUBLISH_ERROR", "message": "Media format not supported" } } ] } }

Same schema as post.published. Use POST /v1/posts/:id/retry or POST /v1/posts/:id/platforms/:platformId/fix to recover.


post.draft.approved

Fires when: A post in an approval workflow reaches its final approval step and is queued for publishing.

{ "event": "post.draft.approved", "timestamp": "2026-06-01T11:30:00Z", "data": { "postId": "post_abc123", "approverId": "usr_approver1", "stepOrder": 2, "comment": "Looks good, approved." } }
FieldTypeDescription
postIdstringPost that was approved
approverIdstring | nullUser ID who approved, or null if system-approved
stepOrderintegerWhich approval step was completed
commentstring | nullReviewer’s comment, if any

post.state_changed

Fires when: Any state-changing post lifecycle event occurs. This is an umbrella event — alongside it, VoxBurst also emits a dedicated event (e.g. post.published, post.failed) for key transitions. Subscribe to post.state_changed as a catch-all for post state changes.

{ "event": "post.state_changed", "timestamp": "2026-06-15T14:00:08Z", "data": { "postId": "post_abc123", "eventType": "PUBLISHED", "platform": null, "actor": null, "details": null, "error": null } }
FieldTypeDescription
postIdstringPost whose state changed
eventTypestringPost lifecycle event type that triggered the change (e.g. PUBLISHED, FAILED, CANCELLED)
platformstring | nullPlatform involved, lowercase, or null when not platform-specific
actorobject | nullWho triggered the change, if user-initiated
detailsobject | nullExtra details about the event, if any
errorobject | nullError details, for failed transitions

account.connected

Fires when: A social account is successfully connected via the OAuth callback.

{ "event": "account.connected", "timestamp": "2026-06-01T09:00:00Z", "data": { "accountId": "acc_abc123", "workspaceId": "ws_xyz", "platform": "INSTAGRAM", "username": "brandname" } }
FieldTypeDescription
accountIdstringVoxBurst account ID
workspaceIdstringWorkspace ID
platformstringPlatform constant — UPPERCASE
usernamestring | nullPlatform username or handle

account.disconnected

Fires when: A social account is disconnected via DELETE /v1/accounts/:id or revoked by the platform.

{ "event": "account.disconnected", "timestamp": "2026-06-01T15:00:00Z", "data": { "accountId": "acc_abc123", "workspaceId": "ws_xyz", "platform": "TWITTER", "reason": "user_disconnected" } }
FieldTypeDescription
accountIdstringVoxBurst account ID
workspaceIdstringWorkspace ID
platformstringPlatform constant — UPPERCASE
reasonstring"user_disconnected", "token_revoked", "token_expired", or "platform_suspended"

account.error

Fires when: A connected account encounters a token error (expired, revoked) that prevents publishing.

{ "event": "account.error", "timestamp": "2026-06-01T16:00:00Z", "data": { "accountId": "acc_abc123", "workspaceId": "ws_xyz", "platform": "LINKEDIN", "error": "Token expired" } }
FieldTypeDescription
accountIdstringVoxBurst account ID
workspaceIdstringWorkspace ID
platformstringPlatform constant — UPPERCASE
errorstringHuman-readable error description

When you receive this event, prompt the user to reconnect the account via the OAuth flow.


media.uploaded

Fires when: A media file completes the S3 upload and processing pipeline — status transitions to READY.

{ "event": "media.uploaded", "timestamp": "2026-06-01T10:01:30Z", "data": { "mediaId": "media_abc1234567890abc12345678", "filename": "campaign-banner.jpg", "contentType": "image/jpeg", "sizeBytes": 204800 } }
FieldTypeDescription
mediaIdstringVoxBurst media ID
filenamestringDisplay filename
contentTypestringMIME type (always image/jpeg after normalization for PNG/WebP)
sizeBytesintegerFile size in bytes (post-normalization)

media.ready and media.processing_failed are internal events and are not deliverable via webhooks. To track processing failures, poll GET /v1/media/:id until status is READY or FAILED.


post.deleted

Fires when: A post is deleted (e.g. via DELETE /v1/posts/:id).

{ "event": "post.deleted", "timestamp": "2026-06-01T12:00:00Z", "data": { "postId": "post_abc123", "eventType": "DELETED", "platform": null, "details": null, "error": null } }
FieldTypeDescription
postIdstringPost that was deleted
eventTypestringPost lifecycle event type — "DELETED"
platformstring | nullPlatform involved, or null when the event is not platform-specific
detailsobject | nullExtra details about the event, if any
errorobject | nullError details, for failed transitions

test.webhook

Fires when: You call the test endpoint (POST /v1/webhooks/test). Sent to the endpoint under test; not subscribed to and subject to a different payload shape than the standard envelope.

{ "id": "evt_test_7f3ab1c2d4e5f6a7", "event": "test.webhook", "created": "2026-06-01T09:00:00Z", "data": { "message": "This is a test webhook delivery from VoxBurst." } }
FieldTypeDescription
idstringTest event ID (evt_test_ prefix)
eventstringAlways "test.webhook"
createdstringISO 8601 timestamp — note the field name is created, not timestamp
data.messagestringFixed test message
Last updated on