Как довести компьютерное зрение от прототипа до продакшена
Прототип с компьютерным зрением легко собрать в ноутбуке, а вот запустить его в продакшен и не утонуть в грязных данных, форматах, камерах и обновлениях уже совсем другая история. В статье разбирем, что ломается между демкой и боевым контуром и как это учитывать в архитектуре.
16 открытий397 показов
Прототип с компьютерным зрением обычно рождается красиво. Есть ноутбук, Jupyter, пара картинок, модель ловит объекты с 0.9 confidence, все в чате довольны.
Продакшен начинается в тот момент, когда к этой модели подключают реальные камеры, реальное железо, реальную сеть и реальных людей. Там внезапно выясняется, что:
- данные живут своей жизнью
- модель не такая уж «устойчивая»
- пайплайн никто толком не спроектировал
- обновлять все это больно и страшно
Ниже разберем, что обычно ломается по дороге от демки до боевого контура, и что лучше заложить сразу.
1. Прототип обманывает
В прототипе все под контролем:
- вы сами выбрали фотки
- вы сами обрезали кадр
- вы сами решили, в каком формате будет вход
В проде:
- камера дает муть, шум и грязь
- половину времени у девайса кривая экспозиция
- иногда кадр вообще не доезжает
Поэтому первая честная мысль: прототип почти всегда переоценивает качество данных.
Если вы тестировали только на статичных картинках, добавьте себе в задачу: «прогнать модель на реальном видеопотоке хотя бы пару часов» и тупо посмотреть глазами, что приходит. Это сильно остудит оптимизм.
2. Видео против картинок: разные миры
Классическая ошибка: модель обучалась на картинках, а в проде работает с видеопотоком.
С картинками все просто, у вас есть независимые сэмплы. В видео:
- кадры коррелируют
- объекты двигаются
- объекты пропадают и появляются
- часть кадров размазана или с артефактами
Отсюда вылезают вопросы:
- как часто вообще дергать модель
- обрабатывать каждый кадр или через N
- как трекать объекты между кадрами
- что считать «исчезновением» объекта, а что временной потерей
Если этого не прописать в архитектуре, вы получите дергающиеся боксы, прыгающие ID объектов и логику, которая ведет себя рандомно в зависимости от FPS и нагрузки.
3. Пайплайн, а не «одна модель»
В продакшене у вас никогда не «одна модель». У вас цепочка, которая примерно выглядит так:
- Ингест: вытащить кадр из камеры, очереди, файла, потока
- Предобработка: ресайз, кроп, нормализация, поправить ориентацию, вытянуть яркость
- Инференс: прогон через модель (или несколько моделей)
- Постобработка: NMS, фильтры по классам и порогам, подправить координаты
- Аггрегация по времени: трекинг, сглаживание, логика «объект появился/исчез»
- Выгрузка: записать события в базу, отправить дальше, дернуть вебхук, обновить UI
И вот в каждом шаге:
- может быть баг
- может быть деградация качества
- может быть узкое место по скорости
Если в голове по-прежнему живет картинка «я просто вызову model.predict()», то прод упадет в тот момент, когда вам нужно будет, например, поменять формат входа или добавить вторую модель в цепочку.
4. Форматы и протоколы: боль тихая, но убийственная
Еще один классический грабель: форматы данных.
То, что в ноутбуке было «просто numpy array», в проде превращается в:
- RTSP, RTMP, HLS
- JPEG с разными профилями
- видео с разным FPS и битрейтом
- разные цветовые пространства
- разные разрешения и соотношения сторон
А дальше начинается веселое:
- где-то перепутали порядок каналов
- где-то поменяли RGB на BGR
- где-то ресайзнули с искажением пропорций
- где-то забыли нормализовать вход
На демке это почти не видно. В проде это может дать стабильный минус к метрикам, и команда месяц будет думать, что «модель устарела».
Минимум, который стоит сделать:
- явно задокументировать формат кадра на каждом шаге
- держать маленький скрипт, который берет кадр «с продакшена» и прогоняет его через пайплайн локально, чтобы снять подозрения
- иметь тесты, которые проверяют, что формат не поехал после очередного «рефакторинга»
5. Время и синхронизация
Еще одна вещь, про которую обычно вспоминают в последнюю очередь: время.
Если у вас:
- несколько камер
- несколько источников данных
- асинхронные очереди
то рано или поздно выяснится:
- у камеры неправильное время
- у сервера своя временная зона
- сеть добавляет задержку
- сообщения приходят не по порядку
В результате:
- объект в одном потоке «появился» позже, чем в другом, хотя в реальности было наоборот
- события сложно связать
- агрегация по времени превращается в кошмар
Поэтому лучше сразу решить, как у вас будет устроен time:
- откуда берете «истину»
- как нормализуете timestamps
- что делаете с событиями, которые слишком отстают или опережают
Без нормальной временной модели CV система в проде превращается в шизофреника.
6. Версионирование моделей и данных
В прототипе живет одна единственная best_model.pth. В реальном проекте:
- есть старая версия модели, которая «точно работает»
- есть новая, которую все хотят выкатить
- есть эксперименты, которые кто-то успел где-то обучить
- есть разные конфиги порогов и постобработки
Если это не систематизировать, вас ждет:
- «а какой моделью сейчас вообще все крутится»
- «а этот баг был и в прошлой версии или новый»
- «а мы точно не переехали на кривый чекпоинт»
Что нужно минимум:
- хранить модели с понятными версиями
- хранить вместе с моделью: конфиг, пороги, схему постобработки
- иметь хотя бы примитивный model registry, неважно, на чем
- писать в логи, какая версия модели обработала конкретный запрос или кадр
Идеально, когда можно взять конкретный кейс из продакшена, поднять его локально и прогнать через нужную версию модели и пайплайна.
7. Качество: как понять, что все пошло не так
В офлайне вы смотрите на mAP, F1, ROC, красивые таблички. В проде метрики живут другой жизнью.
Что реально надо мониторить:
- распределение confidence по классам
- количество срабатываний по источникам и по времени суток
- долю «пустых» кадров
- кол-во ошибок пайплайна по шагам
- latency на каждый этап
И главное: вам нужно хотя бы какое-то количество вручную размеченных продакшен-примеров, чтобы периодически пересчитывать качество на реальных данных.
Без этого проект живет в режиме «пока никто не жалуется, значит, все ок». Это не стратегия.
8. Перформанс и железо
Еще одна история: модель, которая работает за 40 мс на вашей 3090, внезапно превращается в тыкву на реальном железе.
Там может быть:
- слабый GPU
- CPU-only
- ограниченная память
- ограниченный сетевой канал
При этом вам нужно:
- держать стабильный FPS
- не вываливаться по latency
- не убивать соседние сервисы
Тут начинаются компромиссы: квантование, обрезание входа, уменьшение частоты инференса, батчинг, перенос части логики на edge.
Если вы не считали перформансную бюджетку заранее, то неприятно окажется, что «эта крутая модель невозможна на том железе, которое уже купили».
9. Обновления без инфаркта
Прототип никто не обновляет, его просто перезапускают. Продакшен обновлять придется часто:
- поменялась модель
- поменялась постобработка
- поправили баг в трекинге
- добавили новый класс
Если у вас нет стратегии обновления, то каждый релиз превращается в лотерею:
- отвалится ли половина инстансов
- совпадут ли версии клиента и сервера
- не разъедутся ли схемы событий
Нужен минимальный набор:
- staged rollout (канареечные деплои или хотя бы один тестовый источник)
- возможность отката на предыдущую версию без танцев
- проверка схем и форматов до выката
- простой чеклист «что проверяем после деплоя»
10. Что из этого всего важно прямо сейчас
Если коротко, чтобы CV система дожила до продакшена и не умерла через неделю, ей нужны не только веса модели. Ей нужны:
- честное понимание качества реальных данных
- четко описанный пайплайн от кадра до события
- контроль форматов и времени
- версионирование моделей и конфигов
- мониторинг качества и перформанса
- стратегия обновлений
Если об этом думать с самого начала, код в ноутбуке перестает быть разовой демкой и получает шанс стать нормальным продуктом.
Если нет, вы получите очередной «красивый кейс для презентации», который так никогда и не выйдет за пределы пилота.
16 открытий397 показов



