Реализация AI-генерации описаний товаров в мобильном приложении
Продавец на маркетплейсе делает фото товара с телефона и нажимает «Опубликовать». Ему незачем писать описание вручную — система должна предложить готовый текст по фотографии и категории товара. Это не фантастика: связка Vision API + LLM закрывает задачу за 2–4 секунды.
Откуда берётся контент для описания
Визуальный анализ фотографий
Первый шаг — извлечение характеристик из изображения. Google Cloud Vision Product Search или Azure Cognitive Services Computer Vision возвращают: теги объектов, цвет, бренды на упаковке, текст на этикетке (OCR). Для мобильного приложения удобнее не отдельные вызовы, а мультимодальный LLM (GPT-4o, Gemini Pro Vision) — один запрос с изображением сразу и анализирует, и генерирует текст.
Структурированные атрибуты из формы
Пользователь заполняет минимум: категория, цена, состояние (новое/б/у). Эти данные включаются в prompt как structured context. Остальное модель выводит из фото.
Как реализовано на клиенте
Весь flow асинхронный: пользователь выбирает фото, жмёт «Создать описание», видит skeleton loader, через 2–3 секунды получает редактируемый текст.
// Android: отправка изображения на генерацию
class DescriptionGeneratorViewModel : ViewModel() {
fun generateDescription(imageUri: Uri, category: String) {
_uiState.value = UiState.Loading
viewModelScope.launch {
try {
val base64Image = imageUri.toBase64(contentResolver)
val response = descriptionApi.generate(
GenerationRequest(
imageBase64 = base64Image,
category = category,
language = Locale.getDefault().language,
maxLength = 300
)
)
_uiState.value = UiState.Success(response.description)
} catch (e: Exception) {
_uiState.value = UiState.Error(e.message)
}
}
}
}
На iOS аналогично через async/await + URLSession:
func generateDescription(image: UIImage, category: String) async throws -> String {
let imageData = image.jpegData(compressionQuality: 0.8)!
let base64 = imageData.base64EncodedString()
let request = DescriptionRequest(imageBase64: base64, category: category, language: Locale.current.languageCode ?? "ru")
let response = try await api.generateDescription(request)
return response.text
}
Изображение сжимается до JPEG quality 0.8 перед отправкой — это снижает размер payload с ~3 МБ (RAW с камеры) до ~300–500 КБ без заметной потери качества для Vision API.
Бэкенд: prompt engineering для качественного результата
def build_prompt(category: str, image_tags: list, language: str) -> str:
return f"""
You are a professional copywriter for an online marketplace.
Write a product description based on the provided image.
Category: {category}
Detected attributes: {', '.join(image_tags)}
Language: {language}
Requirements:
- 2-3 sentences, 50-100 words
- Start with the main product feature, not "This is a..."
- Include detected color, condition, and brand if visible
- Use active voice
- No adjectives like "great", "amazing", "perfect"
"""
Запрет на «great», «amazing» и «perfect» — не формализм. Модели по умолчанию пихают их в каждое второе предложение, и описания становятся неотличимы друг от друга.
Streaming для улучшения perceived performance
Вместо ожидания полного ответа — стриминг через Server-Sent Events. Текст появляется по мере генерации, как в ChatGPT. На Android реализуется через okhttp3.EventSource, на iOS — URLSessionDataTask с didReceive data делегатом.
Варианты структуры описания
| Тип товара | Длина | Акцент |
|---|---|---|
| Электроника | 100–150 слов | Технические характеристики + состояние |
| Одежда | 60–80 слов | Размер, цвет, материал, состояние |
| Мебель | 80–120 слов | Габариты, материал, стиль |
| Книги | 40–60 слов | Автор, тема, состояние |
Процесс работы
Проектирование API: формат запроса, обработка ошибок Vision API (нечёткое фото, нет объектов).
Настройка prompt templates по категориям товаров.
Разработка клиентского UI с skeleton loader и редактором результата.
Внедрение streaming для улучшения UX при длинных описаниях.
Ориентиры по срокам
Базовая интеграция (фото → описание через GPT-4o / Gemini) — 3–4 дня. С настройкой промптов по категориям и streaming — до 1 недели.







