Seedream v4.5 Text to Image
Seedream v4.5 Text to Image API documentation, supporting high-quality image generation with multiple aspect ratios and resolutions.
Seedream v4.5 is a high-quality AI image generation model launched by ByteDance, featuring excellent Chinese and English understanding capabilities and outstanding image generation quality.
- Supports Chinese and English Prompts
- Multiple aspect ratio options: 1:1, 2:3, 3:2, 3:4, 4:3, 16:9, 9:16, 21:9
- High-resolution output: Supports 2K and 4K resolutions
- Asynchronous task mode: Submit request and poll for results
Interface Definition
Asynchronous Task Mode
This API operates asynchronously. After submitting a request, you will receive a task ID, and you need to poll the status interface to get the result.
Steps: 1. Submit task to get task_id → 2. Poll status interface until completion
# Step 1: Submit image generation task
curl --request POST \
--url https://api.apipod.ai/v1/images/generations \
--header 'Authorization: Bearer <token>' \
--header 'Content-Type: application/json' \
--data '{
"model": "seedream-v4.5",
"prompt": "A vibrant close-up editorial portrait, model with intense gaze, wearing a sculptural hat, rich color blocking, sharp eye focus, shallow depth of field, Vogue magazine cover aesthetic",
"aspect_ratio": "3:4",
"quality": "2K"
}'
# Response example:
# {"code": 0, "message": "success", "data": {"task_id": "task_abc123xyz"}}
# Step 2: Poll task status
curl --request GET \
--url https://api.apipod.ai/v1/images/status/task_abc123xyz \
--header 'Authorization: Bearer <token>'import requests
import time
API_KEY = "<token>"
BASE_URL = "https://api.apipod.ai/v1"
headers = {
"Authorization": f"Bearer {API_KEY}",
"Content-Type": "application/json"
}
# Step 1: Submit image generation task
response = requests.post(
f"{BASE_URL}/images/generations",
headers=headers,
json={
"model": "seedream-v4.5",
"prompt": "A vibrant close-up editorial portrait, model with intense gaze, wearing a sculptural hat, rich color blocking",
"aspect_ratio": "3:4",
"quality": "2K"
}
)
task_id = response.json()["data"]["task_id"]
print(f"Task submitted: {task_id}")
# Step 2: Poll task status
while True:
status_response = requests.get(
f"{BASE_URL}/images/status/{task_id}",
headers=headers
)
data = status_response.json()["data"]
if data["status"] == "completed":
print("Image generation complete!")
print("Image URL:", data["result"])
break
elif data["status"] == "failed":
print("Task failed")
break
else:
print(f"Status: {data['status']}, waiting...")
time.sleep(2) # Poll every 2 secondsconst API_KEY = "<token>";
const BASE_URL = "https://api.apipod.ai/v1";
const headers = {
"Authorization": `Bearer ${API_KEY}`,
"Content-Type": "application/json"
};
async function generateImage() {
// Step 1: Submit image generation task
const submitResponse = await fetch(`${BASE_URL}/images/generations`, {
method: "POST",
headers,
body: JSON.stringify({
model: "seedream-v4.5",
prompt: "A vibrant close-up editorial portrait, model with intense gaze, wearing a sculptural hat, rich color blocking",
aspect_ratio: "3:4",
quality: "2K"
})
});
const { data: { task_id } } = await submitResponse.json();
console.log(`Task submitted: ${task_id}`);
// Step 2: Poll task status
while (true) {
const statusResponse = await fetch(
`${BASE_URL}/images/status/${task_id}`,
{ headers }
);
const { data } = await statusResponse.json();
if (data.status === "completed") {
console.log("Image generation complete!");
console.log("Image URL:", data.result);
break;
} else if (data.status === "failed") {
console.log("Task failed");
break;
} else {
console.log(`Status: ${data.status}, waiting...`);
await new Promise(resolve => setTimeout(resolve, 2000));
}
}
}
generateImage();package main
import (
"bytes"
"encoding/json"
"fmt"
"io/ioutil"
"net/http"
"time"
)
const (
apiKey = "<token>"
baseURL = "https://api.apipod.ai/v1"
)
type SubmitResponse struct {
Code int `json:"code"`
Message string `json:"message"`
Data struct {
TaskID string `json:"task_id"`
} `json:"data"`
}
type StatusResponse struct {
Code int `json:"code"`
Message string `json:"message"`
Data struct {
TaskID string `json:"task_id"`
Status string `json:"status"`
CompletedAt int64 `json:"completed_at"`
Result []string `json:"result"`
} `json:"data"`
}
func main() {
// Step 1: Submit image generation task
payload := map[string]interface{}{
"model": "seedream-v4.5",
"prompt": "A vibrant close-up editorial portrait, model with intense gaze, wearing a sculptural hat",
"aspect_ratio": "3:4",
"quality": "2K",
}
jsonData, _ := json.Marshal(payload)
req, _ := http.NewRequest("POST", baseURL+"/images/generations", bytes.NewBuffer(jsonData))
req.Header.Set("Authorization", "Bearer "+apiKey)
req.Header.Set("Content-Type", "application/json")
client := &http.Client{}
resp, err := client.Do(req)
if err != nil {
panic(err)
}
defer resp.Body.Close()
body, _ := ioutil.ReadAll(resp.Body)
var submitResp SubmitResponse
json.Unmarshal(body, &submitResp)
taskID := submitResp.Data.TaskID
fmt.Printf("Task submitted: %s\n", taskID)
// Step 2: Poll task status
for {
req, _ := http.NewRequest("GET", baseURL+"/images/status/"+taskID, nil)
req.Header.Set("Authorization", "Bearer "+apiKey)
resp, _ := client.Do(req)
body, _ := ioutil.ReadAll(resp.Body)
resp.Body.Close()
var statusResp StatusResponse
json.Unmarshal(body, &statusResp)
if statusResp.Data.Status == "completed" {
fmt.Println("Image generation complete!")
fmt.Println("Image URL:", statusResp.Data.Result)
break
} else if statusResp.Data.Status == "failed" {
fmt.Println("Task failed")
break
} else {
fmt.Printf("Status: %s, waiting...\n", statusResp.Data.Status)
time.Sleep(2 * time.Second)
}
}
}import java.net.http.HttpClient;
import java.net.http.HttpRequest;
import java.net.http.HttpResponse;
import java.net.URI;
import com.google.gson.JsonObject;
import com.google.gson.JsonParser;
public class SeedreamExample {
private static final String API_KEY = "<token>";
private static final String BASE_URL = "https://api.apipod.ai/v1";
public static void main(String[] args) throws Exception {
HttpClient client = HttpClient.newHttpClient();
// Step 1: Submit image generation task
String payload = """
{
"model": "seedream-v4.5",
"prompt": "A vibrant close-up editorial portrait, model with intense gaze, wearing a sculptural hat",
"aspect_ratio": "3:4",
"quality": "2K"
}
""";
HttpRequest submitRequest = HttpRequest.newBuilder()
.uri(URI.create(BASE_URL + "/images/generations"))
.header("Authorization", "Bearer " + API_KEY)
.header("Content-Type", "application/json")
.POST(HttpRequest.BodyPublishers.ofString(payload))
.build();
HttpResponse<String> submitResponse = client.send(submitRequest,
HttpResponse.BodyHandlers.ofString());
JsonObject submitJson = JsonParser.parseString(submitResponse.body()).getAsJsonObject();
String taskId = submitJson.getAsJsonObject("data").get("task_id").getAsString();
System.out.println("Task submitted: " + taskId);
// Step 2: Poll task status
while (true) {
HttpRequest statusRequest = HttpRequest.newBuilder()
.uri(URI.create(BASE_URL + "/images/status/" + taskId))
.header("Authorization", "Bearer " + API_KEY)
.GET()
.build();
HttpResponse<String> statusResponse = client.send(statusRequest,
HttpResponse.BodyHandlers.ofString());
JsonObject statusJson = JsonParser.parseString(statusResponse.body()).getAsJsonObject();
String status = statusJson.getAsJsonObject("data").get("status").getAsString();
if ("completed".equals(status)) {
System.out.println("Image generation complete!");
System.out.println("Image URL: " + statusJson.getAsJsonObject("data").get("result"));
break;
} else if ("failed".equals(status)) {
System.out.println("Task failed");
break;
} else {
System.out.println("Status: " + status + ", waiting...");
Thread.sleep(2000);
}
}
}
}Authentication
All API calls require a Bearer Token in the Header.
Security Notice
Do not expose your API Key directly in browser frontend code. It is recommended to use it only on the server side.
Authorization: Bearer sk-xxxxxxxxxxxxxxxxRequest Parameters
Core Parameters
| Parameter | Type | Required | Default | Description |
|---|---|---|---|---|
model | string | ✅ | seedream-v4.5 | Model identifier |
prompt | string | ✅ | - | Description of the image to generate, max 4000 chars |
aspect_ratio | string | - | 1:1 | Aspect ratio of the generated image |
quality | string | - | 2K | Output image resolution |
Prompt Writing Tips
Describe Subject
Clearly describe the main subject of the image, including people, objects, or scenes.
A young woman wearing a white dress, standing under cherry blossom treesAdd Details
Supplement with lighting, colors, style, and other details.
Soft natural light, pink tones, Japanese fresh styleSpecify Style
Clearly specify the artistic or photography style.
Cinematic, shallow depth of field, medium format shot, 35mm film textureComplete Prompt Example:
A vibrant close-up editorial portrait, model with intense gaze, wearing a sculptural hat (with an APIPod.ai LOGO on the hat),
rich color blocking, sharp eye focus, shallow depth of field, Vogue magazine cover aesthetic, medium format shot, intense studio lighting.Aspect Ratio Options
| Value | Ratio | Use Case |
|---|---|---|
1:1 | Square | Avatars, social media posts |
2:3 | Portrait | Portrait photography |
3:2 | Landscape | Landscape photography |
3:4 | Portrait | Magazine covers, posters |
4:3 | Landscape | Traditional photos |
16:9 | Widescreen | Video thumbnails, Banners |
9:16 | Vertical | Phone wallpapers, short video covers |
21:9 | Ultra-wide | Cinematic frames, website Hero images |
Resolution Options
| Value | Description |
|---|---|
2K | Standard resolution, faster generation |
4K | High resolution, suitable for printing and large displays |
Response Structure
Task Submission Response
After submitting an image generation request, the API returns a task ID:
| Field | Type | Description |
|---|---|---|
code | integer | Response status code, 0 indicates success |
message | string | Response message |
data.task_id | string | Unique identifier for the generation task |
{
"code": 0,
"message": "success",
"data": {
"task_id": "task_abc123xyz"
}
}Status Query Interface
| Path Parameter | Type | Required | Description |
|---|---|---|---|
task_id | string | ✅ | Image generation task ID |
Status Response Fields
| Field | Type | Description |
|---|---|---|
code | integer | Response status code, 0 indicates success |
message | string | Response message |
data.task_id | string | Task ID |
data.error_message | string | Error message |
data.status | string | Task status: pending / processing / completed / failed |
data.completed_at | integer | Completion timestamp (Unix timestamp) |
data.result | array | List of generated image URLs |
Task Status Description
| Status | Description | Recommended Action |
|---|---|---|
pending | Task submitted, waiting for processing | Continue polling, recommended interval 2 seconds |
processing | Task is being processed | Continue polling, recommended interval 2 seconds |
completed | Task completed, image generated | Get image URLs from result |
failed | Task failed | Check error message, resubmit task |
Polling Recommendation
It is recommended to poll the task status every 2-3 seconds. Image generation usually takes 10-30 seconds. Do not poll too frequently to avoid triggering rate limits.
Error Handling
| Status Code | Description |
|---|---|
400 | Request parameter error (e.g., prompt too long, invalid aspect_ratio) |
401 | Authentication failed, API Key invalid or missing |
403 | Insufficient balance or insufficient permissions |
404 | Task does not exist (when querying status) |
429 | Request too frequent, triggered rate limit |
500 | Internal server error |
{
"error": {
"message": "Invalid aspect_ratio value",
"type": "invalid_request_error",
"code": "invalid_parameter"
}
}Best Practices
Set Reasonable Polling Interval
It is recommended to poll every 2-3 seconds and set a maximum number of polls (e.g., 60 times) to avoid infinite waiting.
Handle Timeout Situations
If the task is not completed after 2 minutes, suggests prompting the user to try again later.
Cache Generated Images
Image URLs have a limited validity period. It is recommended to download and store them on your own server or CDN.