Google's high-efficiency image model for generation and editing, model id nano-banana-2-1. Text-to-image and editing are the same model: a prompt alone generates, a prompt plus reference images (up to 10) edits or combines them. Fifteen aspect ratios, 1K / 2K / 4K output at $0.024 / $0.04 / $0.064 per image, charged only on success.
Every request carries your API key in the header:
Authorization: Bearer YOUR_API_KEY| resolution | Price / image | Notes |
|---|---|---|
| 1K | $0.024 | Default tier |
| 2K | $0.04 | |
| 4K | $0.064 | Top tier |
Price depends on resolution only — the number of reference images, the aspect ratio and the prompt length do not change it. Omitting resolution bills 1K. Failed requests are not charged. Examples: 100 images at 1K = $2.40, at 2K = $4.00, at 4K = $6.40.
/v1/images/generationsAsync contract: creating a task returns a taskId immediately; poll GET /v1/images/generations?task_id= until state is completed and read resultUrls, or pass a callback_url to receive a webhook. The request below is the one from our first test on 2026-10-07: 16:9 at 1K, about 20 seconds, delivered at 1376×768 with the sign text spelled correctly.
# Step 1: create the task (text-to-image) — returns a taskId right away
curl -X POST https://api.apimodels.app/v1/images/generations \
-H "Authorization: Bearer YOUR_API_KEY" \
-H "Content-Type: application/json" \
-d '{
"model": "nano-banana-2-1",
"prompt": "A cozy bookstore cafe on a rainy evening, warm window light, a hand-painted sign reading NANO BANANA 2.1 above the door, cinematic wide shot",
"aspect_ratio": "16:9",
"resolution": "1K"
}'
# → { "code": 200, "data": { "taskId": "...", "state": "pending", "model": "nano-banana-2-1" } }
# Step 2: poll until state is "completed" (or "failed")
curl "https://api.apimodels.app/v1/images/generations?task_id=TASK_ID" \
-H "Authorization: Bearer YOUR_API_KEY"
# → { "code": 200, "data": { "state": "completed", "resultUrls": ["https://..."] } }Same endpoint, same model id: include image (one) or image_urls (an array) and the request becomes an edit; the two together accept up to 10 images. Each can be a URL, a data URI or bare base64, in JPEG, PNG or WebP. Refer to them in the prompt as image 1, image 2 and so on.
# Edit one image — image accepts a URL, a data URI or bare base64
curl -X POST https://api.apimodels.app/v1/images/generations \
-H "Authorization: Bearer YOUR_API_KEY" \
-H "Content-Type: application/json" \
-d '{
"model": "nano-banana-2-1",
"prompt": "Keep the room and the lighting, replace the sofa with a dark green velvet one",
"image": "https://example.com/living-room.jpg",
"resolution": "2K"
}'
# Combine several references — image_urls takes up to 10 (image + image_urls together: 10 max)
curl -X POST https://api.apimodels.app/v1/images/generations \
-H "Authorization: Bearer YOUR_API_KEY" \
-H "Content-Type: application/json" \
-d '{
"model": "nano-banana-2-1",
"prompt": "Put the character from image 1 into the street scene from image 2, wearing the jacket from image 3",
"image_urls": [
"https://example.com/character.png",
"https://example.com/street.jpg",
"https://example.com/jacket.jpg"
],
"aspect_ratio": "4:5",
"resolution": "2K"
}'
# Poll GET ?task_id= exactly as in the text-to-image example.| Field | Required | Type | Description |
|---|---|---|---|
| model | Yes | string | nano-banana-2-1 |
| prompt | Yes | string | Image description or editing instruction, up to 20,000 characters |
| image | No | string | One reference image: URL, data URI or bare base64 (image_url / image_base64 also work) |
| image_urls | No | string[] | Several reference images, up to 10 together with image; more than 10 returns a 400 |
| aspect_ratio | No | string | auto, 1:1, 2:3, 3:2, 3:4, 4:3, 4:5, 5:4, 9:16, 16:9, 21:9, 1:4, 4:1, 1:8, 8:1. Default auto |
| resolution | No | string | 1K (default) / 2K / 4K — sets the price |
| callback_url | No | string | Webhook URL called when the task finishes, instead of polling |
pending / processing: still generating — check again in 2–3 secondscompleted: data.resultUrls holds the image linkfailed: data.failMsg gives the reason; the request is not chargedAll of them use the same endpoint and parameters, so switching is a one-string change to model.
Try it in the Playground — pick the ratio and resolution and upload references without writing code.
Per image, by resolution only: $0.024 at 1K (the default), $0.04 at 2K and $0.064 at 4K. Reference images, aspect ratio and prompt length do not change the price, and failed requests are not charged.
Pass image for a single reference or image_urls for an array; together they accept up to 10 images, and more than 10 returns a 400. Each entry can be a URL, a data URI or bare base64 in JPEG, PNG or WebP. Use image_urls rather than images for the array — that is the field the image endpoint reads.
Fifteen: auto (the default), 1:1, 2:3, 3:2, 3:4, 4:3, 4:5, 5:4, 9:16, 16:9, 21:9, and the extreme 1:4, 4:1, 1:8 and 8:1 for banners and tall strips. Any other value returns a 400 instead of being swapped for a nearby ratio.