Skip to content
KLR.gg (собственный продукт) · Игры · Киберспортивная аналитика

KLR.gg: автоматическая аналитика матчей CS2 для приватных лобби

Платформа, которая сама забирает серверные логи, статистику матчей и демозаписи с комьюнити-серверов Counter-Strike 2, оценивает каждую дуэль и раунд и превращает их в рейтинги игроков, динамику и сбалансированные команды — без загрузок вручную и таблиц.

Длительность
4 месяца до запуска, развивается
Опубликовано
26 августа 2026
Стек
PythonpandasFastAPIPostgreSQLNext.jsTypeScriptNode.jsMinIO (S3)DockerSteam OpenIDStripe

100%

игровых дней собираются без ручной загрузки

4

модели рейтинга: 2.0, 3.0, Round Swing, Glicko-2

~2 с

работа пайплайна на одну карту по логу

4

варианта сбалансированных команд

С чего всё началось?

Отправная точка — спор, который каждую неделю ведёт любая компания друзей, играющих в Counter-Strike 2 на собственном сервере: кто на самом деле хорош и как честно поделить команды. Публичные сайты статистики покрывают официальный матчмейкинг, а не приватные лобби, поэтому кто-то ведёт таблицу — пока не бросает. Аудитория немаленькая: Counter-Strike 2 стабильно входит в самые популярные игры Steam с одновременным онлайном от сотен тысяч до более миллиона игроков (Steam, 2024), а Statista (2024) оценивает рынок киберспорта в несколько миллиардов долларов в год.

KLR — наш собственный продукт, который закрывает эти споры цифрами. Он начинался как один Python-скрипт для закрытого лобби из ~25 игроков и вырос в мультитенантную веб-платформу. Это же наш референсный проект по инженерии событийных данных: автоматический сбор, идемпотентный пайплайн разбора и рейтинги, которым доверяют настолько, что о них спорят.

Какую задачу нужно было решить?

Задача — превратить сырой вывод сервера в рейтинги, которым доверяют, без ручных загрузок. Данные есть: сервер CS2 с плагином MatchZy (документация 2024) пишет строку лога на каждый килл, CSV со статистикой игроков на каждую карту и GOTV-демку каждого матча. Но сырые числа — ещё не рейтинг: киллы без пользы для раунда, отсутствующее число раундов, игроки, меняющие ники, несколько Steam-аккаунтов у одного человека. Таблица лидеров, которой не верят, хуже, чем её отсутствие.

Таблица лидеров

Одно лобби, один сезон: Rating 2.0 и 3.0 в стиле HLTV, Round Swing — насколько действия игрока сдвинули вероятность выигрыша раунда — и скилл-рейтинг Glicko-2, где каждый килл считается дуэлью двух игроков.

Сезонная таблица лидеров KLR: карты, раунды, K/D, ADR, KAST, Rating 2.0, Rating 3.0, Swing, Skill, тренд и спарклайн за 30 дней по каждому игроку
Таблица лидеров сезона: раунды, KAST, Rating 2.0 / 3.0, Round Swing, Skill по Glicko-2 и тренд.

Как это было построено?

Решение построено как воркер сбора, рейтинговый пайплайн с полным пересчётом и мультитенантный веб-продукт. Воркер забирает логи, статистику и демки с каждого комьюнити-сервера; пайплайн разбирает логи в дуэли и считает четыре рейтинга — Rating 2.0 и 3.0 в стиле HLTV (HLTV опубликовала составляющие формулы 2.0 в 2017 году), Round Swing и скилл-рейтинг Glicko-2 (система Гликмана с отклонением и волатильностью рейтинга, 2012). Каждый запуск пересчитывает весь сезон, поэтому двойного учёта нет и перезапуск безопасен.

  • Автоматический сбор. Python-воркер подключается по FTP/FTPS, находит новые файлы по времени изменения, забирает их в S3-совместимое хранилище и ставит пересчёт в очередь. Доступы хранятся зашифрованными. Логи (~0,5 МБ на карту) — основной источник, хранятся; демки — запасной, удаляются после разбора.
  • Рейтинговый пайплайн. Модули на pandas разбирают логи в дуэли, считают KAST раунд за раундом, Round Swing с экономическим весом каждого килла, Rating 2.0 и 3.0, рейтинги по картам и Glicko-2. Около двух секунд на карту.
  • Балансировщик команд. Для выбранных игроков предлагает четыре варианта составов — по Rating 2.0, Rating 3.0, Skill и миксу — с ожидаемым разрывом между командами. Логика продублирована на TypeScript, чтобы веб считал мгновенно; расшаренный состав получает публичную ссылку с Open Graph-превью.
  • Продукт. Мультитенантные лобби с ролями, вход через Steam OpenID, снапшоты статистики с откатом в один клик, уведомления, кредиты через Stripe для студии рендера (2D-повторы раундов), GDPR-согласие с аудитом, выгрузка данных и удаление аккаунта.
  • Steam GC-бот. Бот на Node.js забирает демки официального матчмейкинга по share code, так что рейтинговые игры учитываются в том же рейтинге, что и приватные.

Таблица против автоматического пайплайна: что меняется для приватного лобби?

Таблица сравнивает электронную таблицу, с которой начинает большинство лобби, и автоматический пайплайн, которым KLR её заменил. Таблица бесплатна и не требует доступа к серверу, но зависит от одного человека, не умеет считать метрики уровня раунда из CSV со статистикой и молча удваивает результат, если карту внесли дважды. Пайплайну нужны FTP-доступы и воркер — и потом его никто не трогает.

Ручная таблица против пайплайна KLR
КритерийТаблицаПайплайн KLR
Ввод данныхВручную после каждого игрового дняАвтоматически из логов сервера
Метрики уровня раунда (KAST, Round Swing)НедоступныСчитаются по каждой строке килла
Повторный ввод той же картыДвойной учётИдемпотентный пересчёт всего сезона
Смена ников и мультиаккаунтыПравки вручнуюСопоставление по Steam ID
Баланс командКапитаны выбираютЧетыре варианта по рейтингам, ожидаемый разрыв 0,6%
Время на картуМинутыОколо 2 секунд
Ручная таблица против пайплайна KLR

Как идут данные

От игрового сервера до таблицы лидеров без участия человека: воркер, пайплайн, API и веб — отдельные сервисы в Docker; единственный артефакт, который видит веб, — один JSON на лобби, отдаваемый через API с проверкой доступа.

Схема пайплайна данных KLR: сервер CS2, Python-воркер, рейтинговый пайплайн, FastAPI, веб на Next.js и артефакты, которые проходят через них
Поток данных: сервер DatHost → FTP-воркер → логи, статистика, демки → пайплайн → players.json → API → веб.

Результаты

Сбор полностью автоматический, и пайплайн успевает за игровыми вечерами: шесть карт разобраны и оценены в течение минуты после последнего раунда. Балансировщик сокращает разрыв между командами до менее чем одного процента прогнозной доли выигранных раундов.

Оценено карт за игровой день, первый сезон
День 1День 1: 44День 2День 2: 55День 3День 3: 44День 4День 4: 66День 5День 5: 44День 6День 6: 33День 7День 7: 55День 8День 8: 55
Data table
Карты
День 14
День 25
День 34
День 46
День 54
День 63
День 75
День 85
Ожидаемый разрыв между сбалансированными командами
Капитаны выбираютКапитаны выбирают: 8.4%8.4%СлучайноСлучайно: 11.2%11.2%Балансировщик KLR, лучший вариантБалансировщик KLR, лучший вариант: 0.6%0.6%

Среднее за сезон; разрыв — разница прогнозной доли выигранных раундов между двумя командами.

Data table
Разрыв
Капитаны выбирают8.4%
Случайно11.2%
Балансировщик KLR, лучший вариант0.6%

Динамика и составы

Рейтинг по игровым дням с переключением между четырьмя метриками рядом с балансировщиком команд — два экрана, которые реально открывают перед игровым вечером.

Страница трендов KLR: накопительный рейтинг игроков за восемь игровых дней и панель балансировщика с тремя вариантами составов
Тренды: накопительный рейтинг по игровым дням; балансировщик: три из четырёх вариантов составов с ожидаемым разрывом.

Стек

Рейтинговый пайплайн на Python 3 (pandas, matplotlib, awpy для разбора демок); воркер на ftplib с zstd и MinIO; FastAPI с SQLAlchemy и Alembic на PostgreSQL 17; Next.js 16 с React 19 и Tailwind 4; Steam GC-бот на Node.js; Steam OpenID, JWT-сессии, Stripe. Локально всё поднимается через Docker Compose, на VPS в ЕС работает под systemd за nginx.

Кому подходит этот подход?

Подход подходит любой команде, которой нужна платформа событийных данных: автоматический сбор из множества удалённых источников, идемпотентный и быстрый пайплайн разбора, скоринговые модели, которым доверяют, и поверх всего — мультитенантный веб-продукт с ролями, биллингом и комплаенсом. Уберите игру — и та же архитектура работает для телематики, IoT-парков, торговых логов и кликстрим-аналитики. Комплаенс — часть дизайна, а не надстройка: поскольку профили игроков — персональные данные, удаление и выгрузка аккаунта были встроены с первого релиза, как того требует право на удаление по GDPR (статья 17, 2016).

Частые вопросы

Ещё кейсы

Erudil: ИИ-движок, оценивающий вероятность каждого исхода матча

Собственный продукт. Вероятностный движок превращает данные матча в матрицы вероятностей исходов, сверяет их с котировками букмекеров и публикует неизменяемую историю каждого прогноза — и выигрышей, и проигрышей.

  • Спортивная аналитика
  • Python
  • PyTorch
  • PostgreSQL

ИИ-ассистенты по регламентам для продуктовой сети с 30 000 сотрудников

Три RAG-ассистента на одной платформе — для коммерческой функции, директоров магазинов (голосом, прямо из торгового зала) и HR — отвечают на вопросы по корпоративным регламентам со ссылкой на конкретный пункт или честно говорят, что ответа нет, — и сотрудники перестают звонить в офис по типовым вопросам.

  • Ритейл
  • Python
  • LangChain
  • PostgreSQL + pgvector

Document AI, который читает 1 300 накладных от поставщиков в день

Сканы и фото накладных, счетов и актов проходят через мультимодальную модель, которая извлекает типизированные поля с оценкой уверенности по каждому, сверяет их со справочниками поставщиков и договоров и передаёт в ERP. К человеку попадают только документы с низкой уверенностью — примерно каждый девятый.

  • Ритейл · Финансы
  • Python
  • PyTorch
  • Multimodal LLM

Обсудить ваш проект