Reliability
Delivery policy
Control retries, backoff, timeouts and delivery rate for each destination.
Each URL destination has a delivery policy: how long to wait for an answer, which answers are worth retrying, how long to wait between tries, and how fast to send. Defaults are sensible; change them when your service has its own limits.
What counts as a failure
Ensue retries answers that might succeed later, and fails fast on ones that never will.
| Response | Result |
|---|---|
2xx |
Delivered. |
408, 409, 425, 429, 5xx, timeout, network error |
Retried. |
Other 4xx (for example 400, 401, 404, 422) |
Failed at once. Your service rejected the request; trying again would not help. |
3xx |
Failed. Redirects are never followed. |
Retry-After: -1 or x-ensue-retry: never |
Failed at once, on any non-2xx answer. Your service can say “never retry this”. |
Change which answers retry with retry.retry_on, an array drawn from 5xx, 429, 408, 409, 425, timeout and network, or a specific status code.
Retries and backoff
By default a failed delivery is retried up to 7 times, after 5 seconds, 30 seconds, 2 minutes, 10 minutes, 1 hour, 2 hours and 4 hours. That is eight attempts across about seven hours. Each wait is spread randomly by up to half in either direction so retries from many events don’t land together.
{
"max_attempts": 12,
"retry": { "schedule": "exponential", "interval_seconds": 30, "max_window_hours": 24 }
}
| Setting | Meaning |
|---|---|
max_attempts |
Total attempts before the event becomes a dead letter. |
retry.schedule |
default (the schedule above), linear (the same wait every time) or exponential (doubling from interval_seconds, capped at one day). |
retry.interval_seconds |
The base wait for linear and exponential. |
retry.max_window_hours |
A cut-off after which an event stops retrying, whatever attempts remain. |
retry.retry_on |
Which responses retry. |
Retry-After
If your service answers 429 or 503 with a Retry-After header, in seconds or as an HTTP date, Ensue honours it, up to four hours. The header can only push a retry later, never earlier.
Timeouts
timeout_ms is how long Ensue waits for an answer: 1,000 to 30,000 milliseconds, default 15,000. If your handler needs longer, accept the event quickly and process it in the background, or use a deferred acknowledgement.
Rate and concurrency
| Setting | Meaning |
|---|---|
max_in_flight |
The most deliveries running at once. |
rate_per_second with rate_period |
The most deliveries started in each second, minute or hour. |
Events queue in Ensue and drain at the rate you set instead of failing and retrying against a downstream limit. For per-tenant fairness, use delivery groups.
Pausing a destination
Pausing holds every event for that destination until you resume. Nothing is lost, and nothing is retried while paused.
Manual retries
Any event can be retried by hand, even after it has given up. A manual retry sends one attempt immediately and is not counted against the schedule. See Replay and dead letters.