Poll a Sume bulk-run queue in Python and list items not completed

A short asyncio script that polls GET /v1/format-run-queues/{id} until the queue is completed, prints the counts and lists every item that did not complete.

4 min readSume
All posts

A Sume bulk queue has no webhook, so for the queue as a whole you poll GET /v1/format-run-queues/{id}. The queue is done when its status is completed, but the docs say completed means every item is terminal and not that every item succeeded. The script below waits for that status, prints counts and lists the items that are not completed.

What does the queue response give you?

Queue fields used by the script, from the Sume bulk runs docs (read 2026-10-01)
FieldMeaning
statusqueued, running or completed
countstotal, queued, running, completed, failed, canceled
items[]One row per submitted item, in order: index, status, run_id, error
status_urlThe URL to poll

What is the script?

It uses only the standard library, runs the blocking request in a thread, and wraps everything in asyncio.run(main(...)) so it works as a plain script. Read the key and the queue id from the environment.

import asyncio, json, os, urllib.request

BASE = "https://api.sume.com/v1/format-run-queues/"

def get(qid):
    req = urllib.request.Request(
        BASE + qid,
        headers={"Authorization": "Bearer " + os.environ["SUME_API_KEY"]},
    )
    with urllib.request.urlopen(req, timeout=30) as r:
        return json.load(r)["data"]

async def main(qid):
    while True:
        q = await asyncio.to_thread(get, qid)
        if q["status"] == "completed":
            break
        await asyncio.sleep(30)
    print(q["counts"])
    for item in q["items"]:
        if item["status"] != "completed":
            print(item["index"], item["status"], item["run_id"], item["error"])

asyncio.run(main(os.environ["QUEUE_ID"]))

What do I do with the items it prints?

Each printed row has an index that matches the order you submitted, so you can look up the original item. For a failed child, read its receipt at GET /v1/format-runs/{run_id}. Re-submit only the failed items as a new queue with a fresh Idempotency-Key; replaying the old key returns the old queue. The retry post goes through that.

Should I poll or use item webhooks?

Use both for different jobs. A per-item communication.webhook_url delivers one signed format.run.terminal event as each child ends, which suits uploading a clip the moment it is ready. The poll gives you the single moment the whole batch is terminal, which suits a final report. A lost delivery can be sent again with POST /v1/format-runs/{run_id}/webhook/redeliver.

Why does the script not stop on the first failure?

A queue keeps draining the other items when one fails, and a failed child frees its slot for the next one. So the right moment to report is when every item is terminal, which is what completed means. Stopping early on the first failure would leave you with a partial picture and a queue still running in the background, still spending.

What are the limits?

  • The key needs formats:read; a service-account key is refused for Format runs and queues.
  • Thirty seconds between polls is a choice. A shorter delay does not make renders finish faster.
  • There is no queue-cancel endpoint, so a script that gives up leaves the queue running; cancel children with POST /v1/format-runs/{run_id}/cancel.
  • If the script is interrupted, run it again with the same queue id. Nothing is lost, because the queue lives on Sume's side.
  • For a per-item callback, set communication.webhook_url on each item and verify the signature, refusing an empty secret.

Sources

Related posts

More in Developers

All Developers posts

Written by Sume