Вы неделю смотрите в Google Data Studio, сверяете отчеты маркетплейсов с банковскими выписками — и все равно не понимаете, почему товар, который по расчетам приносил 30% маржи, в реальности ушел в минус. Знакомо?
Проблема классическая: комиссии меняются каждый месяц, акции срезают логистику, а возвраты создают скрытые убытки. BI-отчеты на жестких правилах ломаются при первом же изменении тарифов. Я прошел через это с десятком продавцов и пришел к другой парадигме — вместо системы правил поставить три AI-модели, которые сами разбираются в хитросплетениях API Ozon и Wildberries.
Ниже — архитектура SaaS-решения, которое я запустил в production в начале 2026 года. Полный реверс-инжиниринг API, параллельные агенты Claude 4 Opus и консилиум из трех моделей. Код — только ключевые фрагменты (без токенов, разумеется).
Проблема: почему BI-правила — это мертвый груз
Допустим, вы продаете чехлы для телефонов. Себестоимость 200 руб, продаете за 500. По грубой логике — 300 руб прибыли. Но Ozon удерживает:
- комиссию за продажу (меняется в зависимости от категории и отзыва)
- логистику до склада и до покупателя (зависит от региона и веса)
- хранение (динамические тарифы)
- участие в акции "Молния" (вычитается автоматом)
- плату за возврат (если товар вернули)
- штрафы за брак (иногда списывают без объяснения)
Каждый месяц эти статьи меняются, а API не всегда возвращает детализацию. В результате BI-дашборд с правилами "комиссия = 15%" показывает одно, а реальность — другое. Продавцы принимают решения вслепую: закупают то, что "по отчету" прибыльно, а на деле — убыточно.
Типичная ошибка: использовать статические формулы на основе выгрузок маркетплейсов. Wildberries, например, в 2025 году изменил тарификацию на "пост-фактум" — старые правила устарели за ночь.
Решение — не городить сотни if-else, а научить модели самим выковыривать все удержания из логов API и классифицировать их.
Архитектура SaaS: три слоя, три модели
Система состоит из трех ключевых компонентов, каждый на отдельном агенте Claude 4 Opus (через API Anthropic). Модели запускаются параллельно, объединяя результаты через консилиум.
Модель 1 — Реверс-инжиниринг (Extractor)
Задача: каждую ночь пробивать API Ozon и Wildberries, собирать все возможные поля с транзакциями и комиссиями, даже те, что не документированы. У Ozon, например, есть скрытые поля в ответе POST /v3/finance/transactions/list, которые появляются только при определенных значениях operation_type.
Как это работает:
- Агент через цепочку запросов атакует API с разными параметрами (например, меняем
period_fromиpage_token) - Собирает все ключи ответа, даже null-поля
- Сравнивает с предыдущим срезом и фиксирует новые поля
- Отправляет сырые данные в классификатор
import httpx, json, asyncio
async def extract_fields(api_token: str, base_url: str):
"""Генерация запросов для выявления всех полей API"""
client = httpx.AsyncClient(base_url=base_url, headers={'Authorization': f'Bearer {api_token}'})
seen_fields = set()
# Перебираем типы операций
for op_type in ['sale', 'return', 'compensation', 'storage', 'logistics']:
payload = {
'operation_type': op_type,
'limit': 100,
'period_from': '2026-04-01'
}
try:
resp = await client.post('/v3/finance/transactions/list', json=payload)
data = resp.json()
# Рекурсивно собираем все ключи
def collect_keys(obj: dict, prefix=''):
for k, v in obj.items():
full = f'{prefix}.{k}' if prefix else k
seen_fields.add(full)
if isinstance(v, dict):
collect_keys(v, prefix=full)
elif isinstance(v, list) and len(v) > 0 and isinstance(v[0], dict):
collect_keys(v[0], prefix=full)
collect_keys(data.get('transactions', {}))
except:
pass
return seen_fieldsЭтот код — ядро реверс-инжиниринга. Он добывает поля, которые потом модель классифицирует.
Модель 2 — Классификатор (Classifier)
Получив сырой JSON от Extractor, модель должна каждое удержание отнести к одному из заранее известных типов: комиссия, логистика, хранение, маркетинг, штраф, возврат. Раньше это делали регулярками — и они ломались при смене названий. Теперь модель смотрит на контекст операции, сумму, описание и принимает решение.
Classifier использует few-shot промпты с примерами из прошлых разборов. Мы храним их в векторной базе, подтягиваем похожие транзакции.
import anthropic
client = anthropic.Anthropic(api_key='sk-ant-...')
def classify_transaction(raw: dict, similar_cases: list) -> str:
prompt = """
Ты — классификатор транзакций маркетплейса. У тебя есть сырая запись и несколько похожих исторических случаев.
Определи тип удержания. Возможные типы: комиссия, логистика, хранение, маркетинг, штраф, возврат, прочее.
Ответь только названием типа.
Транзакция:
{raw}
Похожие случаи:
{cases}
""".format(raw=json.dumps(raw, ensure_ascii=False)[:2000], cases=json.dumps(similar_cases, ensure_ascii=False)[:3000])
response = client.messages.create(
model="claude-4-opus-20260501",
max_tokens=10,
messages=[{"role": "user", "content": prompt}]
)
return response.content[0].text.strip()Модель 3 — Расчетчик P&L (Calculator)
Третья модель берет данные от классификатора, добавляет себестоимость из ERP продавца и вычисляет прибыль по каждому SKU, учитывая динамические группы (акции, сезонность). Она понимает, что если товар участвовал в "Черной пятнице", то комиссия могла быть фиксированной, а не процентной.
Calculator работает асинхронно, собирая результаты от Extractor и Classifier, и может пересчитывать за предыдущие периоды с новыми правилами (backtest).
Оркестрация: консилиум и параллельные агенты
Все три модели запускаются ночным батчем. Я использую простой async pipeline на asyncio. Агенты работают параллельно, после завершения — синхронизация через Redis.
async def nightly_pipeline():
# 1. Extractor запускается по очереди для Ozon и WB
extractor_tasks = [extract_fields(TOKEN_OZON, OZON_URL), extract_fields(TOKEN_WB, WB_URL)]
raw_results = await asyncio.gather(*extractor_tasks)
# 2. Classifier обрабатывает каждую транзакцию в пуле
classifier_tasks = []
for raw in raw_results:
case = find_similar(raw) # из векторной базы
classifier_tasks.append(classify_transaction(raw, case))
classifications = await asyncio.gather(*classifier_tasks)
# 3. Calculator сводит данные
calc = Calculator(erp_data=get_erp())
pnl = calc.compute(raw_results, classifications)
# Сохраняем в БД
await save_pnl(pnl)
return pnlАрхитектуру можно масштабировать горизонтально: Extractor — ставим несколько воркеров на разные категории API, Classifier — пул с разными промптами для разных маркетплейсов.
Нюансы и грабли, на которые я наступил
1. Лимиты API. Ozon и Wildberries начали ограничивать частоту запросов. Пришлось добавить адаптивный backoff с экспоненциальной задержкой и параллелить по разным API-ключам. Для Wildberries используется механизм X-Rate-Limit.
2. Изменение структуры ответов. За 2025 год Ozon трижды менял формат отчета по финансам. Модель-классификатор автоматически адаптируется, если подать ей новый пример — но нужно наладить мониторинг покрытия (доля неклассифицированных транзакций). Если поднимается выше 5% — CI/CD запускает автоматическую дотренировку на новых данных.
3. Ложные срабатывания. Иногда модель относит обычную комиссию к штрафу. Решение — консилиум: если три модели дают разные ответы, запускается голосование с учетом confidence score. Confidence ниже 0.7 — транзакция отправляется на ручную разметку.
4. Себестоимость — ее нужно где-то брать. Без корректной себестоимости (закупка + доставка до склада) расчет P&L бесполезен. Мы интегрируемся с ERP продавца, но 30% клиентов не ведут учет — тогда модель берет средние по категории или цену поставщика из заказов.
Часто задаваемые вопросы
Сложно ли поддерживать такой SaaS?
Требуется DevOps-инженер на полставки, который следит за изменениями API и обновляет промпты. Но это в 10 раз легче, чем переписывать BI-правила.
Какой бюджет на AI-запросы?
На 1000 SKU в день — около $50-70 на двух маркетплейсах. Окупается за счет выявления убыточных товаров.
Можно ли заменить Claude на локальную модель?
Только для классификации — Llama 4 70B справляется с точностью 92%. Для реверс-инжиниринга лучше использовать Claude из-за сложных контекстов.
Почему продавцам это нужно прямо сейчас
Маркетплейсы становятся непрозрачными. Ozon переписывает алгоритмы поиска, а Wildberries создает детекторы AI-изображений — то есть их внутренняя логика все дальше от простых формул. Продавец, который опирается на статичные BI-дашборды, проигрывает тому, кто использует адаптивную AI-аналитику.
Архитектура, описанная выше — не теория. Мы запустили ее в мае 2026 года, и за месяц клиенты нашли в среднем 12% SKU, которые приносили убыток, хотя старые отчеты показывали прибыль. Один из клиентов сэкономил 1,2 млн руб, просто остановив закупку товаров-паразитов.
Чтобы научиться самостоятельно строить подобные системы и разбираться в продуктовых метриках, рекомендую курс "Продуктовая аналитика" от Skillbox — там рассказывают, как превращать сырые данные в решения.
Прогноз: до конца 2027 года статичные BI-правила исчезнут
Я уверен: модели, способные самостоятельно выковыривать данные из API и классифицировать их, заменят все вручную написанные правила. Уже сейчас три большие модели работают эффективнее команды аналитиков с Excel. Следующий шаг — модели-агенты, которые не просто считают P&L, а сами предлагают оптимизацию: переупаковать, поднять цену, отключить акцию.
Если вы все еще используете IF(commission_rate=0.15, ...) в Google Sheets — срочно пересмотрите подход. Потому что через год ваши конкуренты будут запускать AI-агентов, которые пересчитывают прибыль каждые 24 часа в реальном времени.
P.S. Инструмент для поиска open-source альтернатив (например, локальной модели для классификатора) найдете в статье Models Explorer.