ComfyUI Node

API Image

Run a Model You Can't Download, Inside Your Graph

By Einzieg·Created a day ago·Updated a day ago· 0
API Image
  • image
  • mask
  • images
  • response_json
  • metadata_json
provider_id
model_id
operation
prompt
parameters{}
cache_modereuse
request_nonce0

Why you'd want it

There's a category of model you cannot download at any VRAM - Nano Banana, GPT Image, Seedream, the closed frontier. No weights, no local option, the API is the only door, and API Image is a generic keyhole for it: an HTTP call to a model you configured, sitting where a sampler normally would, returning what comes back as an ordinary IMAGE you can preview, save, upscale or feed anywhere.

It's also the honest answer to "my card can't do it" - the same node calling a hosted FLUX or Qwen-Image-Edit is renting a GPU per call instead of buying one. Keep those moves separate: one is a capability you'll never have locally, the other is a convenience better hardware would solve. And like its sibling nodes, this pack has almost no community trail yet, so you're early; in exchange you get a short, MIT, readable source - not a small thing for the category that holds credentials by design.

How it works

Two operations, two genuinely different requests. image is text-to-image: the stock Images · Generate template POSTs JSON to /images/generations with model, prompt, size and n. image_edit is the multipart path: Images · Edit POSTs to /images/edits, uploading your input as image[] and, if you wired one, the mask as a mask file. operation picks a template binding - no binding, and you get unsupported_operation.

Responses come back through a small JSONPath-ish selector like $.data[*] plus image_value = auto, which understands a bare URL string, b64_json, url or raw base64 - and providers that stream image/* bytes need no mapping at all. Returned URLs get fetched, redirects followed, but your credential is deliberately not forwarded to a different host, so an image CDN never gets handed your key.

Then the bytes become IMAGE tensors: RGB, EXIF-rotated, one per returned image. Because they arrive as a list, each keeps its original size - nothing is resized to match anything. Perfect for a 1536×1024 next to a 1024×1536; a problem if you meant to stack them into a video node.

The call runs interruptibly, so Cancel works while you wait, and paid submissions are never retried. Slow providers should use a template with the optional async polling block: a task ID polled every 2s (600s default timeout), progress reported on the node, and an optional remote cancellation that cancels the wait but can't guarantee a refund.

The inputs that matter

provider_id and model_id are set by the node's own model picker - leave them and you'll get an error rather than a rogue billed call.

  • operation - image or image_edit. Pick the edit path and you must wire image, or you get missing_image.
  • prompt - multiline, with a "Connect input" socket so another node can drive it.
  • parameters - JSON, default {}, connectable. size and n come from the stock templates, but only if the template references them; unreferenced keys are dropped silently. API Parameter chains are the tidy way to build this.
  • image / mask - the edit image, and a mask with a real convention trap. ComfyUI paints 1 as the area to edit, while image-edit APIs read the transparent region as the edit region, so the node inverts your mask into PNG alpha. The mask only uploads if the template has a file entry with source: mask - the stock edit template does, a hand-rolled one may not, and then your masking does nothing.
  • cache_mode (reuse / refresh) and request_nonce - reuse re-runs an unchanged graph from cache instead of billing you again. Change the nonce for a fresh result; refresh calls every run, and also poisons ComfyUI's cache for every node behind it. A nonce is not a seed.

Outputs: images - an IMAGE list, straight into PreviewImage, SaveImage or an upscaler. Ask for n: 2 and you get two list items; since sizes are preserved rather than unified, nodes expecting a stack will complain. Also response_json (raw response, secrets and base64 stripped) and metadata_json (request_id, model, duration_ms, and usage if the template maps one) - the dull output that pays for itself the first time you wonder what a session cost.

Install

Manager search comfyui-custom-api, or the git route with ComfyUI's own interpreter:

cd ComfyUI/custom_nodes
git clone https://github.com/Einzieg/ComfyUI-custom-api.git
/path/to/ComfyUI/venv/bin/python -m pip install -r ComfyUI-custom-api/requirements.txt

aiohttp, Pillow, numpy. No weights, no download step. Restart, refresh the browser. Then configure a provider once from the top-bar API panel: Base URL, auth, Save & fetch models, and bind Images · Generate / Images · Edit to the models that support them. Discovery lists IDs and never guesses capabilities - the number-one reason a fetched model doesn't show up in the picker.

Where people get burned

unsupported_operation - no template bound for the image operation on that model.

Nothing happens, twice, and you were only billed once. That's reuse doing its job.

Timeout at 120 seconds. Slow image models blow past the provider default; raise it in the provider's advanced network settings or move to an async provider template. The shipped Async image template is labelled "customize before use" - its paths and status strings are placeholders, not a working provider.

The download fails even though the API answered. If a provider hands back a URL on a different host that also wants the auth header, the node won't send your key there. That's a privacy feature working; a failed fetch is the cost. Prefer base64 or signed URLs.

Cost, the real one. Every run is metered and you can't see the number until the invoice. Use reuse, watch metadata_json, and remember your prompt and reference images leave the machine by design - whatever the provider's filter refuses, your graph refuses too.

CategoryModel API

Inputs (9)

NameTypeDefaultDescription
provider_idSTRINGSelect a provider using the model picker.
model_idSTRINGStable model configuration ID.
operationCOMBO2 options: image, image_edit
promptSTRING
parametersSTRING{}JSON parameters; can also be connected from another node.
cache_modeCOMBOreuse2 options: reuse, refresh
request_nonceINT00–2147483647Change this number to make a new API request.
imageoptIMAGE
maskoptMASK

Outputs (3)

NameTypeDescription
imagesIMAGE
response_jsonSTRING
metadata_jsonSTRING