API · 10 min read

GPTImage2.ai API: Endpoint Reference, Interfaces and Demo Examples

The GPTImage2.ai API is the production endpoint for your account. Create an API key on the Keys page, call https://gptimage2.ai/api/generatefrom your server, and poll the returned job id until images are ready. Every generated image spends the key owner’s credits.

Published 2026-04-22 · Updated 2026-04-25

Endpoints

POSThttps://gptimage2.ai/api/generate

Create a generation job. Use mode="text-to-image" for prompt-only renders or mode="image-to-image" with reference image URLs.

GEThttps://gptimage2.ai/api/generate/{jobId}

Poll a generation job. The endpoint returns 202 while pending or running, then 200 with either generated image URLs or a failure error.

Never put a GPTImage2.ai API key in browser code. Call these endpoints from your backend or a server route handler, then expose only your own scoped UI response to the browser.

Authentication and credits

Keys created on the Keys page authenticate with Authorization: Bearer $GPTIMAGE2_API_KEY. Every generated image spends 10credits from the key owner’s account. Failed upstream jobs are refunded by the same generation pipeline used by Studio.

Request interface

FieldTypeRequiredDescription
promptstringYesThe image brief. Put the subject first, then style, light, frame, and text.
modestringNotext-to-image for prompt-only renders, or image-to-image when sending reference URLs.
ratiostringNoAspect ratio such as 1:1, 16:9, 9:16, 4:3, or 3:4.
countnumberNoNumber of images to generate. Values are capped between 1 and 4.
imageUrlsstring[]NoReference image URLs for image-to-image jobs. Required when mode is image-to-image.
stylestringNoOptional style preset slug, such as editorial-photo, studio-product, or cinematic.
lightingstringNoOptional lighting hint appended to the final prompt.
camerastringNoOptional camera or framing hint appended to the final prompt.
negativestringNoOptional avoid list appended to the final prompt.
export interface GptImage2GenerateRequest {
  prompt: string;
  mode?: "text-to-image" | "image-to-image";
  ratio?: "1:1" | "16:9" | "9:16" | "4:3" | "3:4";
  count?: 1 | 2 | 3 | 4;
  imageUrls?: string[];
  style?: string;
  lighting?: string;
  camera?: string;
  negative?: string;
}

export type GptImage2JobResponse =
  | {
      jobId: string;
      status: "pending" | "running";
      balance?: {
        paidCredits: number;
        totalImages: number;
      };
    }
  | {
      jobId: string;
      status: "succeeded";
      results: Array<{
        imageUrl: string;
        finalPrompt: string;
        seed: string;
      }>;
      balance?: {
        paidCredits: number;
        totalImages: number;
      };
    }
  | {
      jobId: string;
      status: "failed";
      error: string;
      balance?: {
        paidCredits: number;
        totalImages: number;
      };
    };

Response interface

FieldTypeRequiredDescription
jobIdstringYesGeneration job id returned by the create call and used for polling.
statusstringYesrunning, pending, succeeded, or failed.
results[].imageUrlstringNoGenerated image URL, present after the polling response succeeds.
balanceobjectNoRemaining credit balance for the API key owner.
errorstringNoMachine-readable error code when the request or job fails.
{
  "jobId": "8b93b17d-6ec7-4bd7-96a2-b06f69e8b862",
  "status": "running",
  "balance": {
    "paidCredits": 490,
    "freeImagesRemaining": 0,
    "totalImages": 49,
    "freeImagesPerDay": 0
  }
}

// Poll success
{
  "jobId": "8b93b17d-6ec7-4bd7-96a2-b06f69e8b862",
  "status": "succeeded",
  "results": [
    {
      "imageUrl": "https://file.gptimage2.ai/generated/demo.png",
      "seed": "1",
      "finalPrompt": "A clean studio product photo of a ceramic espresso cup"
    }
  ],
  "balance": {
    "paidCredits": 490,
    "freeImagesRemaining": 0,
    "totalImages": 49,
    "freeImagesPerDay": 0
  }
}

Demo 1: Generate with cURL

The create call returns a jobId and the remaining balance after credits are reserved.

curl https://gptimage2.ai/api/generate \
  -H "Authorization: Bearer $GPTIMAGE2_API_KEY" \
  -H "Content-Type: application/json" \
  -d '{
    "mode": "text-to-image",
    "prompt": "A clean studio product photo of a ceramic espresso cup",
    "ratio": "1:1",
    "count": 1,
    "style": "studio-product"
  }'

Poll the job with the same API key:

curl https://gptimage2.ai/api/generate/{jobId} \
  -H "Authorization: Bearer $GPTIMAGE2_API_KEY"

Demo 2: Image-to-image with reference URLs

Send image URLs for multi-reference jobs. Each URL should have one purpose: subject, palette, composition, or material reference.

curl https://gptimage2.ai/api/generate \
  -H "Authorization: Bearer $GPTIMAGE2_API_KEY" \
  -H "Content-Type: application/json" \
  -d '{
    "mode": "image-to-image",
    "prompt": "Keep the product from ref 1, use the color palette from ref 2.",
    "imageUrls": [
      "https://cdn.example.com/subject.png",
      "https://cdn.example.com/palette.png"
    ],
    "ratio": "1:1",
    "count": 1
  }'

Demo 3: Node.js job polling

This demo uses native fetch in Node 18+ and prints the first image URL after the job succeeds.

const create = await fetch("https://gptimage2.ai/api/generate", {
  method: "POST",
  headers: {
    Authorization: `Bearer ${process.env.GPTIMAGE2_API_KEY}`,
    "Content-Type": "application/json",
  },
  body: JSON.stringify({
    mode: "text-to-image",
    prompt: "An editorial product photo of a matte black camera on red lacquer",
    ratio: "1:1",
    count: 1,
  }),
});

const job = await create.json();
if (!create.ok) throw new Error(job.error ?? `HTTP ${create.status}`);

let result = job;
while (result.status === "pending" || result.status === "running") {
  await new Promise((resolve) => setTimeout(resolve, 2500));
  const poll = await fetch(`https://gptimage2.ai/api/generate/${job.jobId}`, {
    headers: { Authorization: `Bearer ${process.env.GPTIMAGE2_API_KEY}` },
  });
  result = await poll.json();
}

console.log(result.results?.[0]?.imageUrl ?? result.error);

Demo 4: Python requests

Install the HTTP client with pip install requests, set GPTIMAGE2_API_KEY, then run the script.

import os
import time
import requests

headers = {
    "Authorization": f"Bearer {os.environ['GPTIMAGE2_API_KEY']}",
    "Content-Type": "application/json",
}

job = requests.post(
    "https://gptimage2.ai/api/generate",
    headers=headers,
    json={
        "mode": "text-to-image",
        "prompt": "A warm studio portrait of a ceramic bottle on folded linen",
        "ratio": "1:1",
        "count": 1,
    },
)
job.raise_for_status()
data = job.json()

while data["status"] in ("pending", "running"):
    time.sleep(2.5)
    poll = requests.get(
        f"https://gptimage2.ai/api/generate/{data['jobId']}",
        headers=headers,
    )
    poll.raise_for_status()
    data = poll.json()

print(data.get("results", [{}])[0].get("imageUrl") or data.get("error"))

Demo 5: Next.js route handler proxy

Use a route handler when your app needs extra authorization, rate limits, or request shaping before calling GPTImage2.ai.

// app/api/render/route.ts
import { NextResponse } from "next/server";

export async function POST(req: Request) {
  const { prompt } = (await req.json()) as { prompt?: string };
  if (!prompt?.trim()) {
    return NextResponse.json({ error: "prompt_required" }, { status: 400 });
  }

  try {
    const upstream = await fetch("https://gptimage2.ai/api/generate", {
      method: "POST",
      headers: {
        Authorization: `Bearer ${process.env.GPTIMAGE2_API_KEY}`,
        "Content-Type": "application/json",
      },
      body: JSON.stringify({
        mode: "text-to-image",
        prompt,
        ratio: "1:1",
        count: 1,
      }),
    });
    const result = await upstream.json();

    return NextResponse.json(
      result,
      {
        status: upstream.status,
        headers: { "Cache-Control": "no-store" },
      },
    );
  } catch (err) {
    return NextResponse.json({ error: "image_generation_failed" }, { status: 500 });
  }
}

Operational checklist

Validation

Trim prompts, reject empty input, cap count, validate ratios, and verify reference image URLs before spending credits.

Cost control

Start with count: 1, show remaining credits after each job, and only request multiple candidates when the workflow needs comparison.

Reliability

Retry 429/5xx responses with backoff, add idempotency keys for paid jobs, and store the original prompt, ratio, count, and returned job id.

Security

Keep provider keys on the server, scope customer access through your own auth, and log enough metadata to audit expensive or abusive requests.

Migration: dall-e-3 to gpt-image-2

- POST https://old-provider.example/images/generations
+ POST https://gptimage2.ai/api/generate
- Authorization: Bearer $OLD_PROVIDER_KEY
+ Authorization: Bearer $GPTIMAGE2_API_KEY
- { "prompt": "...", "width": 1024, "height": 1024, "count": 1 }
+ { "mode": "text-to-image", "prompt": "...", "ratio": "1:1", "count": 1 }

Test three differences in staging: payloads are larger, quoted in-image text is followed more literally, and image URLs are returned after asynchronous job polling instead of inside the create response. Full side-by-side breakdown on GPT Image 2 vs DALL-E 3.

Pricing detail on the pricing page; full walkthrough on how to use GPT Image 2.