HiAPI
Blog

Tutorial

Cómo llamar a seedream-5.0-lite/text-to-image mediante la API de HiAPI: guía con curl y Python

Un recorrido práctico y ejecutable para desarrolladores: integración de texto a imagen a través de HiAPI

Oct 31, 2026
极简建筑感封面图:暖灰混凝土平面与斜切的青灰蓝色块、一道细鼠尾草绿接缝,构成安静的布里库特风格几何构图。

Qué hace realmente esta integración

Iniciar una llamada de texto a imagen en HiAPI es una breve conversación entre tu código y una cola de tareas asíncrona. Envías una solicitud describiendo la imagen que deseas; la plataforma valida la solicitud, acepta la tarea y devuelve un identificador. La imagen no viene en la primera respuesta: se genera después. Luego, tu código monitorea la tarea hasta que esta informa que ha terminado y, finalmente, descarga la imagen desde la URL que expone la tarea.

Esta forma es importante porque determina cómo escribes la integración. Hay tres momentos distintos: envío, sondeo (polling) y obtención. Cada uno tiene sus propios modos de fallo. El envío falla cuando el payload tiene un formato incorrecto o la ruta del modelo no es válida. El sondeo falla cuando el bucle está mal escrito: demasiado rápido, demasiado corto o incapaz de distinguir entre «aún en ejecución» y «terminado». La obtención falla cuando tratas la URL de salida como permanente o cuando olvidas escribir los bytes en el disco.

En esencia, seedream-5.0-lite/text-to-image es un modelo genérico de texto a imagen en la plataforma HiAPI. Lo invocas mediante ese identificador exacto de modelo. Los parámetros que envías son los habituales para este tipo de llamada: el nombre del modelo, el prompt y cualquier parámetro de control de tamaño o cantidad de salida que indique la documentación del endpoint. No necesitas ningún SDK especial; un cliente HTTPS común es suficiente.

Al terminar este recorrido tendrás una solicitud reproducible con curl, una función de Python que la envuelve, un truco para redactar prompts de modo que el texto renderizado quede claro y legible, y un bucle de sondeo que realmente termina. Todo se ejecuta a través del mismo endpoint de HiAPI, así que una vez que una llamada funciona, lo que queda es ajustar parámetros.

Construir la solicitud con curl

Empieza desde la línea de comandos. Una llamada ejecutable con curl es la base del payload: una vez que funciona, cualquier otro lenguaje es solo un ejercicio de traducción.

Antes de la primera llamada necesitas dos cosas: tu clave de API de HiAPI y la URL base de la API. La clave va en la cabecera Authorization como token bearer. Siempre que sea posible, evita que acabe en el historial de tu shell; las variables de entorno son el hábito más sencillo.

export HIAPI_API_KEY="your_api_key_here"

La solicitud en sí es un POST con un cuerpo JSON. El identificador del modelo es el segmento de ruta que invocas y el prompt describe la imagen:

curl -sS -X POST "$HIAPI_BASE_URL" \
  -H "Authorization: Bearer $HIAPI_API_KEY" \
  -H "Content-Type: application/json" \
  -d '{
    "model": "seedream-5.0-lite/text-to-image",
    "prompt": "A minimalist poster for a coffee shop called North Roast, warm cream background, bold dark lettering"
  }'

Configura HIAPI_BASE_URL con el endpoint de envío de texto a imagen que muestra la documentación de la plataforma; la ruta varía según la interfaz del producto, así que cópiala en lugar de adivinarla.

Antes de escribir más código, lee la respuesta. Un envío exitoso devuelve un objeto JSON con un identificador de tarea y un campo de estado. Normalmente el estado indica que la tarea está en cola o en proceso, es decir, aún no terminada. Esto es lo esperado. Anota con precisión los nombres de los campos devueltos; los usarás en las dos secciones siguientes.

Dos errores en el nivel de curl provocan la mayoría de los primeros fallos. El primero es una clave ausente o con el alcance equivocado: la respuesta es un error de autenticación, no un error del modelo. El segundo es un cuerpo mal formado: comillas sin escapar dentro del prompt, una coma final o comillas simples donde JSON exige comillas dobles. Si la plataforma rechaza el payload, formatea la salida con jq y valídalo por separado antes de culpar al modelo.

Cuando el envío devuelve un identificador, ya tienes una solicitud válida. Todo lo que sigue es esperar y obtener.

Portar a Python

La versión en Python debería ser una función pequeña y reutilizable, no un script con un único prompt codificado de forma fija. Usa requests (o httpx, si lo prefieres); la llamada en sí no requiere un cliente especial.

import os
import requests

API_KEY = os.environ["HIAPI_API_KEY"]
BASE_URL = os.environ["HIAPI_BASE_URL"]

HEADERS = {
    "Authorization": f"Bearer {API_KEY}",
    "Content-Type": "application/json",
}

def submit_image(prompt: str, **params) -> dict:
    payload = {
        "model": "seedream-5.0-lite/text-to-image",
        "prompt": prompt,
        **params,
    }
    response = requests.post(BASE_URL, headers=HEADERS, json=payload, timeout=30)
    response.raise_for_status()
    return response.json()

Aquí hay tres decisiones deliberadas. La clave y la URL base provienen del entorno, así que la función puede confirmarse en el control de versiones sin riesgo. El comodín **params te permite pasar el tamaño de salida u otras opciones documentadas sin editar la función. Y raise_for_status() convierte de inmediato los errores HTTP en excepciones, que es justo lo que quieres: un 4xx en el envío nunca dará lugar a una tarea válida, así que fallar rápido es mejor que inspeccionar un cuerpo de respuesta confuso.

El diccionario devuelto es el registro de tu tarea. Imprímelo una vez durante el desarrollo para conocer los nombres exactos de las claves del identificador y del estado. No lo indexes a ciegas; un pequeño accesor mantiene legible el resto del código:

job = submit_image("A flat illustration of a paper plane over a city map")
print(job)

Si imprime una tarea en cola, el port desde curl es correcto. Si lanza una excepción, el mensaje de la excepción generada por raise_for_status() te dirá si el problema es de autenticación o de payload, las mismas dos clases de problemas que encontrarías en el shell.

Redactar prompts para conocimiento del mundo y texto renderizado

Los modelos de texto a imagen son más fuertes cuando el prompt describe lo que debe ser visible y más débiles cuando insinúa conocimiento que el modelo debe inferir. seedream-5.0-lite/text-to-image puede aprovechar el contexto general del mundo (objetos reconocibles, convenciones de diseño comunes, estilos tipográficos), pero aun así debes darle suficiente contenido para anclar ese contexto.

Para prompts de escena, describe el sujeto, la composición y el estilo visual. «A cozy reading nook by a window, soft afternoon light, three-quarter view, muted earth tones» le dice al modelo tanto qué dibujar como cómo estilizarlo. Los prompts vagos producen imágenes genéricas; los prompts específicos producen imágenes utilizables.

El texto renderizado es donde los prompts suelen fallar. Si necesitas texto dentro de la imagen, sigue algunas reglas:

  • Cita la cadena exacta. Escribe el texto que quieres entre comillas para que quede claro que es un literal y no una descripción.
  • Manténlo breve. Un titular corto o un nombre de marca se renderizan de forma fiable; un párrafo, no.
  • Indica posición y estilo. «The word "North" centered at the top in a bold sans-serif» supera a «some text at the top».
  • Evita textos que compitan entre sí. Varios elementos de texto distintos en una sola imagen tienden a producir texto ilegible. Si necesitas varios, mantenlos breves y separados entre sí.
  • Itera una sola variable a la vez. Cambia la redacción, no la redacción, el diseño y el estilo al mismo tiempo, o no sabrás qué resolvió el problema.

Para cualquier cosa que implique un contexto reconocible (categoría de producto, tipo de póster, tipo de letrero), nómbralo explícitamente. El conocimiento previo del modelo resulta más útil cuando el prompt le da un anclaje. «A vintage travel poster for a coastal town» aporta más contexto útil que «a poster».

No inventes parámetros. Si el prompt no produce la ubicación del texto que deseas, ajusta primero la redacción del propio prompt antes de probar opciones que no estén documentadas.

Manejar tareas asíncronas y descargar la salida

El sondeo es donde la integración falla en silencio. La tarea es asíncrona, así que necesitas un bucle que compruebe el estado, espere entre comprobaciones, se rinda finalmente y sepa exactamente qué valores de estado significan «terminado».

import time

def wait_for_job(job_id: str, poll_interval: float = 3.0, timeout: float = 180.0) -> dict:
    deadline = time.monotonic() + timeout
    while time.monotonic() < deadline:
        response = requests.get(
            f"{BASE_URL}/{job_id}", headers=HEADERS, timeout=30
        )
        response.raise_for_status()
        job = response.json()

        status = job.get("status")
        if status in {"succeeded", "completed"}:
            return job
        if status in {"failed", "error", "cancelled"}:
            raise RuntimeError(f"Job {job_id} ended with status {status}")

        time.sleep(poll_interval)
    raise TimeoutError(f"Job {job_id} did not finish within {timeout}s")

Ajusta la ruta de sondeo y las cadenas de estado a lo que muestre la documentación de la plataforma; estos dos detalles son los más propensos a diferir del esbozo anterior. La estructura es lo clave: una fecha límite monotónica, una pausa entre comprobaciones, conjuntos explícitos de éxito y de fallo, y un tiempo de espera agotado que lanza una excepción en lugar de devolver una tarea a medio terminar.

Cuando la tarea informa que tuvo éxito, la respuesta contiene la URL de salida. Trata esa URL como temporal. Descarga los bytes de inmediato en lugar de almacenar el enlace:

def download_image(url: str, path: str) -> None:
    response = requests.get(url, timeout=60)
    response.raise_for_status()
    with open(path, "wb") as f:
        f.write(response.content)

job = wait_for_job(job_id)
download_image(job["output"]["url"], "out.png")

Antes de continuar, confirma que el archivo es una imagen real: ábrelo, comprueba las dimensiones o al menos verifica que la longitud en bytes no sea anormalmente pequeña. Si el servidor cierra la conexión correctamente, una descarga truncada puede parecer un éxito para requests.

Errores comunes y cómo solucionarlos

La mayoría de los fallos en una primera integración se agrupan en cuatro categorías. Abórdalas en orden.

El envío es rechazado

Si la primera llamada devuelve un 4xx, imprime el cuerpo de la respuesta. Un error de autenticación significa que la clave falta, ha caducado o no se envió como token bearer. Un error de esquema significa que el payload está mal formado: campo de modelo incorrecto, prompt ausente o un parámetro documentado mal escrito. Valida el JSON por separado y compáralo con el ejemplo ejecutable de curl.

La tarea nunca termina

El bucle gira indefinidamente o agota el tiempo. Comprueba primero el intervalo de sondeo: golpear el endpoint sin pausa puede activar límites de tasa y hacer que una tarea sana parezca atascada. Luego revisa la comparación de estados: si la plataforma devuelve success y tú comparas con succeeded, toda tarea parecerá incompleta. Registra una vez el valor de estado en bruto en lugar de adivinarlo.

La URL de salida devuelve 404 o 403

La URL de salida está firmada y tiene un tiempo limitado. Si has estado sondeando durante mucho tiempo y luego la obtienes, el enlace puede haber caducado. Obtenla en cuanto termine la tarea y, si necesitas conservar el resultado, guarda el archivo en lugar del enlace.

La imagen se renderiza pero el texto sale ilegible

Esto es un problema de prompt, no de código. Acorta el texto, cítalo con precisión, reduce el número de elementos de texto y haz más explícitas las instrucciones de estilo. Vuelve a ejecutar con un solo cambio cada vez para saber qué ajuste ayudó.

La solicitud se cuelga o agota el tiempo

Establece siempre tiempos de espera explícitos en las llamadas de envío y de sondeo. Una solicitud sin tiempo de espera puede bloquear indefinidamente un proceso de trabajo, y un bucle de sondeo sin fecha límite convierte una interrupción transitoria en un proceso atascado.

Cuando ocurra un comportamiento inesperado, redúcelo a la llamada de curl mínima que todavía falle. Si la solicitud HTTP sin procesar se comporta mal, la capa de Python no es el problema; una vez que curl vuelva a funcionar, portarlo de nuevo a Python es mecánico. La página del modelo seedream-5.0-lite/text-to-image enumera los parámetros y la forma de respuesta actuales, así que revísala antes de suponer nombres de campos.

Artículos relacionados

Ver todos los artículos →

Empieza a crear con artefactos de IA persistentes

Consigue tu API key y llama a modelos de imagen, vídeo y audio a través de una única API basada en tasks.

Leer la documentación de la API