next_poll_after_seconds vs recommended_poll_interval_seconds
Which delay a Sume poller should sleep: next_poll_after_seconds, recommended_poll_interval_seconds, or retry-after. Null rules, a fallback, and read budgets.

Sleep for next_poll_after_seconds when a Sume status response carries it: the OpenAPI schema calls it the suggested minimum delay before the next status poll, and null for terminal jobs. recommended_poll_interval_seconds is the default SDK and CLI cadence for non-terminal jobs, and the HTTP retry-after header is the wait Sume sends on a 429. When none is present, use exponential backoff.
Descriptions below are from the JobStatusResponse schema in the API reference and the polling rule on Jobs and results. The header semantics come from MDN's Retry-After page. All read 2026-10-02.
What does each delay field mean?
Three body fields and one header sound alike. They answer different questions, and none of them is a promise about how long the job will take.
| Field | Where | Meaning | Null when |
|---|---|---|---|
next_poll_after_seconds | status and submit body | Suggested minimum delay before the next status poll | The job is terminal |
recommended_poll_interval_seconds | status and submit body | Default SDK/CLI polling cadence for non-terminal jobs | The job is terminal |
retry_after_seconds | status and submit body | Backoff hint when Sume has delayed the next worker attempt | No special backoff applies |
retry-after | 429 response header | Seconds to wait before retrying | Only sent on a 429 |
Which one should my loop sleep on?
The docs say to honor next_poll_after_seconds when it is present and back off otherwise. Using recommended_poll_interval_seconds as the second choice is a reasonable reading of its description, but it is my suggestion, not a documented rule. A small helper keeps that order in one place:
def next_delay(st: dict, current: float) -> float:
return (st.get("next_poll_after_seconds")
or st.get("recommended_poll_interval_seconds")
or min(current * 2, 30))
print(next_delay({"next_poll_after_seconds": 3}, 2)) # 3
print(next_delay({}, 2)) # 4What about a 429 on the status call itself?
Status reads have their own budget. Sume splits request budgets into reads (any GET or HEAD) and writes, so a tight status loop cannot 429 your own submits. On the Free plan the read budget is 4800 per minute and the write budget is 120; Pro is 12000 and 300. A 429 names the budget in error.details.scope as read or write.
If a poll gets a 429, wait for the retry-after seconds, then continue. Read ratelimit-remaining rather than counting requests yourself. Per the authentication page, the headers describe whichever budget the current request spent from.
When does polling stop?
Poll until terminal is true, or until your own deadline. Both delay fields are null on a terminal job, which is a second signal to stop. The deadline is client-side: the docs suggest 20 minutes for video as a reasonable client deadline, and say a timeout does not cancel the job, so you have only stopped watching.
For many jobs, prefer a webhook with polling kept as a backup, rather than shortening the interval.
Sources
Related posts
More in Developers
- Sume queue capacity: max(3, concurrency x 5), and 7 jobs on Free
Sume's default queue capacity is max(3, concurrency_limit x 5). On Free that is 5 queued plus 1 processing, so a seventh live generation job gets queue_full.
- verifyWebhook returns false during a Sume secret rotation
The npm build of @sume-com/sdk 0.2.0 compares the signature header for equality, so rotation deliveries with two signatures fail. A 21-line fix.
- Does the Sume SDK retry POSTs? Only with an Idempotency-Key
createSumeClient retries 408, 429 and 5xx twice with backoff, but replays a POST only when it carries an Idempotency-Key. How to set it and tune maxRetries.
- @sume-com/sdk waitForJob is not exported: a 26-line replacement
The docs show waitForJob, but the npm build of @sume-com/sdk 0.2.0 does not export it. Here is a fetch version with 429 tolerance and a deadline.
Written by Sume