Я сделал шахматного помощника для браузера — и Stockfish оказался самой простой частью
Когда я начал делать ChessNavio, задача казалась почти прямолинейной: прочитать позицию с веб-доски, передать её движку и нарисовать стрелку с хорошим ходом. Stockfish давно умеет играть сильнее человека — оставалось только аккуратно подключить его к браузеру.
Первый прототип действительно появился быстро. На тестовой странице всё выглядело убедительно: позиция прочитана, движок ответил, стрелка появилась. Настоящее веселье началось на живых сайтах. На гостевом экране Chess.com все фигуры уже стоят на доске до нажатия Play, а на World Chess рядом с основной доской может находиться ещё одна, уменьшенная. Для человека очевидно, что происходит. Для наивного селектора обе доски выглядят вполне настоящими.
Тогда и выяснилось, что найти сильный ход гораздо проще, чем понять, к какой именно доске он относится и не устарел ли результат за время расчёта.
Так небольшой эксперимент превратился в полноценное расширение для Chrome, Edge и Яндекс Браузера. Ниже расскажу, что получилось, где всё ломалось и почему у такого продукта невозможно обойти неудобный вопрос про шахматные читы.
Чтобы не держать интригу до конца: подсказка во время партии с человеком — это чит, и большинство площадок её запрещает. Против компьютера, на тренировочной доске или после партии тот же механизм становится обычным анализатором. ChessNavio не обещает обход античита; ниже ещё вернусь к тому, где я провёл границу со своей стороны.
Что делает ChessNavio
ChessNavio распознаёт активную шахматную партию в браузере и показывает подсказку рядом с доской: рекомендуемый ход, стрелку, варианты и короткое объяснение идеи.
Можно выбрать формат помощи:
- получить ход сразу;
- открывать подсказку по шагам;
- сначала сыграть самому, а затем сравнить решение;
- сохранить партию и разобрать критические позиции после её завершения.
Расчёт выполняется локально. Текущая позиция, варианты Stockfish и текст подсказки не отправляются на сервер. Сервер нужен для аккаунта и доступа, но не находится между доской и движком.
Есть и отдельный анализ PGN/FEN в браузере — им можно пользоваться без установки расширения. Но основной сценарий проекта всё-таки другой: помощник находится рядом с доской и не заставляет постоянно переключаться между вкладками.
Почему «увидеть доску» недостаточно
На шахматной странице может одновременно находиться несколько досок: игровая, миниатюра последней позиции, трансляция, анализ или скрытый элемент мобильной вёрстки. Наличие 64 клеток и фигур ещё не означает, что пользователь вообще начал партию.
У простого прототипа здесь нет ощущения контекста. Он может выбрать первый подходящий узел в DOM, получить корректную позицию и честно рассчитать для неё лучший ход. Математически всё верно — только зелёная стрелка относится не к той доске. В первый раз такой результат выглядит почти забавно. В продукте это уже недопустимая ошибка.
Поэтому общего селектора вида «найди доску и запусти Stockfish» у расширения нет. Для каждой площадки нужен отдельный адаптер, который проверяет маршрут, видимость доски, состояние партии, сторону пользователя и другие признаки.
Если данных недостаточно, ChessNavio ничего не показывает. Ложный отказ здесь лучше, чем уверенная подсказка для чужой трансляции или соседней миниатюры.
Даже правильную доску нельзя читать в произвольный момент. После хода сайт несколько раз меняет DOM: фигура уже переместилась, индикатор очереди ещё старый, список ходов обновится чуть позже, а сама доска может быть полностью пересоздана. Для игрока это одна плавная анимация. Для расширения — несколько противоречивых состояний подряд.
Позицию приходится читать повторно и считать подтверждённой только после короткой стабилизации.
Старый правильный ответ тоже бывает ошибкой
Есть ещё одна гонка. Stockfish начал анализировать позицию, но за это время пользователь сделал ход, открыл реванш или вернулся в восстановленную вкладку. Движок честно прислал хороший результат — только он уже относится к прошлому состоянию.
Представьте: на доске уже сделаны два быстрых хода, а поверх новой позиции внезапно появляется стрелка из позапрошлой. Движок не ошибся, отмена задачи тоже была отправлена — просто старое сообщение уже стояло в очереди. Именно такие ошибки раздражают сильнее обычного сбоя: интерфейс выглядит уверенным и показывает убедительную ерунду.
Поэтому каждый запрос привязан не просто к FEN, а к снимку сессии: партии, позиции, стороне игрока и монотонному номеру состояния. Перед показом результата расширение сравнивает этот снимок с текущим. Не совпало хоть одно поле — ответ отбрасывается.
Команды stop для движка недостаточно. Она не может отменить сообщение, которое уже оказалось в очереди. Надёжнее считать любой поздний результат потенциально устаревшим и не давать ему доступ к интерфейсу без повторной проверки.
Почему движок работает на компьютере пользователя
Stockfish 18 и модель выбора более «человеческих» ходов находятся внутри расширения. У такого решения есть цена: сборка весит больше, а анализ нагружает процессор. Зато позиция не путешествует через внешний API, а скорость ответа не зависит от сети и состояния сервера.
Сложность добавляет Manifest V3. Фоновый service worker браузер может остановить после бездействия, поэтому его нельзя считать вечным процессом с надёжно сохранённой памятью. Расширение должно уметь восстановить соединение, перезапустить расчёт и при этом не показать старую стрелку.
Сам движок поэтому живёт в отдельном локальном контексте, а задачи идут через очередь. Подсказка для текущей позиции имеет приоритет над фоновым разбором уже сыгранной партии.
А ход «примерно как человек» — это просто слабый Stockfish?
Я тоже сначала так думал: уменьшаем глубину — получаем более слабую и человеческую игру. На практике ограниченный Stockfish иногда пропускает простой ответ, а в следующей позиции всё равно находит компьютерный манёвр.
Поэтому объективная оценка и выбор рекомендации разделены. Stockfish оценивает позицию и тактический риск. Локальная Maia предлагает ходы, которые чаще встречаются в человеческой игре, а Stockfish отбрасывает слишком дорогие ошибки. Для максимальной силы остаётся обычный лучший ход движка.
Это не точная имитация рейтинга и не обещание «сыграть как конкретный шахматист». Скорее способ отделить объективно лучший ход от разумной рекомендации выбранного уровня.
Теперь о главном: это помощник или чит?
Зависит не от названия расширения, а от контекста.
Если показывать движковые подсказки во время партии с человеком, это шахматный чит. Большинство площадок запрещает такую помощь. Если тот же инструмент используется в игре с компьютером, на своей тренировочной доске или для разбора завершённой партии, это уже обычный шахматный помощник и анализатор.
Я не хочу прятать эту границу за словом «обучение». ChessNavio не обещает незаметность, обход античита или защиту от блокировки. Перед подключением сторонней площадки пользователь видит предупреждение и сам отвечает за соблюдение её правил. Техническая совместимость с сайтом не означает одобрение со стороны этого сайта.
Полностью исключить неправильное применение локального инструмента невозможно. Но можно не строить продукт вокруг скрытности, не автоматизировать игру за человека и честно описывать допустимые сценарии.
В каком состоянии проект сейчас
Сейчас расширение умеет показывать ход, стрелку и объяснение, вести локальную историю, разбирать PGN/FEN и восстанавливать работу после сна фонового процесса. Для разных шахматных площадок используются разные адаптеры; статус совместимости указывается по конкретному проверенному режиму, а не обещается сразу для всего сайта.
Пока есть заметный порог входа: расширение устанавливается вручную из архива, а не из магазина. На странице установки опубликованы версия, контрольная сумма, проверка архива и пошаговая инструкция. Обычный разбор PGN/FEN доступен без регистрации.
Рабочая версия проекта и инструкция по установке находятся на сайте ChessNavio.
Сейчас мне важнее всего проверить не силу Stockfish — с ней как раз всё понятно, — а две продуктовые гипотезы:
- Нужны ли людям короткие объяснения рядом с ходом или достаточно одной стрелки?
- Готовы ли пользователи вручную установить расширение ради такого сценария?
Буду рад предметной критике — особенно от тех, кто пользуется шахматными анализаторами или разрабатывал расширения под Manifest V3.