Интеграция LLM (ChatGPT/Claude) в мобильного чат-бота
Прямое обращение к OpenAI API из мобильного приложения работает на прототипах и убивает продакшн: ключ в APK — это вопрос часов до его компрометации. Правильная архитектура всегда предполагает прокси-сервер между приложением и LLM. Это не усложнение — это обязательное условие.
Архитектура: что должно быть на сервере
Бэкенд выполняет несколько задач, которые нельзя перекладывать на клиент:
- Хранение API-ключей OpenAI / Anthropic
- Rate limiting по пользователю — без него один активный юзер может выжечь весь месячный лимит
- История диалога — LLM stateless, каждый запрос должен включать предыдущие сообщения
-
Модерация —
omni-moderation-latestот OpenAI или собственная проверка перед отправкой в модель - Кэширование одинаковых запросов (FAQ, часто повторяющиеся вопросы)
История диалога — самый дорогостоящий аспект. Каждый дополнительный обмен репликами увеличивает контекст, а значит — стоимость запроса. Для чат-бота поддержки нет смысла хранить всю историю: достаточно последних 10–20 сообщений плюс system prompt.
Streaming на мобильном клиенте
Пользователь не будет ждать 5–10 секунд пока модель сформирует ответ целиком. Нужен streaming: сервер передаёт токены по мере генерации через Server-Sent Events (SSE) или WebSocket, клиент отображает их в реальном времени.
OpenAI API поддерживает SSE через параметр stream: true. На сервере:
const stream = await openai.chat.completions.create({
model: 'gpt-4o',
messages: conversationHistory,
stream: true,
});
for await (const chunk of stream) {
const delta = chunk.choices[0]?.delta?.content;
if (delta) {
res.write(`data: ${JSON.stringify({ token: delta })}\n\n`);
}
}
res.write('data: [DONE]\n\n');
res.end();
На Android клиент читает SSE через OkHttp EventSource:
val request = Request.Builder()
.url("$baseUrl/chat/stream")
.post(body)
.build()
val listener = object : EventSourceListener() {
override fun onEvent(source: EventSource, id: String?, type: String?, data: String) {
if (data == "[DONE]") return
val token = Json.decodeFromString<TokenEvent>(data).token
viewModel.appendToken(token)
}
}
EventSources.createFactory(okHttpClient).newEventSource(request, listener)
На iOS — URLSession с dataTaskPublisher или AsyncSequence для чтения SSE-потока построчно.
System prompt: главный инструмент управления поведением
Качество бота на 80% определяется system prompt, а не выбором между GPT-4o и Claude. Типичные ошибки:
Слишком общий промпт. «Ты — полезный ассистент магазина» оставляет модели слишком широкий простор. Модель начнёт рассуждать на отвлечённые темы и галлюцинировать несуществующие акции.
Нет ограничений на области знаний. Явно пишем: «Отвечай только на вопросы о продуктах компании X. Если вопрос не по теме — вежливо отказывай».
Не указан формат ответа. Для чат-бота в мобильном приложении длинные абзацы неудобны — просим модель отвечать кратко, использовать списки только когда необходимо.
Anthropic Claude через Messages API работает аналогично, но у него нет system в массиве messages — он передаётся отдельным параметром. Claude лучше держит роль при попытках jailbreak, что актуально для публичных ботов.
Функциональные вызовы (Tool Use / Function Calling)
Для бота, который должен совершать действия (создать заказ, проверить статус, найти товар), нужен механизм function calling. Модель возвращает не текст, а JSON с именем функции и параметрами. Сервер выполняет функцию и отдаёт результат обратно модели для формирования ответа.
tools = [{
"type": "function",
"function": {
"name": "get_order_status",
"description": "Получить статус заказа по его номеру",
"parameters": {
"type": "object",
"properties": {
"order_id": {"type": "string", "description": "Номер заказа"}
},
"required": ["order_id"]
}
}
}]
Это позволяет строить бота, который реально выполняет задачи, а не только отвечает на вопросы.
Выбор модели
| Модель | Контекст | Скорость | Применение |
|---|---|---|---|
| GPT-4o | 128K | Средняя | Сложные сценарии, длинные документы |
| GPT-4o mini | 128K | Быстрая | FAQ, простые запросы |
| Claude 3.5 Haiku | 200K | Очень быстрая | Массовые чаты, streaming |
| Claude 3.5 Sonnet | 200K | Средняя | Качественные ответы, tool use |
Для мобильного чат-бота поддержки GPT-4o mini или Claude 3.5 Haiku дают лучший баланс скорости и стоимости.
Процесс работы
Проектирование архитектуры: сценарии использования, инструменты (functions), хранение истории.
Разработка бэкенда: API-прокси, rate limiting, хранение контекста.
Системный промпт: тестирование на граничных случаях, попытках выйти за рамки темы.
Мобильный клиент: SSE/WebSocket для streaming, UI анимации «печатает...».
Нагрузочное тестирование и настройка лимитов перед запуском.
Ориентиры по срокам
Базовый чат-бот с LLM + мобильный клиент — 3–5 дней. С function calling, историей, rate limiting, модерацией и аналитикой диалогов — 2–4 недели.







