Tutoriale
Come usare gpt-image-2.5-sunburst/image-to-image tramite l'API HiAPI: curl e Python
Richieste eseguibili per sviluppatori, flusso di caricamento dell'immagine di riferimento e risoluzione degli errori
In questa pagina
Le capacità image-to-image di questo endpoint
L'endpoint gpt-image-2.5-sunburst/image-to-image segue una convenzione semplice: invii un'immagine di riferimento insieme a un'istruzione di modifica in linguaggio naturale, e il modello restituisce una nuova immagine che applica tale istruzione mantenendosi ancorata all'immagine di riferimento. A differenza del text-to-image — che parte da zero e dipende interamente dal tuo prompt — l'image-to-image usa l'immagine di riferimento come contesto visivo: composizione, soggetto, stile e indizi cromatici vengono ereditati, a meno che la tua istruzione non chieda esplicitamente di modificarli.
Questo lo rende la scelta giusta quando hai già materiale esistente e vuoi una trasformazione controllata, ad esempio cambiare lo stile di una foto di prodotto, modificare l'illuminazione o lo sfondo, ritoccare l'aspetto del soggetto o generare varianti di un concept esistente. Scegli il text-to-image quando non hai materiale di partenza e desideri la massima libertà creativa; scegli l'image-to-image quando la fedeltà all'immagine esistente conta più della novità.
Il modello mentale chiave da ricordare per gli sviluppatori: l'immagine di riferimento è un vincolo di input, mentre l'istruzione di modifica è un incremento. Una buona istruzione descrive cosa deve cambiare, non tutto ciò che deve esistere. "Sostituisci lo sfondo con un gradiente da studio pulito, mantenendo il soggetto e la sua ombra" funziona meglio di una descrizione completa della scena, perché l'immagine di riferimento fornisce già la scena. Tieni presente questo punto mentre leggi la struttura della richiesta qui sotto — il corpo della richiesta è piccolo, ma la qualità dell'istruzione determina la qualità dell'output.
Prerequisiti e struttura della richiesta
Prima della prima chiamata, assicurati di avere tre cose pronte:
- La chiave API, rilasciata dal tuo account HiAPI. Conservala in una variabile d'ambiente, non nel codice sorgente.
- Il base URL, ossia il base URL dell'API HiAPI, consultabile nella tua dashboard o nella documentazione di riferimento dell'API.
- Il percorso dell'endpoint:
gpt-image-2.5-sunburst/image-to-image.
Ogni richiesta è una richiesta POST che trasporta un corpo JSON e un'intestazione Authorization. Concettualmente, il corpo della richiesta contiene tre parti logiche:
- Selezione del modello — l'identificatore del modello per questo endpoint, affinché il gateway instradi correttamente la chiamata.
- Input — l'immagine di riferimento (URL ospitato o stringa di dati base64) e il testo dell'istruzione di modifica.
- Controllo dell'output — qualsiasi parametro opzionale elencato nella documentazione dell'endpoint, ad esempio dimensioni o quantità. Usa solo i parametri che compaiono nella documentazione di riferimento ufficiale; non indovinare i nomi.
Un consiglio sulla disciplina: poiché si tratta di un endpoint ospitato, i campi effettivamente accettati sono definiti dalla documentazione di riferimento attuale dell'API, non da inferenze basate su altre API di immagini. In caso di dubbio, invia prima il corpo di richiesta minimo valido (model, image, prompt), verifica che restituisca una risposta 200, poi aggiungi i campi opzionali uno alla volta. Così ogni guasto è attribuibile a una singola modifica, invece che a un corpo di richiesta assemblato in una volta sola.
Inviare l'immagine di riferimento e le istruzioni di modifica
Esistono due modi supportati per fornire l'immagine di riferimento; la scelta dipende principalmente da dove risiedono i byte dell'immagine.
URL ospitato
Se l'immagine è già accessibile pubblicamente, passa direttamente il suo URL. Così il corpo della richiesta è piccolo, la serializzazione è rapida ed è l'opzione più semplice in fase di sviluppo. L'URL deve poter essere recuperato direttamente dal servizio — non deve trovarsi dietro autenticazione, non deve essere una catena di redirect, né una pagina HTML che contiene per caso un'immagine.
Dati base64
Se l'immagine è locale o è una risorsa privata, codificala e inviala inline. Il base64 gonfia il corpo della richiesta di circa un terzo, quindi con immagini di partenza grandi si può avvicinare al limite di dimensione. Se sei vicino al limite, riduci la risoluzione prima di codificare.
Insidie di formato e dimensione
- Attieniti ai formati mainstream (PNG, JPEG, WebP) e assicurati che l'estensione del file corrisponda ai byte effettivi.
- Le immagini troppo grandi sono la causa più comune di richieste rifiutate. Usa immagini di partenza di dimensioni ragionevoli; per guidare una modifica di solito non servono materiali a piena risoluzione.
- Se costruisci la stringa base64 da solo, aggiungi il prefisso data URI solo se gli esempi della documentazione di riferimento dell'API lo includono; altrimenti omettilo. Mescolare le due convenzioni è una fonte frequente di errori "invalid image".
Scrivere l'istruzione di modifica
La qualità dell'output dipende dall'istruzione. Specifica cosa cambiare e indica esplicitamente cosa preservare. Scrivi l'oggetto ("la giacca"), la trasformazione ("r colorala in blu navy scuro") e il vincolo ("mantieni la posa del modello e le ombre esistenti"). Evita di accumulare più modifiche non correlate in un'unica istruzione — se servono modifiche indipendenti, dividile in più chiamate, così ogni risultato è anche più facile da valutare.
Una richiesta curl eseguibile
Quella che segue è una richiesta eseguibile per intero dal terminale. Sostituisci i segnaposto della chiave e dell'immagine con i tuoi valori.
curl -X POST "$HIAPI_BASE_URL/gpt-image-2.5-sunburst/image-to-image" \
-H "Authorization: Bearer $HIAPI_API_KEY" \
-H "Content-Type: application/json" \
-d '{
"model": "gpt-image-2.5-sunburst/image-to-image",
"image": "https://your-cdn.example.com/reference.png",
"prompt": "Sostituisci lo sfondo con un morbido gradiente da studio neutro; mantieni invariati il soggetto, la sua posa e le ombre esistenti."
}'
Spiegazione voce per voce:
-X POST— l'operazione crea una nuova immagine, quindi si usa POST.- L'URL è composto dal base URL e dal percorso dell'endpoint; tenere il base URL in una variabile d'ambiente rende facile cambiare ambiente.
Authorization: Bearer ...— la tua chiave API. Esportala comeHIAPI_API_KEYcosì non finisce nella cronologia della shell o nei log.Content-Type: application/json— il corpo è JSON; omettere questa intestazione è una causa comune di risposte 4xx confuse.model— l'identificatore dell'endpoint. Deve corrispondere esattamente alla documentazione.image— l'immagine di riferimento, qui un URL ospitato. Per usare invece base64, sostituiscilo con la stringa di dati o una variabile codificata localmente.prompt— l'istruzione di modifica. Limitati a scrivere la modifica e ciò che va preservato.
Se vuoi testare con un file locale senza codificarlo manualmente, la maggior parte delle shell può costruire il JSON con un piccolo script o con jq; la cosa importante è che il corpo finale sia JSON valido contenente questi campi.
La stessa richiesta in Python
La versione Python mantiene il corpo della richiesta identico, così puoi confrontare le risposte affiancate. Usa requests:
import os
import requests
base_url = os.environ["HIAPI_BASE_URL"]
api_key = os.environ["HIAPI_API_KEY"]
payload = {
"model": "gpt-image-2.5-sunburst/image-to-image",
"image": "https://your-cdn.example.com/reference.png",
"prompt": (
"Sostituisci lo sfondo con un morbido gradiente da studio neutro; "
"mantieni invariati il soggetto, la sua posa e le ombre esistenti."
),
}
response = requests.post(
f"{base_url}/gpt-image-2.5-sunburst/image-to-image",
headers={
"Authorization": f"Bearer {api_key}",
"Content-Type": "application/json",
},
json=payload,
timeout=120,
)
response.raise_for_status()
print(response.json())
Due cose meritano attenzione. Primo, json=payload imposta il content type e serializza il corpo per te, eliminando un'intera classe di errori dovuti alla costruzione manuale del JSON. Secondo, timeout=120 è intenzionale: la generazione di immagini non è istantanea, e un client che aspetta all'infinito è peggio di un client che fallisce in modo pulito. Adatta il timeout al tuo carico di lavoro, ma impostalo sempre.
Per usare invece un file locale, leggi i suoi byte, codificali in base64 e assegna il risultato a image. Con un URL ospitato, lascia la stringa così com'è. Una volta che le chiamate curl e Python restituiscono la stessa struttura, hai confermato che si comportano allo stesso modo e puoi costruire sopra una delle due.
Risolvere i fallimenti di richiesta più comuni
La maggior parte dei fallimenti rientra in quattro categorie. Esamina in questo ordine, perché ciascuna può mascherarsi da quella successiva.
Errori di autenticazione
401 o 403 significano quasi sempre chiave mancante, malformata o scaduta. Verifica che l'intestazione sia esattamente Authorization: Bearer <key>, controlla che non ci siano virgolette o ritorni a capo in più introdotti dal copia-incolla e assicurati che la variabile d'ambiente sia effettivamente impostata nella shell o nel processo che esegue la richiesta. Una chiave che funziona in curl ma non in Python di solito indica una variabile non impostata, non una chiave rotta.
Corpo della richiesta malformato
Un 400 con informazioni di validazione di solito significa JSON non valido o campi obbligatori mancanti. Prima di inviare, stampa in forma leggibile il corpo della richiesta, verifica che model corrisponda all'identificatore dell'endpoint e che il nome del campo dell'istruzione di modifica sia coerente con la documentazione. Scrivendo JSON a mano in curl, le virgole finali e gli apici singoli sono i colpevoli classici; il json= di Python li evita.
Input immagine non valido o troppo grande
Se il servizio rifiuta l'immagine, verifica tre cose: che l'URL sia recuperabile pubblicamente e restituisca un'immagine (non un redirect o una pagina di errore), che il formato sia supportato e che il corpo della richiesta non superi il limite di dimensione indicato nella documentazione. Per input base64, verifica che la codifica sia pulita e che la convenzione del prefisso data URI corrisponda all'esempio di riferimento. In caso di dubbio, riduci la risoluzione e riprova — immagini di partenza più piccole risolvono una buona parte di questi errori.
Timeout e guasti transitori
Generazioni lunghe possono superare il timeout del client, mentre risposte 429 o 5xx indicano che è scattato il rate limiting o che si è verificato un problema temporaneo del server. Distinguili dagli errori del client: non riprovare 400 così com'è, ma 429 o 503 si prestano a un retry con backoff. Registra codice di stato e corpo della risposta per ogni fallimento — un log degli errori chiaro trasforma la risoluzione dei problemi da congettura a verifica punto per punto.
Da script a client riutilizzabile
Uno script usa e getta dimostra che l'endpoint funziona; un piccolo wrapper lo fa funzionare stabilmente in una pipeline. Avvolgi la chiamata in una funzione che si occupi di tre cose: la richiesta, il timeout e una strategia di retry con limite.
import os
import time
import requests
class ImageEditClient:
def __init__(self, base_url: str, api_key: str, timeout: int = 120):
self.base_url = base_url.rstrip("/")
self.api_key = api_key
self.timeout = timeout
def edit(self, image: str, prompt: str, retries: int = 3):
url = f"{self.base_url}/gpt-image-2.5-sunburst/image-to-image"
headers = {
"Authorization": f"Bearer {self.api_key}",
"Content-Type": "application/json",
}
payload = {
"model": "gpt-image-2.5-sunburst/image-to-image",
"image": image,
"prompt": prompt,
}
last_error = None
for attempt in range(retries):
try:
resp = requests.post(
url, headers=headers, json=payload, timeout=self.timeout
)
except requests.Timeout as err:
last_error = err
time.sleep(2 ** attempt)
continue
if resp.status_code in (429, 500, 502, 503, 504):
last_error = RuntimeError(f"transient {resp.status_code}: {resp.text}")
time.sleep(2 ** attempt)
continue
if resp.status_code >= 400:
raise RuntimeError(f"request failed {resp.status_code}: {resp.text}")
return resp.json()
raise RuntimeError(f"exhausted retries: {last_error}")
Le scelte di progettazione contano più del codice stesso. Il retry si applica solo a timeout e codici di stato transitori, mai agli errori del client 4xx, perché riprovare un corpo di richiesta malformato spreca soltanto quota. Il backoff esponenziale evita che una pipeline soggetta a rate limiting martelli ripetutamente l'endpoint. Gli errori del client vengono sollevati immediatamente insieme al corpo della risposta, così il chiamante vede esattamente cosa il servizio contesta. E centralizzare l'identificatore del modello in un solo punto significa che passare in futuro a un altro endpoint di immagini richiede una sola riga, invece di perlustrare l'intero codice.
Su questa base, aggiungi log strutturati per ogni tentativo e un controllo di dimensione/forma prima che i consumatori a valle usino la risposta. Quando sei pronto a esplorare altri modelli di immagini sullo stesso gateway, il catalogo dei modelli HiAPI è il posto giusto per confrontare gli endpoint senza riscrivere il client.
Articoli correlati
Vedi tutti gli articoli →-
Tutoriale
Come chiamare kimi-k3.1-pro tramite l'API HiAPI: curl, Python e richieste eseguibili direttamente
Una guida pratica all'integrazione, che copre endpoint, parametri della richiesta, streaming, tool calling e risoluzione dei problemi
-
Tutoriale
API ElevenLabs Music su HiAPI: generare musica con curl, Python e ricette di prompt
Un tutorial pratico per chiamare elevenlabs/music-v2.5 tramite HiAPI, con ricette di prompt pronte da copiare per stile, mood e durata
-
Tutoriale
Come usare gemini-omni-1.2-flash tramite l'API HiAPI: curl e Python