Интеграция AI в Django через AI Gateway: сервисный слой и фон
Как встроить AI в Django: OpenAI SDK с base_url AI Gateway в отдельном сервисном слое, вызов из view и вынос долгих запросов в фоновые задачи Celery, ключ в окружении.
Аккуратная интеграция AI в Django — это не вызов модели прямо во view, а тонкий сервисный слой, который прячет клиент OpenAI SDK за одной функцией. View дёргает сервис для быстрых запросов, а тяжёлые (разбор длинных текстов, пакетная обработка) уходят в фон. Модели берём из каталога AI Gateway по OpenAI-совместимому API.
Подготовка
Понадобится ключ sk-aigate-… и адрес https://ai-gatewey.ru/v1. Ключ читаем из окружения (os.environ или django-environ), а не из settings.py в репозитории.
pip install openaiРеализация
- Сервисный слой
Один модуль инкапсулирует клиент и все обращения к модели — остальной код Django ничего не знает про SDK:
# ai/services.py import os from openai import OpenAI client = OpenAI( base_url="https://ai-gatewey.ru/v1", api_key=os.environ["AIGATE_API_KEY"], ) def ask(prompt: str, model: str = "deepseek/deepseek-chat") -> str: resp = client.chat.completions.create( model=model, messages=[{"role": "user", "content": prompt}], ) return resp.choices[0].message.content - Вызов из view
View остаётся тонким — принимает запрос, зовёт сервис, возвращает JSON:
# ai/views.py import json from django.http import JsonResponse from django.views.decorators.http import require_POST from .services import ask @require_POST def chat(request): prompt = json.loads(request.body)["message"] return JsonResponse({"reply": ask(prompt)}) - Долгие запросы — в фон
Запрос к модели может идти секунды, а под нагрузкой это заняло бы worker'ы Django. Выносим в задачу Celery и записываем результат в модель:
# ai/tasks.py from celery import shared_task from .models import Ticket from .services import ask @shared_task def summarize_ticket(ticket_id: int): ticket = Ticket.objects.get(pk=ticket_id) ticket.summary = ask(f"Кратко изложи суть обращения:\n\n{ticket.body}") ticket.save(update_fields=["summary"]) - Запуск задачи
Из view или сигнала ставим задачу в очередь неблокирующе — пользователь получает ответ сразу, а саммари появляется позже:
summarize_ticket.delay(ticket.id)
settings.py под контролем версий. Запрос к модели — сетевой вызов на секунды: в синхронном view под нагрузкой он свяжет worker, поэтому пакетную и фоновую работу отправляйте в Celery или другой воркер.Какие модели подойдут
Для массовых операций (классификация, саммари обращений) берут быструю дешёвую модель; сложные задачи можно точечно направить на флагман:
| Модель | Ввод, ₽/1М | Вывод, ₽/1М | Контекст |
|---|---|---|---|
| DeepSeek: DeepSeek V3 | 31 | 125 | 128K |
| OpenAI: GPT-5.4 Mini | 118 | 705 | 400K |
| Anthropic Claude Haiku Latest | 157 | 784 | 200K |
Частые вопросы
Обязателен ли Celery?
Нет. Для быстрых ответов хватает синхронного вызова сервиса прямо во view. Фон нужен там, где запрос долгий или их много: подойдёт Celery, RQ, Dramatiq или Django-Q — сервисный слой при этом не меняется.
Где хранить ключ в Django?
В переменной окружения, а в settings.py читать её через os.environ или django-environ. Так ключ не попадёт в репозиторий и легко меняется между стендами.
Как показать ответ модели «печатающимся»?
Включите stream=True в сервисе и отдавайте чанки через StreamingHttpResponse. На классическом WSGI это работает, но для устойчивого стриминга лучше ASGI-стек (Daphne/Uvicorn).
AI в Django-проекте — начните с ключа
Получить ключ