Skip to main content

Delivery History

View every delivery attempt with status, HTTP codes, and timing, inspect request and response bodies, replay failed attempts, and clear the delivery log.

The delivery history tracks every attempt to deliver a payload to a destination. Each attempt is recorded as a delivery item with status, timing, HTTP response code, and optional request/response bodies. Use this endpoint to audit delivery performance and debug failures.

Query items by binding_id or destination_id to narrow results to a specific delivery path. Filter by status to find failures (failed) or in-progress attempts (in_flight). Use GET /v1/delivery/items/:id to inspect the full request and response bodies for a single attempt.

Each item includes an idempotency_key (deterministic SHA-256 of binding ID and event ID) that is sent on the wire so receivers can deduplicate. The attempt field is 1-indexed — multiple items with the same event_id and binding_id represent retries of the same delivery. Status values are in_flight, succeeded, or failed.

Use POST /v1/delivery/items/:id/replay to re-enqueue a specific attempt with a fresh attempt number but the same idempotency key. For terminal failures, check the DLQ endpoint instead — items that exhausted all retries are moved there automatically. Pair history inspection with binding and destination detail to diagnose delivery issues end-to-end.

Request and response bodies are truncated to 10 KB and retained for a configurable period (default 30 days). After the retention period, bodies are nulled but metadata (status, HTTP code, duration, error code) is preserved indefinitely.
GET/v1/delivery/items

Query parameters

binding_idstringFilter by binding ID.
destination_idstringFilter by destination ID.
statusstringFilter by status: `in_flight`, `succeeded`, `failed`.
limitintegerMaximum results to return. Default: 50
offsetintegerNumber of results to skip. Default: 0

Response

Response fields

itemsarrayArray of delivery attempt records.
items[].idstringDelivery item UUID.
items[].binding_idstringBinding that produced this attempt.
items[].event_idstringOutbox event ID (BIGSERIAL, as string).
items[].idempotency_keystringSHA-256 idempotency key sent on the wire.
items[].statusstring`in_flight`, `succeeded`, or `failed`.
items[].attemptintegerAttempt number (1-indexed).
items[].http_statusinteger | nullHTTP response status code, if applicable.
items[].error_codestring | nullMachine-readable error code on failure.
items[].error_messagestring | nullHuman-readable error message on failure.
items[].duration_msinteger | nullDelivery duration in milliseconds.
items[].completed_atstring | nullISO 8601 completion timestamp.
items[].created_atstringISO 8601 attempt creation timestamp.
totalintegerTotal number of matching delivery items.

Response

{
  "items": [
    {
      "id": "e5f6a7b8-c9d0-1234-efab-456789012345",
      "binding_id": "d4e5f6a7-b8c9-0123-defa-345678901234",
      "event_id": "98765",
      "idempotency_key": "a3f8c2d1e4b7",
      "status": "succeeded",
      "attempt": 1,
      "http_status": 200,
      "error_code": null,
      "error_message": null,
      "duration_ms": 234,
      "completed_at": "2024-09-15T11:00:00.000Z",
      "created_at": "2024-09-15T10:59:59.000Z"
    }
  ],
  "total": 1280
}

Errors

Error responses

401unauthorizedMissing or invalid API key.
429rate_limitedToo many requests. Retry after the period indicated in the Retry-After header.
GET/v1/delivery/items/:id

Response

Response fields

idstringDelivery item UUID.
binding_idstringBinding that produced this attempt.
event_idstringOutbox event ID.
idempotency_keystringSHA-256 idempotency key sent on the wire.
statusstring`in_flight`, `succeeded`, or `failed`.
attemptintegerAttempt number.
http_statusinteger | nullHTTP response status code.
error_codestring | nullMachine-readable error code.
error_messagestring | nullHuman-readable error message.
request_bodystring | nullTruncated request body (up to 10 KB). Nulled after retention period.
response_bodystring | nullTruncated response body (up to 10 KB). Nulled after retention period.
duration_msinteger | nullDelivery duration in milliseconds.
completed_atstring | nullISO 8601 completion timestamp.
created_atstringISO 8601 attempt creation timestamp.

Response

{
  "id": "e5f6a7b8-c9d0-1234-efab-456789012345",
  "binding_id": "d4e5f6a7-b8c9-0123-defa-345678901234",
  "event_id": "98765",
  "idempotency_key": "a3f8c2d1e4b7",
  "status": "succeeded",
  "attempt": 1,
  "http_status": 200,
  "error_code": null,
  "error_message": null,
  "request_body": "{"vendor":"Acme Corp","total":4950.00}",
  "response_body": "{"ok":true}",
  "duration_ms": 234,
  "completed_at": "2024-09-15T11:00:00.000Z",
  "created_at": "2024-09-15T10:59:59.000Z"
}

Errors

Error responses

401unauthorizedMissing or invalid API key.
404not_foundNo delivery item with this ID exists for your organization.
429rate_limitedToo many requests. Retry after the period indicated in the Retry-After header.
POST/v1/delivery/items/:id/replay

Response

Response fields

enqueuedbooleanAlways true when the replay was accepted.
idempotency_keystringThe idempotency key that will be sent on the new attempt — identical to the original so receivers can deduplicate.

Response

{
  "enqueued": true,
  "idempotency_key": "a3f8c2d1e4b7"
}

Errors

Error responses

400bad_requestReplay is not available in master view (organization-wide API key).
401unauthorizedMissing or invalid API key.
404not_foundNo delivery item with this ID exists for your organization.
429rate_limitedToo many requests. Retry after the period indicated in the Retry-After header.

Clearing the delivery log

Two write routes remove history rows. DELETE /v1/delivery/items/:id deletes one attempt record; DELETE /v1/delivery/items bulk-clears the log, honouring the same binding_id, destination_id, and status filters as the list route, so "clear only failed attempts" or "clear one binding's log" work with a single call. With no filters, every row for the organization is removed. Both routes require the write scope and an organization-scoped API key.

DELETE/v1/delivery/items

Query parameters

binding_idstringOnly clear attempts for this binding.
destination_idstringOnly clear attempts for bindings targeting this destination.
statusstringOnly clear attempts with this status: `in_flight`, `succeeded`, `failed`.
DELETE/v1/delivery/items/:id
Deleting history rows is an admin cleanup, not a replay operation. A dead-letter row that references a deleted item is de-linked and stays in the DLQ, so terminal failures remain visible until you dismiss or replay them there.

Frequently asked questions

What is the idempotency key?+
The idempotency key is a deterministic SHA-256 hash of the binding ID and event ID. It is sent on the wire (as an HTTP header, object metadata, or filename token depending on the connector) so receivers can deduplicate repeated deliveries.
How does replay differ from DLQ replay?+
Item replay re-enqueues a specific (binding, event) pair with a new attempt number. DLQ replay deletes the dead-letter row and re-enqueues with attempt=1. Both preserve the same idempotency key so receivers can deduplicate.
How long are delivery request and response bodies kept?+
Bodies are truncated to 10 KB and retained for a configurable period, 30 days by default. After that they are nulled, while metadata (status, HTTP code, duration, error code) is preserved indefinitely.
Does clearing the delivery log remove DLQ rows?+
No. DELETE /v1/delivery/items removes attempt records only. A dead-letter row referencing a deleted item is de-linked rather than removed; manage the DLQ through its own dismiss and replay routes.