HiAPI
Blog

Tutorial

So verwendest du nano-banana-pro über die HiAPI-API: curl- und Python-Beispiele

Oct 31, 2026
平面流体形态层叠交错的封面图,墨色底上流动着青瓷绿与石板灰的波纹,呼应教程主题。

Was dir nano-banana-pro auf HiAPI bietet

nano-banana-pro ist ein Bildgenerierungsmodell, das über die einheitliche API von HiAPI aufgerufen werden kann. Du musst dich nicht direkt in den Modellanbieter integrieren – du sendest einfach eine Anfrage im einheitlichen Format an HiAPI und erhältst das generierte Bild, mit derselben Authentifizierung, denselben Endpunktkonventionen und derselben Antwortkapselung wie bei anderen Plattformmodellen.

nano-banana-pro ist für die promptgesteuerte Bildgenerierung konzipiert und kann neben Text-Prompts auch Referenzbilder enthalten. Referenzbilder ermöglichen es dir, die Ausgabe mit visuellem Kontext (Motiv, Stil, Komposition) zu steuern, ohne alles in Worten beschreiben zu müssen. Die Ausgabe wird in 2K-Auflösung geliefert, weshalb sich das Modell eher für Produktions-Assets als für schnelle Entwürfe eignet.

Nach Abschluss dieses Tutorials verfügst du über eine voll funktionsfähige Integration, die:

  • einen Prompt über eine verifizierte curl-Anfrage an HiAPI an nano-banana-pro sendet;
  • denselben Aufruf in Python reproduziert, ohne die Anfrage-Nutzlast zu ändern;
  • ein Referenzbild in die Anfrage einbezieht;
  • asynchrone Aufgaben übermittelt, bis zur Fertigstellung abfragt und Wiederholungsversuche sinnvoll behandelt;
  • das fertige 2K-Bild herunterlädt und in deiner eigenen Infrastruktur speichert.

Jeder Abschnitt baut auf dem vorherigen auf, daher ist der sicherste Weg, der Reihe nach vorzugehen: zuerst die Anfrage manuell bestätigen, dann in Code überführen.

Bevor du die erste Anfrage sendest

Vor dem ersten Aufruf brauchst du drei Dinge.

Einen API-Schlüssel

Erstelle einen API-Schlüssel in deinem HiAPI-Konto und stelle sicher, dass er nicht in die Quellcodeverwaltung gelangt. Behandle ihn wie jedes andere Geheimnis: aus einer Umgebungsvariablen (HIAPI_API_KEY) oder einem Secret Manager laden, niemals fest in Dateien codieren, die du möglicherweise committest. Wenn der Schlüssel kompromittiert wird, rotiere ihn im Dashboard, statt zu versuchen, ihn aus der Historie zu entfernen.

Einen HTTP-Client

Jedes Tool, das HTTPS-Anfragen senden kann, ist geeignet. Für die erste Anfrage ist curl auf der Kommandozeile ideal, da sich zwischen dir und dem Netzwerk kein Framework befindet – jeder Header und jedes Byte des Antwort-Bodys ist sichtbar. Für den Python-Teil reicht die Standardbibliothek urllib.request aus; wenn du bereits requests oder httpx verwendest, ist die Zuordnung dieselbe. Dieses Tutorial beschränkt Python auf die Standardbibliothek, sodass nichts zusätzlich installiert werden muss.

Einen Ort für die Ausgabe

Da nano-banana-pro-Aufgaben asynchron sind, plane von Anfang an ein Verzeichnis oder einen Bucket für die fertigen Bilder ein. In der Entwicklung genügt ein lokaler output/-Ordner; in der Produktion sollte Objektspeicher das Ziel sein.

Du musst kein Anbieter-SDK installieren. HiAPI läuft über normales HTTPS, daher ist die Anfrage, die du in curl baust, identisch mit der, die dein Python-Client später sendet.

Eine funktionierende curl-Anfrage, Schritt für Schritt

Der schnellste Weg zu bestätigen, dass Schlüssel, Endpunkt und Nutzlast korrekt sind, ist eine manuell gesendete Anfrage. Zerlege sie vor der Eingabe in ihre Bestandteile.

Endpunkt und Methode

Alle Modellaufrufe gehen an dieselbe HiAPI-Basis-URL; das Modell wird im Anfrage-Body identifiziert, nicht im Pfad. Generierungsanfragen verwenden POST.

Header

Bei jedem Aufruf sind drei Header wichtig:

  • Authorization: Bearer $HIAPI_API_KEY – dein Schlüssel, als Bearer-Token übergeben.
  • Content-Type: application/json – für reine Prompt-Anfragen.
  • Accept: application/json – damit du eine strukturierte Antwort erhältst und keine HTML-Fehlerseite.

Anfrage-Body

Der JSON-Body enthält den Modellnamen und die Generierungsparameter. Mindestens musst du den Modellbezeichner und deinen Prompt senden:

curl -sS -X POST "$HIAPI_BASE_URL" \
  -H "Authorization: Bearer $HIAPI_API_KEY" \
  -H "Content-Type: application/json" \
  -H "Accept: application/json" \
  -d '{
    "model": "nano-banana-pro",
    "input": {
      "prompt": "a glass terrarium on a sunlit windowsill, soft morning light, shallow depth of field"
    }
  }'

Setze vor dem Ausführen dieses Befehls HIAPI_BASE_URL und HIAPI_API_KEY in deiner Shell. Die URL in einer Variable zu speichern bedeutet, dass du dasselbe Skript später auf eine Staging- oder Sandbox-URL richten kannst, ohne den Befehl zu ändern.

Die Antwort lesen

Eine erfolgreiche Übermittlung gibt ein JSON-Objekt zurück, das die Aufgabe identifiziert. Das wichtige Feld ist der Aufgabenbezeichner – du wirst ihn im Abfrageschritt verwenden. Da die Generierung Zeit braucht, erwarte nicht, dass du das Bild selbst bereits in der ersten Antwort erhältst; nano-banana-pro läuft asynchron, und dieser Aufruf ist nur der Übermittlungsteil der Interaktion.

Wenn der Befehl einen Fehler zurückgibt, stoppe hier und behebe ihn, bevor du Code schreibst. Die verifizierte curl-Anfrage ist deine Referenzimplementierung: Jeder spätere Schritt sollte dieselbe HTTP-Anfrage erzeugen.

Die Anfrage nach Python portieren

Das Portieren ist mechanisch: URL, Methode, Header und JSON-Body bleiben unverändert. Nur der Client ändert sich.

Dieselbe Anfrage mit urllib

import json
import os
import urllib.request

api_key = os.environ["HIAPI_API_KEY"]
base_url = os.environ["HIAPI_BASE_URL"]

payload = {
    "model": "nano-banana-pro",
    "input": {
        "prompt": "a glass terrarium on a sunlit windowsill, soft morning light, shallow depth of field"
    },
}

request = urllib.request.Request(
    base_url,
    data=json.dumps(payload).encode("utf-8"),
    method="POST",
    headers={
        "Authorization": f"Bearer {api_key}",
        "Content-Type": "application/json",
        "Accept": "application/json",
    },
)

with urllib.request.urlopen(request, timeout=60) as response:
    body = json.loads(response.read().decode("utf-8"))

print(body)

Zuordnungsregeln

Bei der Umstellung von curl sind drei Details fehleranfällig:

  1. Der Anfrage-Body muss Bytes sein. json.dumps erzeugt einen String; er muss kodiert werden, bevor er an das Request-Objekt übergeben wird.
  2. Header sind ein Dictionary, keine Flags. Jede -H-Zeile wird zu einem Schlüssel/Wert-Paar. Behalte das Präfix Bearer und das darauffolgende Leerzeichen bei.
  3. Die Methode muss explizit angegeben werden. Bei vorhandenen Daten verwendet urllib.request standardmäßig POST, aber method="POST" zu setzen macht die Absicht klarer und verhindert Überraschungen, wenn du später den Anfrage-Body entfernst.

Wenn du requests verwendest, lautet das Äquivalent requests.post(base_url, headers=headers, json=payload, timeout=60) – json= übernimmt Serialisierung und Content-Type für dich. Wenn du httpx verwendest, ist die Aufrufform identisch.

Eine kleine Hilfsfunktion, die sich lohnt

Packe den Übermittlungsaufruf in eine Funktion, die einen Prompt entgegennimmt und den Aufgabenbezeichner zurückgibt. Jeder spätere Abschnitt – Referenzbilder, Abfragen, Herunterladen – baut auf dieser Funktion auf, und sie an einer Stelle zu halten bedeutet, dass Änderungen an der Anfrageform nur einmal erfolgen müssen.

Referenzbilder mit dem Prompt senden

Referenzbilder ändern die Form der Anfrage, daher solltest du früh entscheiden, welche Eingabeart deine Anwendung verwenden wird.

Zwei praktische Optionen

URL-basierte Eingabe. Wenn das Referenzbild bereits über HTTPS erreichbar ist, kannst du seine URL zusammen mit dem Prompt in den Anfrage-Body aufnehmen. Dadurch bleibt die Anfrage application/json, die am einfachsten zu wiederholende und zu protokollierende Form.

Datei hochladen. Wenn das Bild auf dem Client oder in privatem Speicher liegt, kannst du es als Dateiteil in einer multipart/form-data-Anfrage senden. In diesem Fall wird der Header Content-Type: application/json durch den Multipart-Content-Type ersetzt – lass deinen HTTP-Client ihn erzeugen, damit die Boundary korrekt ist – und die JSON-Felder werden zu Formularfeldern in derselben Anfrage.

Für die meisten serverseitigen Integrationen ist die URL-basierte Eingabe einfacher: Deine Bilder liegen bereits im Objektspeicher, die Anfrage bleibt JSON, und bei Wiederholungsversuchen vermeidest du es, große Anfrage-Bodys zweimal zu senden.

Prompt und Referenzbild aufeinander abstimmen

Der Prompt sollte den Zweck des Referenzbilds beschreiben, nicht nur seinen Inhalt. „Beleuchtung und Farbton des Referenzbilds übernehmen; das Motiv durch eine Keramikvase ersetzen“ gibt dem Modell eine klare Aufgabe. Ein Prompt, der das Referenzbild ignoriert, verschwendet die Eingabe.

Vor dem Senden validieren

Referenzbilder sind die häufigste Fehlerquelle bei Anfragen. Prüfe, ob die URL öffentlich zugänglich ist (oder ob sich beide Seiten deines Systems über die Ablaufzeit von signierten URLs einig sind), ob der Dateityp vom Modell akzeptiert wird und ob das Bild so groß ist, dass es Upload-Timeouts verursacht. Führe diese Prüfungen zuerst in deinem eigenen Code durch – fehlgeschlagene clientseitige Validierung ist weitaus günstiger zu debuggen als eine abgelehnte Anfrage.

Asynchrone Aufgaben behandeln und Ergebnisse abfragen

Die Generierung mit nano-banana-pro ist asynchron. Baue deinen Client rund um drei getrennte Schritte: Übermitteln, Abfragen, Herunterladen. Sie in einer Funktion zu vermischen macht Wiederholungsversuche und Timeouts schwer nachvollziehbar.

Schritt 1: Übermitteln

Sende die oben beschriebene Anfrage und speichere den zurückgegebenen Aufgabenbezeichner. Persistiere diesen Bezeichner an einem dauerhaften Ort – eine Datenbankzeile oder eine Warteschlangen-Nachricht –, da dein Prozess zwischen Übermittlung und Abschluss neu gestartet werden kann.

Schritt 2: Abfragen

Rufe den Aufgabenstatus mit derselben Basis-URL und demselben Authorization-Header ab, indem du den Aufgabenbezeichner in der Anfrage mitschickst. Frage in Intervallen ab, nicht in einer tight loop; einige Sekunden zwischen den Prüfungen sind typisch, und wenn mehrere aufeinanderfolgende Prüfungen einen ausstehenden Status zurückgeben, solltest du mit Backoff arbeiten.

import time

TERMINAL = {"succeeded", "failed"}

def wait_for_job(job_id, timeout=300, interval=3):
    deadline = time.monotonic() + timeout
    while time.monotonic() < deadline:
        status = get_job_status(job_id)  # same headers as submit
        if status in TERMINAL:
            return status
        time.sleep(interval)
    raise TimeoutError(f"job {job_id} did not finish in time")

Schritt 3: Status respektieren

Behandle das Statusfeld als Enum. Eine Aufgabe läuft entweder noch, ist erfolgreich abgeschlossen oder fehlgeschlagen. Behandle alle drei Fälle explizit: bei Erfolg zum Download übergehen; bei Fehlschlag die Fehlermeldung lesen und entscheiden, ob das Problem in der Eingabe oder im Prompt liegt; bei Timeout das Abfragen beenden und den Aufgabenbezeichner für spätere Untersuchungen bereitstellen.

Wiederholungsversuche gehören auf zwei Ebenen

Wiederholungsversuche auf Netzwerkebene sollten auf den Übermittlungsaufruf und jede Abfrageanfrage angewendet werden, mit einer begrenzten Anzahl von Versuchen. Wiederholungsversuche auf Aufgabenebene sind anders: Wenn eine Aufgabe aufgrund eines schlechten Prompts oder Referenzbilds fehlschlägt, wird das erneute Senden derselben Nutzlast auf dieselbe Weise fehlschlagen. Wiederhole die Aufgabe selbst erst, nachdem du die Eingabe geändert hast.

Ein gängiges Produktionsmuster ist ein Worker, der die Abfrageschleife übernimmt, sodass Web-Anfragen nie durch die Generierung blockiert werden. Übermittle aus deinem API-Handler, übergib den Aufgabenbezeichner an den Worker und benachrichtige den Client, wenn der Worker fertig ist.

Die 2K-Ausgabe herunterladen und speichern

Die endgültige Antwort der Aufgabe verweist auf das generierte Bild, statt es einzubetten – das bedeutet, dass der Download ein Schritt ist, den du selbst verantwortest.

Das Bild abrufen

Wenn die Aufgabe Erfolg meldet, enthält die Antwort den Speicherort der Ausgabe. Rufe ihn mit einer normalen GET-Anfrage ab und schreibe dann die Bytes in eine Datei oder streame sie in den Speicher. Speichere in der Entwicklung in einem lokalen Verzeichnis mit einem vorhersagbaren Namen, der aus dem Aufgabenbezeichner gebildet wird, damit du die Datei dem Aufgaben-Datensatz zuordnen kannst.

import pathlib
import urllib.request

def save_image(url, job_id, out_dir="output"):
    pathlib.Path(out_dir).mkdir(exist_ok=True)
    target = pathlib.Path(out_dir) / f"nano-banana-pro-{job_id}.png"
    with urllib.request.urlopen(url, timeout=60) as response:
        target.write_bytes(response.read())
    return target

Richtig speichern

In der Produktion solltest du die Antwort direkt in den Objektspeicher streamen statt auf die lokale Festplatte zu schreiben, damit das Verhalten unabhängig davon konsistent bleibt, welcher Worker die Aufgabe bearbeitet. Zeichne den Objektschlüssel und den Aufgabenbezeichner in der Datenbank auf und prüfe, ob Content-Type und Dateiendung mit dem übereinstimmen, was das Modell generiert hat. Wenn die Bilder im Web bereitgestellt werden sollen, erzeuge im selben Pipeline-Schritt Vorschaubilder, damit öffentliche Seiten nie die vollständige 2K-Datei laden.

Aufbewahrungsstrategie planen

Die generierten Ausgaben sind deine Daten. Entscheide, wie lange du sie aufbewahrst, ob du Versionierung brauchst und ob der endgültige Speicherort von deiner Anwendung nach einem Verlust neu generiert werden kann. Wenn die Antwort nein lautet, speichere sowohl die Anfrage-Nutzlast als auch das Bild, damit dir künftige Bugs oder Modelländerungen niemals die Reproduzierbarkeit der Ergebnisse nehmen.

Häufige Fehlerquellen und wie man sie debuggt

Die meisten ersten Integrationen scheitern aus wenigen Gründen. Gehe diese Checkliste Punkt für Punkt durch, bevor du annimmst, dass das Modell ein Problem hat.

  • Autorisierungsfehler. Fehlendes Präfix Bearer , ein Schlüssel mit einem abschließenden Zeilenumbruch, weil er aus einer Env-Datei kopiert wurde, oder ein Schlüssel aus einer anderen Umgebung als der gesetzten Basis-URL.
  • Content-Type-Nichtübereinstimmung. JSON-Felder mit Multipart-Headern zu senden oder Dateien mit application/json zu senden ist die häufigste Ursache für abgelehnte Referenzbild-Anfragen. Lass bei Multipart-Bodys den Client den Header setzen.
  • Falsche Methode oder falsche Body-Form. GET statt POST oder ein prompt auf oberster Ebene statt des verschachtelten input-Objekts erzeugt Validierungsfehler, die völlig unzusammenhängend wirken. Vergleiche deine Anfrage Byte für Byte mit dem verifizierten curl-Aufruf – curl -v zeigt die tatsächlich gesendeten Header.
  • Zu schnelles Abfragen oder gar kein Abfragen. Häufige Anfragen an den Status-Endpunkt führen zu Rate Limits; nie abzufragen bringt gar nichts. Verwende ein festes Intervall mit Backoff und ein hartes Timeout.
  • Abgelaufene Ausgabe-URL. Wenn du zwischen Abschluss der Aufgabe und dem Download zu lange wartest, kann die signierte Ausgabe-URL ablaufen. Lade sofort nach dem Erfolg herunter oder halte einen erneuten Abrufpfad für einen neuen Speicherort bereit.
  • Stille Fehler im Code. Protokolliere bei Fehlern immer den HTTP-Statuscode und den Antwort-Body. Allgemeine Ausnahmemeldungen von HTTP-Clients verbergen die nützlichen Teile der Antwort.

Wenn etwas unklar ist, greife auf die verifizierte curl-Anfrage aus dem ersten Abschnitt zurück. Wenn diese funktioniert und dein Python-Aufruf nicht, dann ist die Differenz zwischen beiden der Bug.

Ähnliche Artikel

Alle Artikel ansehen →

Starte mit persistenten KI-Artefakten

Hol dir deinen API-Key und rufe Bild-, Video- und Audiomodelle über eine einzige task-basierte API auf.

API-Dokumentation lesen