Preflight a Sume image request against capability descriptors
Catch unsupported_parameter before you send: fetch the model descriptors, then check each field of your request against enum, range and boolean types.

Sume publishes what each image model accepts as typed capability descriptors, and rejects anything else with 400 unsupported_parameter. A preflight function can check your request body against those descriptors first, so you find a bad aspect_ratio or an unsupported reference count in your own code. The check is local; the descriptors come from one catalog call.
Descriptor types
From the Image API docs.
| Type | Meaning |
|---|---|
| enum | Discrete allowlist of string values |
| range | Any integer within min and max |
| boolean | Supported when present, unsupported when absent |
The preflight
It reports problems as a list. Free-text fields such as prompt are boolean descriptors, so only presence is checked. input_references is checked by length.
def preflight(body, params):
problems = []
for key, val in body.items():
if key in ("model", "metadata", "mode", "webhook_url", "wait_timeout_seconds"):
continue
d = params.get(key)
if d is None:
problems.append(f"{key}: not supported")
elif d["type"] == "enum" and val not in d["values"]:
problems.append(f"{key}: {val!r} not in {d['values']}")
elif d["type"] == "range":
size = len(val) if isinstance(val, list) else val
if not d["min"] <= size <= d["max"]:
problems.append(f"{key}: {size} outside {d['min']}-{d['max']}")
return problemsWire it up
Fetch supported_parameters for the model from GET /v1/images/models, call preflight(body, params), and send the request only if the list is empty. Cache the catalog for a short time, not forever.
Limits
The check cannot know about token-priced quality reservations or content policy, and it skips routing fields. Treat it as a first filter; the API stays the authority.
Sources
Related posts
More in Developers
- Pub/Sub push subscription for Sume events: ack codes and dedupe
Pub/Sub push redelivers on any code outside 102, 200, 201, 202 and 204. Fan Sume completions through Pub/Sub safely with run_id and job_id dedupe.
- Python 3.15 TaskGroup.cancel: stop at the first Sume job done
Python 3.15 adds TaskGroup.cancel. Watch several Sume jobs and stop the other watchers when the first one completes, without cancelling the paid jobs.
- Python asyncio.timeout around a Sume job poll: a hard budget
Wrap a Sume status loop in asyncio.timeout so it stops at a fixed budget and returns still_running, leaving the job alone. A short version, run against a mock.
- Python httpx and asyncio: submit and poll a Sume image job
A runnable Python recipe: submit a Sume image job in async mode with an Idempotency-Key, poll with httpx and asyncio, honor retry-after, fetch the artifacts.
Written by Sume