TEXTAGRAM.ru API
Документация API для генерации описания товара по фотографии
Вы можете интегрировать функциональность TEXTAGRAM в свои системы и приложения с помощью нашего API. Для этого нужно зарегистрироваться в TEXTAGRAM.ru и получить API KEY в профиле.
Для всех запросов необходимо передавать API KEY в HTTP-заголовке Authorization:
Authorization: Bearer <API_KEY>
Запрос: генерация текстов по фото
POST /api/text/product
Вызов генерирует карточку товара и возвращает сгенерированные тексты (описание, заголовки и др.).
Параметры запроса (JSON)
| Поле | Тип | Обяз. | Описание |
|---|---|---|---|
image_url |
string | array | Да |
Изображение товара: ссылка на изображение ИЛИ строка data:image/...;base64,... ИЛИ «чистая» base64-строка.
Можно передать несколько фото одного товара массивом строк — тогда все они учитываются в одной генерации.
Максимальное число фото зависит от тарифа; за превышение возвращается ошибка.
Генерация в любом случае списывает 1 кредит независимо от числа фото.
|
short_description |
string (max: 500) | Да | Краткое описание товара. |
product_facts |
object | Нет | Известные характеристики товара. Допустимые поля: brand, model, material, composition, dimensions, weight, color, size, quantity, country, certificates, compatibility, package_contents. Значения — строки до 250 символов; числа передавайте вместе с единицами как строку. Вложенные объекты, массивы и неизвестные поля не принимаются. Доступно на всех тарифах. |
style |
string | Да | Стиль оформления описания (допустимые значения: 'standard','playful','marketing','friendly','storytelling'). |
length |
integer | Нет | Желаемая длина описания: от 200 до меньшего из 3000 и лимита вашего тарифа. По умолчанию — 300, с ограничением по тарифу. |
headers |
boolean | string | nullable | Нет | Если передано true (для совместимости также "headers") — дополнительно генерируются заголовки (поле headers в ответе). |
slogans |
boolean | string | nullable | Нет | Если передано true (для совместимости также "slogans") — дополнительно генерируются рекламные слоганы (поле slogans в ответе). |
creativity |
string | nullable | Нет | Уровень креативности текста: low, middle, high. balanced поддерживается как синоним middle. Опция должна быть доступна на тарифе. |
Дополнительно можно передать keywords (до 500 символов, 20 фраз через запятую, до 100 символов на фразу) при доступности опции на тарифе. Флаги features и audience включают или выключают соответствующие блоки; по умолчанию они включены, если доступны на тарифе. headers и slogans по умолчанию выключены. Для всех флагов используйте JSON true / false; массивы и произвольные строки не принимаются.
Пример характеристик: {"product_facts":{"brand":"Samsung","model":"Galaxy S24","material":"пластик","dimensions":"10 × 15 см"}}. Это сведения, подтверждённые пользователем; сервис не проверяет их независимо. При расхождении с коротким описанием они имеют приоритет. Если явно видимая деталь фотографии противоречит текстовым сведениям, спорное свойство опускается. Ключевые слова не подтверждают свойства товара. Названия брендов и моделей могут оставаться в оригинальном написании.
Для повтора после потери ответа передайте заголовок Idempotency-Key (1–100 латинских букв, цифр или символов ._:-) либо поле request_id. Сохраняйте ключ и исходные поля запроса: успешный повтор возвращает прежний результат без новой генерации и списания. Новая попытка после ошибки генерации требует нового ключа; кредит освобождается.
Ответ (200 OK)
{
"success": true,
"error": null,
"data": {
"uid": "01JABCDEFGH...",
"created_at": "2025-08-23T12:34:56.000000Z",
"style": "standard",
"style_name": "Стандартный",
"description": "...сгенерированный текст...",
"description_length": 234,
"features": ["..."],
"audience": "...описание целевой аудитории...",
"headers": ["..."],
"slogans": ["..."],
"images": ["products/xxxx/yyyy.jpg"]
}
}
Поля features (характеристики) и audience (целевая аудитория) возвращаются, если
соответствующие опции доступны на вашем тарифе; headers и slogans — если они были
запрошены (см. параметры выше) и доступны на тарифе. Иначе приходят пустыми ([] или null).
Ошибка содержит success: false, стабильный code, русское message и совместимое поле error. Неверные параметры или фото — HTTP 422 (invalid_parameters, image_invalid); отсутствующий тариф, API-доступ, недоступная опция или недостаточный баланс — HTTP 403 (plan_required, api_unavailable, tariff_option_unavailable, insufficient_credits). Повтор работающей операции — 409 (generation_in_progress), изменённые поля с прежним ключом — 409 (idempotency_conflict), удалённый результат — 410 (result_deleted). Ошибки генерации — 502: сбой провайдера (generation_failed), отказ модели (generation_refused), незавершённый ответ (generation_incomplete), пустой ответ (generation_empty), нарушение схемы или длины (generation_invalid_response), фото временно недоступно — 502 (image_unavailable), внутренняя недоступность — 500/503 (generation_unavailable). Ограничители частоты и размера могут вернуть 429/413.
Описание проверяется по фактической длине: от 80% до 115% запрошенного объёма, с пробелами, без маркеров **. Запрошенные списки содержат ровно предусмотренное тарифом число непустых строк; аудитория — непустую строку. Лишние или отсутствующие блоки отклоняются. Карточка создаётся только после успешной проверки; при ошибке AI кредит освобождается.
Примеры вызова
PHP (Guzzle)
<?php
require __DIR__ . '/vendor/autoload.php';
use GuzzleHttp\Client;
$baseUrl = 'http://textagram.loc';
$token = '1|YOUR_TOKEN_HERE';
// Варианты image_url: обычный URL, data:image/...;base64,... или «чистая» base64-строка
$imageUrl = 'https://via.placeholder.com/300';
$client = new Client(['base_uri' => $baseUrl, 'timeout' => 30, 'http_errors' => false]);
$payload = [
'image_url' => $imageUrl,
'short_description' => 'Краткое описание товара',
'style' => 'standard',
// 'creativity' => 'balanced',
// 'length' => 200,
];
$response = $client->post('/api/text/product', [
'headers' => [
'Authorization' => 'Bearer ' . $token,
'Accept' => 'application/json',
'Content-Type' => 'application/json',
],
'json' => $payload,
]);
echo $response->getStatusCode() . "\n";
echo (string) $response->getBody() . "\n";
Python (requests)
import requests
base_url = 'http://textagram.loc'
token = '1|YOUR_TOKEN_HERE'
headers = {
'Authorization': f'Bearer {token}',
'Accept': 'application/json',
'Content-Type': 'application/json',
}
payload = {
'image_url': 'https://via.placeholder.com/300',
'short_description': 'Краткое описание товара',
'style': 'standard',
# 'creativity': 'balanced',
# 'length': 200,
}
r = requests.post(base_url + '/api/text/product', json=payload, headers=headers, timeout=30)
print(r.status_code)
print(r.text)
Node.js (axios)
import axios from 'axios';
const baseUrl = 'http://textagram.loc';
const token = '1|YOUR_TOKEN_HERE';
const payload = {
image_url: 'https://via.placeholder.com/300',
short_description: 'Краткое описание товара',
style: 'standard',
// creativity: 'balanced',
// length: 200,
};
axios.post(baseUrl + '/api/text/product', payload, {
headers: {
Authorization: `Bearer ${token}`,
Accept: 'application/json',
'Content-Type': 'application/json',
},
timeout: 30000,
}).then(res => {
console.log(res.status);
console.log(res.data);
}).catch(err => {
if (err.response) {
console.error(err.response.status, err.response.data);
} else {
console.error(err.message);
}
});