flux-1-kontext-max is a single hiapi model id that does two jobs: text-to-image when you send only a prompt, and single-image editing when you add input_image. This guide shows both calls in curl and Python, with the parameters and limits we confirmed against the live API. You need a hiapi API key from your dashboard (it starts with sk-).
What the endpoint accepts
The model runs on the unified task API: POST /v1/tasks creates a task, then you poll GET /v1/tasks/<taskId> until status is success. The input fields below were confirmed by sending deliberately invalid values and reading the validation errors, then by two real requests.
| Field | Type | Notes |
|---|---|---|
prompt | string | Required. Omitting it returns missing required field "prompt". |
input_image | string (URL) | Optional. Present = edit mode; absent = text-to-image. |
aspect_ratio | enum | 21:9, 16:9, 4:3, 1:1, 3:4, 9:16 |
output_format | enum | jpeg or png |
safety_tolerance | integer | 0, 1 or 2 |
prompt_upsampling | boolean | Optional |
The schema is closed: unknown fields are rejected. image_url, image, seed, num_images and resolution all returned additional properties ... not allowed. The image field is input_image, not image_url. There is no resolution or seed field, so output size follows aspect_ratio and you cannot pin a seed for reproducibility.
The model is listed with the image-to-image and text-to-image capabilities on the flux-1-kontext-max model page. Per-image price is on /en/pricing; we don't quote it here because it can change.
Minimal example: text to image
curl -s https://api.hiapi.ai/v1/tasks \
-H "Authorization: Bearer $HIAPI_API_KEY" \
-H "Content-Type: application/json" \
-d '{
"model": "flux-1-kontext-max",
"input": {
"prompt": "A quiet reading corner by a tall window at golden hour, linen armchair, warm light, editorial photography",
"aspect_ratio": "4:3",
"output_format": "png"
}
}'
The response contains only a task id:
{"code":200,"data":{"taskId":"tk-hiapi-01M5X4DBGATQ6A0PH9X1EEVR2H"},"message":"success"}
Poll it:
curl -s https://api.hiapi.ai/v1/tasks/tk-hiapi-01M5X4DBGATQ6A0PH9X1EEVR2H \
-H "Authorization: Bearer $HIAPI_API_KEY"
When finished, the result carries the image URL in data.output[0].url:
{"code":200,"data":{"model":"flux-1-kontext-max","output":[{"artifactId":"292574","expireAt":1793657700,"type":"image","url":"https://temp.hiapi.ai/7c6ttvrbpt/01M5X4DBGATQ6A0PH9X1EEVR2H-0.png"}],"status":"success","storage":"temp","taskId":"tk-hiapi-01M5X4DBGATQ6A0PH9X1EEVR2H"},"message":"success"}
Python: generate, then edit
This script generates an image, then feeds the output URL back as input_image for an edit. It saves both files, because output URLs expire (see below).
import os, time, requests
BASE = "https://api.hiapi.ai"
HEADERS = {"Authorization": f"Bearer {os.environ['HIAPI_API_KEY']}"}
def run(input_: dict, timeout=300) -> str:
r = requests.post(f"{BASE}/v1/tasks", headers=HEADERS,
json={"model": "flux-1-kontext-max", "input": input_})
r.raise_for_status()
task_id = r.json()["data"]["taskId"]
deadline = time.time() + timeout
while time.time() < deadline:
d = requests.get(f"{BASE}/v1/tasks/{task_id}", headers=HEADERS).json()["data"]
if d["status"] == "success":
return d["output"][0]["url"]
if d["status"] == "fail":
raise RuntimeError(d)
time.sleep(5)
raise TimeoutError(task_id)
def save(url: str, path: str):
open(path, "wb").write(requests.get(url).content)
base_url = run({
"prompt": "A quiet reading corner by a tall window at golden hour, linen armchair, warm light, editorial photography",
"aspect_ratio": "4:3",
"output_format": "png",
})
save(base_url, "base.png")
edited_url = run({
"prompt": "Change the armchair to deep green velvet, keep everything else identical",
"input_image": base_url,
"output_format": "png",
})
save(edited_url, "edited.png")
Observed results
Both requests below were real calls made on 2026-10-27 with a test key.
Text to image. aspect_ratio: "4:3", output_format: "png". The task stayed in handling for about 85 seconds, passed through an archiving state, then reached success. The PNG came back at 1184 x 880 (about 1.28 MB), so 4:3 does not map to an exact 4:3 pixel grid. Check the real dimensions if your layout depends on them.
Edit. We passed the first output URL as input_image with the prompt "Change the armchair to deep green velvet, keep everything else identical", and no aspect_ratio. This finished in about 17 seconds (one sample each, so treat the timing gap as indicative rather than a benchmark). The armchair turned deep green velvet. The window, curtains, bookshelf, vase and throw blanket stayed in place. One caveat: the warm golden lighting tinted the velvet, so the green reads more olive-gold in highlights than a flat "deep green". If colour accuracy matters, name the lighting in the edit prompt.
The edit output was 1152 x 864 while the source was 1184 x 880. Both are 4:3, but the edit is not pixel-aligned with its input. If you composite the edit back over the original, resize first rather than assuming identical dimensions.
We did not test prompt_upsampling, safety_tolerance levels or multi-image input; the validation errors confirm the fields exist, but we have no output comparison for them.
Production notes
- Output URLs expire. Each
outputitem has anexpireAtunix timestamp; ours was about seven days after creation, ontemp.hiapi.ai. Download or copy the file to your own storage as soon as the task succeeds. - Poll tolerantly. Task completion can take well over a minute for generation. Use a deadline and retry transient network errors rather than aborting on the first failed poll. Save the
taskIdso you can re-poll after a crash. - Failures. Validation errors return HTTP 400 with
error_code: "INVALID_REQUEST"and a message naming the field, for exampleaspect_ratio: value must be one of '21:9', '16:9', '4:3', '1:1', '3:4', '9:16'. These are returned synchronously and no task is created. - Pick the right field. If you port code from another FLUX model on hiapi, check the field name; this model takes
input_imageas a string, not an array.
Related pages
- flux-1-kontext-max model page
- hiapi pricing
- How to use the FLUX.2 image-to-image API
- How to use the FLUX.1 Fill Pro API for mask inpainting
- FLUX.3 image prompt recipes
FAQ
Is an input image required?
No. Without input_image the model generates from the prompt alone; with it, the model edits that image.
Which field carries the image?
input_image, a single URL string. image_url, image and similar names are rejected.
Can I set a seed or choose a resolution?
Not on this endpoint: seed and resolution are rejected, and size follows aspect_ratio.
How long do result URLs last?
Our task's expireAt was about seven days out. Save the file on your side.





