Объявление: Ограниченное время: скидка 20% на новинки GPT Image 2.6 Flare и Sunburst, попробуйте сейчас
HiAPI
Блог

Руководство

Как использовать flux-1.1-pro через HiAPI API: curl, Python и работающие запросы

Практическое руководство по интеграции: запросы, которые действительно работают, асинхронная обработка и рецепты промптов с реальными выводами

Nov 10, 2026
Abstract tutorial cover art: terracotta stepped bands descending across a warm sand background, flat print style, no text.
На этой странице

Что даёт flux-1.1-pro до того, как вы напишете код

flux-1.1-pro — это модель генерации изображений по тексту, вызываемая через HiAPI.ai как управляемая конечная точка. Вы отправляете промпт и параметры генерации в формате JSON, а возвращается сгенерированное изображение. Ничего устанавливать не нужно, веса не нужно хостить самостоятельно, и не нужно управлять GPU-ресурсами. Ваша поверхность интеграции — это HTTP-эндпоинт плюс учётные данные для аутентификации.

Для разработчика это означает, что ещё до первой строки кода дизайн определяют три вещи.

Во-первых, запрос — это JSON на входе и изображение на выходе. Ваш промпт, соотношение сторон и несколько управляющих параметров лежат в теле запроса. Ответ несёт данные изображения или ссылку на них, в зависимости от способа доставки задачи. Относитесь к телу запроса как к контракту и храните его в одном месте, чтобы пути curl и Python никогда не расходились.

Во-вторых, по сравнению с обычным вызовом API генерация изображения — медленная операция. Несколько секунд — это норма; сложные промпты в высоком разрешении могут занять больше. Любой производственный вызывающий код должен предполагать задержку и планировать её, а не трактовать вызов как чтение из базы данных.

В-третьих, качество вывода определяется в первую очередь промптом, а не обвязкой. Интеграция — простая часть. Настоящая работа — точно описать желаемое и проверить рецепт на реальных выводах до запуска в продакшен.

Держа в уме эти три вещи, остальная часть руководства — механический процесс: составить запрос, убедиться, что он работает, перенести его, затем укрепить и настроить. На всём пути всё идёт через HiAPI API — одни учётные данные, один базовый URL, одна структура JSON для изучения.

Ваш первый curl-запрос

Начните с curl. Он убирает все слои абстракции между вами и эндпоинтом, поэтому при сбое вы точно знаете: проблема в теле запроса, а не в вашем фреймворке.

Минимальный вызов состоит из трёх частей: эндпоинт, заголовок аутентификации и тело JSON.

curl -X POST "https://api.hiapi.ai/v1/images/generations" \
  -H "Authorization: Bearer $HIAPI_API_KEY" \
  -H "Content-Type: application/json" \
  -d '{
    "model": "flux-1.1-pro",
    "prompt": "a ceramic coffee mug on a weathered wooden table, soft morning window light, shallow depth of field, product photography",
    "aspect_ratio": "1:1"
  }'

Прочитайте тело запроса по полям:

  • model задаёт модель, которую вы используете. Указывайте её явно, чтобы будущие изменения значений по умолчанию никогда не изменили ваш вывод незаметно.
  • prompt — это описание на естественном языке. Здесь сосредоточен почти весь ваш бюджет качества.
  • aspect_ratio управляет кадрированием. Выбирайте его осознанно, а не полагайтесь на непроверенное значение по умолчанию.

Поместите ключ в переменную окружения (HIAPI_API_KEY), а не вставляйте его прямо в команду. Эта привычка напрямую перейдёт в Python и в любые шаги CI, которые вы добавите позже.

При успешном вызове вы получите JSON-ответ с описанием готового изображения. Прежде чем закрыть терминал, изучите его и найдите ссылку на изображение или данные. При неудачном вызове вы получите тело ошибки с кодом состояния и сообщением; читайте это сообщение буквально, потому что неверный формат поля — самая частая причина первого сбоя.

Предупреждение, экономящее час: не вставляйте многострочные промпты с неэкранированными кавычками в shell. Для всего длиннее короткой фразы используйте heredoc или файл.

curl -X POST "https://api.hiapi.ai/v1/images/generations" \
  -H "Authorization: Bearer $HIAPI_API_KEY" \
  -H "Content-Type: application/json" \
  --data @request.json

Этот request.json — артефакт, который следует закоммитить в репозиторий. Это единственный источник истины для тела запроса, и следующий раздел использует его как есть.

Перенос того же вызова в Python

Цель переноса — не написать новую логику, а отправить точно такое же тело JSON. Загружайте тот же request.json, чтобы два пути не могли разойтись.

import json
import os

import requests

API_URL = "https://api.hiapi.ai/v1/images/generations"

with open("request.json") as f:
    payload = json.load(f)

response = requests.post(
    API_URL,
    headers={
        "Authorization": f"Bearer {os.environ['HIAPI_API_KEY']}",
        "Content-Type": "application/json",
    },
    json=payload,
    timeout=120,
)

if response.status_code != 200:
    print(response.status_code)
    print(response.text)
    response.raise_for_status()

print(response.json())

Здесь важны три детали.

Заголовок аутентификации и заголовок содержимого — одна группа заголовков. Использование json=payload заставляет requests сериализовать тело запроса и установить тип содержимого; явное указание заголовка безвредно и документирует намерение.

Задайте таймаут. Никогда не оставляйте запрос генерации висеть на бесконечном значении по умолчанию. Щедрый явный таймаут — это нормально; главное, чтобы он был явным.

Проверяйте тело ошибки до выброса исключения. Если сначала вызвать raise_for_status(), он отбросит тело ответа из ваших логов. Сначала напечатайте код состояния и текст, затем выбрасывайте. Когда поле отклонено, вам понадобится этот текст.

Если вы используете асинхронный HTTP-клиент, структура не меняется: тот же URL, те же заголовки, то же тело, только await client.post(...) с тем же таймаутом. Контракт тела запроса постоянен; клиент — деталь реализации.

Храните тело запроса вне исходников Python. Когда рецепт промпта работает, он должен лежать в файле или строке базы данных, а не в строковом литерале внутри функции — так вы сможете сравнить его и перезапустить.

Обработка асинхронных задач без блокировки приложения

Относитесь к генерации как к задаче, а не как к вызову функции. Независимо от того, выглядит ли ваш путь доставки синхронным или возвращает задачу, которую нужно опрашивать, практическое следствие одно: ваше приложение никогда не должно бесконечно занимать поток запроса в ожидании изображения.

Рабочий шаблон состоит из четырёх шагов.

1. Отправляйте из воркера, а не из пользовательского запроса

Примите действие генерации от пользователя на уровне веб-слоя, сохраните запись задачи, поставьте её в очередь и сразу верните ответ. Фактический вызов API выполняет фоновый воркер. Пользователь опрашивает ваш эндпоинт, а не модель.

2. Ограничьте ожидание

Задайте таймаут для каждой попытки, выбранный осознанно. Если платформа возвращает задачу, которую нужно опрашивать, опрашивайте с фиксированным интервалом, максимальным числом попыток и дедлайном, отсчитываемым от момента старта задачи, а не от числа попыток. Предпочитайте умеренную задержку вместо плотного цикла.

3. Повторяйте только те сбои, которые стоит повторять

Повторяйте транспортные ошибки, таймауты и серверные сбои с экспоненциальной задержкой и джиттером в пределах небольшого числа попыток. Не повторяйте ошибки валидации: отклонённое поле или пустой промпт будут сбоить одинаково каждый раз, и повтор лишь заставит пользователя дольше ждать настоящего сообщения.

4. Сделайте задачу идемпотентной на своей стороне

Записывайте в базу точное тело запроса и ID задачи. Если ваш воркер упал после отправки, но до записи успеха, вы можете перепроверить задачу, а не слепо отправлять её снова. Когда повторная отправка всё же необходима, добавьте короткий клиентский ключ дедупликации, чтобы временный сбой не поставил в очередь три одинаковые генерации.

import time

def poll_until_done(fetch_status, job_id, deadline_seconds=180):
    start = time.monotonic()
    delay = 2.0
    while True:
        status = fetch_status(job_id)
        if status["state"] in ("succeeded", "failed"):
            return status
        if time.monotonic() - start > deadline_seconds:
            raise TimeoutError(f"generation {job_id} exceeded deadline")
        time.sleep(delay)
        delay = min(delay * 1.5, 10.0)

Этот вспомогательный метод намеренно универсален: он принимает функцию получения статуса, поэтому один и тот же цикл подходит для любой задачо-ориентированной конечной точки, которую вы интегрируете позже. Важные свойства — дедлайн, ограниченная задержка и проверка конечного состояния, а не конкретный транспорт.

Создание промптов, которые стабильно рендерятся

Длинный промпт не равен лучшему промпту. Структура важнее. Повторяемый каркас даёт стабильные результаты и место, где при проблемах можно менять по одной переменной.

Используйте четыре слота в следующем порядке:

  1. Субъект — что есть на изображении, конкретно. «Керамическая кофейная кружка» лучше, чем «что-то для кафе».
  2. Стиль — визуальный тон: фотография, иллюстрация, акварель, 3D-рендер, продуктовая съёмка. Укажите среду и, если полезно, свет.
  3. Композиция — кадрирование и камера: соотношение сторон, дистанция съёмки, угол, глубина резкости, положение субъекта в кадре.
  4. Ограничения — конкретное, что вы явно хотите и не хотите, кратко.
[subject] a single ceramic coffee mug, matte glaze, small handle
[style] product photography, soft diffused window light, muted palette
[composition] 1:1, eye-level, subject centered, shallow depth of field, plain background
[constraints] no text, no logos, no hands

При отправке разверните это в одну строку промпта; квадратные скобки — для вас, не для модели. Ценность письма по слотам в том, что когда вывод неверен, вы знаете, какой слот редактировать.

Несколько практических правил:

  • Ставьте субъект первым. Первое предложение имеет наибольший вес.
  • Предпочитайте конкретные существительные и прилагательные, а не абстрактные эмоции. «Матовая глазурь» меняет пиксели; «премиальность» — почти нет.
  • Помещайте язык камеры в слот композиции, а не субъекта. Смешивание создаёт нетерпеливые и противоречивые инструкции.
  • При итерации меняйте один слот за раз и сохраняйте точный текст промпта, давший принятый вывод.

Соотношение сторон — решение композиции, а не заплатка. Выбирайте его под место, где будет изображение — квадрат для сетки, выше для главного баннера — и подгоняйте остальную часть промпта под этот кадр.

Эффективное использование списков негативных слов

Список негативных слов говорит модели, чего избегать. Это острый инструмент с узкой областью применения: отлично подавляет повторяющиеся дефекты, но плох как мусорный бак для всех несовершенств, которые вы можете вообразить.

Негативные слова должны быть краткими и конкретными. Для большинства промптов достаточно пяти-восьми коротких пунктов. Указывайте конкретные вещи:

no text, no watermark, no logos, no extra fingers, no harsh shadows

Этот список работает, потому что каждый пункт называет видимое и проверяемое. Сравните с размытыми отрицаниями вроде «not ugly» или «bad quality» — они почти не несут действенного сигнала и размывают действительно важные пункты.

Где негативные слова действительно помогают:

  • Подавление дефектов, которые вы видите снова и снова. Если руки или текст повторяются, прямое их указание — самый прямой фикс.
  • Брендовая и юридическая гигиена. Исключите логотипы и водяные знаки до того, как изображение попадёт в пользовательский интерфейс.
  • Принудительно чистый фон для продуктовых снимков или изображений, близких к UI.

Где они работают против вас:

  • Противоречие позитивному промпту. «Без теней» в негативе против «драматического бокового света» в субъекте — конфликт, который модель разрешит непредсказуемо. Исправляйте позитивный промпт.
  • Отрицание маловероятного. Длинный список маловероятных сбоев лишь добавляет шум и не меняет рендер.
  • Использование негатива для компенсации размытого субъекта. Если субъект неясен, никакой список негативных слов его не спасёт.

Практическая деталь: некоторые клиенты принимают негативные слова как отдельное поле, а не как дополнительный текст. Выясните, какой способ поддерживает ваш запрос, и сохраните это поле в сохранённом теле запроса, чтобы curl и Python вели себя одинаково.

Рецепты промптов с реальными выводами

Приведённые ниже рецепты — отправная точка, а не гарантия. Честный рабочий процесс таков: запустите рецепт через свою интеграцию, посмотрите на вывод, затем настройте один слот. Любой вывод, который вы не сгенерировали лично, следует считать непроверенным.

Рецепт 1 — чистое продуктовое фото

A single matte-black wireless earbud case on a light concrete surface,
studio product photography, soft key light from the left, 1:1, centered,
shallow depth of field, plain background. No text, no logos, no hands.

Ожидаемые характеристики: чёткий, центрированный субъект, мягкое затухание и незахламлённый фон. Если поверхность выглядит слишком сложной, ужесточите «plain background» и уберите любые слова о текстуре. Если свет слишком плоский, добавьте одно направленное ключевое слово — и только его.

Рецепт 2 — редакционный портрет

Portrait of a person in a wool coat, natural window light, calm expression,
3:4, chest-up framing, subject slightly off-center, muted film palette.
No text, no watermark.

Ожидаемые характеристики: мягкий направленный свет, сдержанные цвета. Если кадрирование шире ожидаемого, переместите «chest-up framing» вперёд и уберите конкурирующие слова о композиции.

Рецепт 3 — изометрическая иллюстрация

Isometric illustration of a small reading nook: armchair, floor lamp, bookshelf,
flat vector style, limited palette of warm neutrals and one accent color,
1:1, centered composition, clean white background. No text, no gradients.

Ожидаемые характеристики: чистая геометрия и плоские заливки. Если палитра уходит в сторону, явно укажите акцентный цвет и оставьте «clean white background» последним предложением, чтобы оно победило.

Рецепт 4 — главный баннер

A wide misty mountain ridge at sunrise, layered depth, minimal detail,
16:9, subject occupying the lower third, generous empty sky for overlaid text.
No text, no watermark.

Ожидаемые характеристики: спокойное, малодетализированное изображение с полезным негативным пространством. Формулировка «overlaid text» резервирует место; она не рендерит буквы, а список негативных слов не пускает текст в само изображение.

Для каждого рецепта записывайте точное тело запроса, соотношение сторон и дату. При просмотре через месяц вы сможете перезапустить записанное тело и сравнить с записанным выводом, а не гадать, почему результат изменился.

Ошибки, ограничения и что проверять в первую очередь

Когда генерация сбоит или вывод неверен, пройдите этот чек-лист, прежде чем менять код.

Сначала проверьте тело запроса

  • Тело запроса — валидный JSON? Висячие запятые или неэкранированные кавычки — самая частая причина первого сбоя. Проверяйте сохранённый request.json перед отправкой.
  • Имена полей точно верны? Опечатанные параметры обычно отклоняются или молча игнорируются. Сверяйтесь со структурой запроса в документации, а не с памятью.
  • Имя модели верно и существует? Не полагайтесь на значения по умолчанию.
  • Промпт непустой и в пределах длины, указанной в документации? Ограничения указаны в документации платформы; читайте там, а не предполагайте число.

Затем проверьте аутентификацию и транспорт

  • API-ключ существует и действителен? 401 обычно означает отсутствующий или неверно отформатированный заголовок, либо ротированный ключ.
  • URL эндпоинта и метод верны? POST на GET-путь будет выглядеть как проблема с ключом.
  • Ваш таймаут слишком жёсткий? Если клиент сдаётся до завершения задачи, вы видите таймаут, не связанный с моделью.

Затем проверьте структуру запроса

  • Класс кода состояния говорит, куда смотреть. 4xx почти всегда проблема вашего запроса; 5xx обычно временные и заслуживают ограниченного повтора.
  • Читайте сообщение об ошибке буквально. Печатайте тело ответа до выброса исключения. Поле, упомянутое в сообщении, и есть то, что нужно исправить.
  • Ответы об ограничении скорости или квоте означают: замедлитесь и повторите с задержкой, а не переписывайте промпт.

Наконец, проверьте промпт

Если вызов успешен, но изображение неверно, вы в области промпта, а не ошибки:

  • Субъект отсутствует или слишком общий? Переместите его в первое предложение и сделайте конкретным.
  • Композиция неверна? Исправляйте и соотношение сторон, и слова кадрирования; не компенсируйте одно другим.
  • Дефекты повторяются? Добавьте короткое, конкретное негативное слово.
  • Есть противоречие? Найдите негативное слово, борющееся с позитивным промптом, и удалите его.

Самое важное — сохранять привычку: для каждой важной генерации записывайте точное тело запроса, статус ответа и ссылку на изображение. Воспроизводимость превращает отладку из догадок в сравнение. Составьте первый запрос, проверьте вывод, затем ужесточите промпт перед запуском — и сохраните тело запроса, с которым вышли в продакшен, чтобы следующее изменение имело реальную базу для сравнения.

Похожие статьи

Все статьи →

Начните работать с постоянными артефактами ИИ

Получите API-ключ и вызывайте модели изображений, видео и аудио через один API на основе tasks.

Читать документацию API