Переезд в другую страну — это почти всегда стресс, и Польша здесь не исключение. Карта побыту, виза, ZUS, банковский счёт, налоги, нострификация диплома, воссоединение семьи — на каждом шагу возникают десятки вопросов, а ответы разбросаны по форумам, чатам, устаревшим статьям и окошкам ужендов, где на соседних стойках нередко говорят разное. Легко потеряться, легко поверить неверному совету и потерять на этом недели, деньги и нервы. Именно из этого хаоса и вырос наш проект.

Legalka KB — это бесплатный Telegram-бот, который помогает разобраться в релокации в Польшу. В отличие от обычного чат-бота, который на такие вопросы уверенно фантазирует — выдумывает номера счетов, сроки и адреса ужендов, которых не существует, — Legalka KB отвечает строго из верифицированной базы знаний и честно говорит «не знаю», когда ответа в базе нет. В этой статье мы подробно, но доступно разберём, как система устроена внутри: откуда берутся знания, как рождается ответ, что удерживает бот от выдумок и как мы поддерживаем базу в актуальном состоянии. По ходу — все схемы из нашей внутренней документации.

Главный принцип, на котором держится всё остальное, звучит просто: база знаний и есть продукт. Бот не «умный сам по себе» — он лишь аккуратно достаёт и пересказывает то, что уже лежит в проверенной базе. Нет в базе — нет ответа. Из этого принципа вытекает и вся архитектура, к которой мы теперь и перейдём.

Как устроена система целиком

Прежде чем нырять в детали, полезно увидеть карту целиком. Система состоит из четырёх крупных частей: базы знаний, сборщика практики, ассистента с Telegram-ботом и панели управления для куратора.

Общая схема: сообщения из сообщества проходят через сборщик в базу знаний, а ассистент отвечает пользователям строго из неё.

Слева — источники: открытые чаты и каналы диаспоры в Telegram. Из них сборщик вытягивает «практику» — как всё происходит на самом деле. Справа — сами пользователи, которые задают вопросы боту на пяти языках. В центре — база знаний, разделённая на два слоя, и ассистент, который превращает вопрос в ответ. Всем этим управляет куратор через отдельную панель. Дальше разберём каждый блок по очереди.

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

Из чего состоит проект: каждая часть отвечает за свой участок.

База знаний: «норма» и «практика»

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

Слой «норма» — то, что требует закон. Каждое утверждение сопровождается ссылкой на источник (по возможности — на конкретную статью), помечается проверенным только после ревью юриста и переобследуется не реже чем раз в 60 дней.

Слой «практика» — как это работает в реальности: сроки, привычки инспекторов, нюансы конкретных ужендов. Это наблюдения заявителей, всегда с оговоркой «по сообщениям заявителей» и обязательной датой, после которой факт считается устаревшим (не позже чем +90 дней).

Ни одна страница не попадает к пользователям сразу. Всё рождается как черновик и должно пройти ревью — это защищает от того, чтобы сырые или ошибочные данные ушли «в прод».

Жизненный цикл страницы: от черновика до проверенной нормы или практики.

Пока страница в статусе черновика, бот всё равно может её показывать, но честно помечает такой ответ как непроверенный — чтобы не терять свежие данные, но и не выдавать их за окончательно проверенные.

Как рождается ответ

Это самая важная часть — то, ради чего всё затевалось. Когда пользователь пишет вопрос, ответ проходит цепочку: переформулирование → поиск → оценка релевантности → генерация с проверкой → запись для обратной связи. На каждом шаге у системы есть возможность честно остановиться и сказать «не знаю».

Путь вопроса: поиск → оценка → генерация → привязка обратной связи. Ветки влево ведут к честной абстенции.

Разберём по шагам.

Переформулирование. Диалог редко состоит из полных вопросов. «А какие документы?», «для этого», «а там?» — такие реплики бессмысленны для поиска в отрыве от контекста. Поэтому короткие и ссылочные вопросы компактная модель gpt-4o-mini переформулирует в самостоятельный запрос с учётом истории диалога и выбранного воеводства: «а какие документы?» после вопроса про ВНЖ по бизнесу превращается в «документы для zezwolenie na pobyt czasowy i pracę, mazowieckie». Так поиск не теряет нить.

Поиск. Каждая секция каждой страницы базы заранее превращена в вектор моделью text-embedding-3-small и хранится в поисковом индексе. Запрос тоже превращается в вектор, и система ищет ближайшие по смыслу секции по косинусному сходству. Если пользователь выбрал воеводство, его страницы получают приоритет над общими — чтобы конкретика вроде номера счёта или адреса уженда выигрывала у общих страниц.

Оценка релевантности. Прежде чем что-либо генерировать, система смотрит только на оценки поиска (это отдельный, строго протестированный шаг). Если лучший результат ниже заданного порога или попаданий нет — бот сразу воздерживается. Если совпадение очевидно хорошее и запрос не переформулировался — отвечаем сразу, без лишней проверки моделью. В промежуточных случаях запускается дополнительная проверка.

Проверка моделью. Она сверяет ИСХОДНЫЙ вопрос пользователя (а не переформулированный запрос) с найденными фрагментами — потому что переформулирование иногда «уезжает» на прошлую тему и высоко оценивает не ту страницу. Если проверку не удаётся однозначно интерпретировать, система склоняется к тому, чтобы ответить. Бот воздерживается, только если контекст признан нерелевантным.

Генерация. Ответ формирует та же модель gpt-4o-mini — но только из найденных секций, без «знаний из головы». Каждый факт помечается как «норма» (то, что требует закон) или «практика» (наблюдение заявителей, обязательно с датой). Если в контексте есть конкретика — номер счёта, сумма, адрес — бот выдаёт её прямо, а не отсылает «уточните в уженде», и добавляет официальные ссылки для самостоятельной проверки. Отвечает на языке вопроса, переводя факты из русскоязычной базы. В конце — дисклеймер.

Запись и обратная связь. Каждый выданный ответ записывается (с обязательным удалением персональных данных), чтобы позднее 👍 или 👎 привязались именно к тому, что легло в его основу, и пережили перезапуск бота. Голос 👎 автоматически раскладывается на тип — плохой поиск, плохая генерация или пробел в базе — и попадает на панель как сигнал, что чинить в первую очередь.

Что умеет бот для пользователя

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

Пользовательские возможности: голос, инлайн-кнопки под каждым ответом и команды.

Голос в обе стороны. Вопрос можно не печатать, а надиктовать: голосовое сообщение распознаёт модель whisper-1 с языковым хинтом, бот эхом показывает распознанный текст и обрабатывает его как обычный вопрос. Работает и обратное направление: под каждым ответом есть кнопка «Прочитать вслух» — текст очищается от лишнего и озвучивается моделью tts-1.

Кнопки под ответом. 👍/👎 — обратная связь; 🔊 — озвучить; ✍️ — предложить правку (уходит в очередь предложений); 📍 — показать на карте, если в ответе есть польский адрес; 🔔 — встать в лист ожидания, если по вашему воеводству ещё нет локальной практики; 📋 — создать чек-лист, если ответ перечисляет пункты.

Команды. /topics — обзор разделов базы с примерами вопросов; /checklist и /checklists — личные редактируемые списки (например, «Я» и «Жена»); /region — выбор воеводства; /lang — язык интерфейса и ответов; /new, /chats, /reset и другие — память по нескольким параллельным чатам.

Отдельно про языки: интерфейс и ответы доступны на пяти — русском, украинском, белорусском, польском и английском. Выбор языка «липкий»: один раз указав его, вы не собьёте настройку случайным сообщением на другом языке. Сама база остаётся русскоязычной, а модель переводит каждый ответ на выбранный язык уже на этапе ответа.

Личные чек-листы — это скорее записная книжка, а не часть базы: редактирование списка никогда не трогает саму базу знаний и поиск. Удалив пункт, пришедший из ответа бота, вы убираете его только из своего списка.

Откуда берётся практика

Нормативный слой пишет куратор по официальным источникам. А вот практический слой наполняется полуавтоматически — отдельным сборщиком на LangGraph, который превращает чаты диаспоры в обезличенные, дедуплицированные факты.

Сборщик практики: приём → диалоги → извлечение → фильтр личных данных → классификация → дедупликация → подготовка.

Цифры на сегодня: через сборщик прошло около 2,4 млн сообщений, из которых 28 091 признано релевантными, а из них извлечено 17 284 практических факта. Извлечением занимается модель gpt-4o-mini — только обезличенные факты, без имён, ников и цитат.

Ключевой момент — фильтр персональных данных работает по принципу «сначала безопасность»: сначала автоматический поиск контактов, номеров документов и длинных цитат, при необходимости — дополнительная проверка моделью; любой «грязный» факт отбрасывается без сохранения. Перенос факта в базу — всегда ручной шаг куратора, а не автоматика.

Ещё одна деталь, за которую пришлось побороться, — классификатор тем. Раньше он отправлял весь набор фактов в один запрос к модели, та упиралась в таймаут и молча сваливалась на грубую эвристику по ключевым словам, сбрасывая полезные факты в «мусорную» категорию «прочее». Мы разбили обработку на небольшие порции — и доля «прочего» упала с 51% до 23%, а полезных, но неправильно уложенных фактов стало около 3%.

Историческая загрузка устроена так, чтобы её можно было прерывать и возобновлять: у каждого канала есть контрольная точка, и повторный запуск не начинает всё заново, а продолжает с места остановки.

Как мы держим базу актуальной

Собрать факты — половина дела. Дальше их нужно проверить, отредактировать и одобрить. Для этого у куратора есть локальная панель управления — она работает только на его компьютере и никуда не выставлена наружу.

Панель управления: три вкладки, за которыми стоит вся работа со сбором, базой и ботом.

У панели три вкладки: «Сбор» — контроль сбора фактов, «Ревью» — просмотр, правка и одобрение страниц, и «Предложения» — только-читаемые сигналы от пользователей (предложения правок, сводка 👍/👎, лист ожидания по регионам).

Вкладка «Сбор» показывает статус исторической загрузки и состояние каждого Telegram-канала простыми значками — что уже готово, что идёт, что прервалось и возобновится на следующем запуске.

Вкладка «Сбор»: статус, каналы, управление и просмотр извлечённых фактов.

Вкладка «Ревью» — рабочее место ревьюера: список страниц с фильтрами, детальный просмотр с источниками и проверочными вопросами, и действия по одобрению.

Вкладка «Ревью»: список → детали → действия.

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

Последовательность ревью и одобрения: от выбора страницы до пометки «проверено».

Самое интересное здесь — правка через диалог с ИИ. Вместо ручного редактирования текста куратор просто пишет агенту, что нужно. Агент сам понимает, вопрос это или инструкция на правку.

Агент правок: загрузка → определение намерения → ответ или план → правка → проверка → запись.

Агент трогает только текст страницы — служебные поля, источники и статус черновика остаются нетронутыми. Выдумывать факты ему запрещено: если источника нет, он оставляет пометку о том, что нужен источник, вместо того чтобы что-то сочинить. После правки идёт проверка: не пропали ли разделы, не обрезан ли текст; если потеряно слишком много — до двух повторов, затем откат без сохранения.

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

Диалог с ИИ: вопрос не меняет файл, а инструкция переписывает текст и показывает изменения.

Как мы измеряем качество

Качество ответов у нас измеряется, а не предполагается. Есть набор из 109 «золотых» вопросов, и каждая новая страница добавляет минимум один. Отдельная модель-судья прогоняет этот набор и проверяет две вещи: передал ли ответ суть ожидаемых фактов (по смыслу, не дословно) и не утверждает ли он как факт что-то запрещённое. Проверка специально настроена строго, чтобы «запрещённое» срабатывало только на явное утверждение, а не на простое упоминание темы.

Текущие метрики: цитируемость около 99%, покрытие фактов около 97%, воздержание на вопросах вне базы — 100%.

Свой сервер, свои модели

Ничего из перечисленного не привязано к одному поставщику. Все модели — распознавание смысла, генерация, распознавание и синтез речи — заменяемы на локальные (например, Ollama или LM Studio) одной настройкой, а сам код остаётся прежним. Для чувствительных данных о релокации это значит, что весь стек можно поднять на собственном сервере и не отдавать вопросы пользователей наружу.

Весь цикл целиком

Если собрать всё вместе, жизненный путь одного факта выглядит так: его собирают из чатов, куратор продвигает практику или пишет норму (черновик), ревьюер проверяет и одобряет, изменения фиксируются, а затем поиск пересобирается и прогоняются проверочные вопросы перед релизом.

Полный цикл: сбор → черновик → ревью → проверено → фиксация → переиндексация и тесты.

Заключение

Legalka KB показывает, что «умный ассистент» и «честный ассистент» — не одно и то же. Секрет не в размере модели, а в дисциплине вокруг неё: строгая привязка к проверенной базе, честное «не знаю» вместо догадок, обязательные источники и даты, обезличивание на входе и измеримое качество на выходе. Именно это отличает полезного помощника по релокации от красноречивого генератора выдумок.

Попробовать бот можно прямо в Telegram и бесплатно — @legalka_pl_bot. А если вам нужен похожий ассистент, который отвечает строго из ваших данных и не фантазирует, — напишите нам: development@mi-code.pl.

Какая модель за что отвечает

Напоследок — сводка: какая модель решает какую задачу.

ЗадачаModel
Индексация базы знанийtext-embedding-3-small
Поиск по базе (ретривер)text-embedding-3-small
Переформулирование вопросовgpt-4o-mini
Ответ пользователюgpt-4o-mini
Голосовой ввод (STT)whisper-1
Озвучивание ответов (TTS)tts-1
Извлечение практических фактовgpt-4o-mini
PII-проверка (опционально)gpt-4o-mini
Классификация темgpt-4o-mini
Определение намеренияgpt-4o-mini
Ревизия страниц базыgpt-4o-mini
Eval-судьяgpt-4o-mini

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

Что такое Legalka KB и бесплатно ли им пользоваться?
Legalka KB — это бесплатный Telegram-бот (@legalka_pl_bot), который помогает разобраться в релокации в Польшу: карта побыту, виза, ZUS, банковский счёт, налоги, нострификация диплома, воссоединение семьи и многое другое. Попробовать его можно прямо в Telegram и бесплатно.
Как Legalka KB избегает выдумывания номеров счетов, сроков или адресов ужендов?
В отличие от обычного чат-бота, Legalka KB отвечает строго из верифицированной базы знаний и никогда не использует «знания из головы». Когда ответа в базе нет, он честно говорит «не знаю», а не сочиняет что-либо.
На каких языках можно пользоваться Legalka KB?
Интерфейс и ответы доступны на пяти языках — русском, украинском, белорусском, польском и английском. Выбор языка «липкий», поэтому случайное сообщение на другом языке его не собьёт; сама база остаётся русскоязычной, а модель переводит каждый ответ на выбранный вами язык.
В чём разница между «нормой» и «практикой» в ответах?
«Норма» — это то, что требует закон: каждое утверждение сопровождается ссылкой на источник, помечается проверенным только после ревью юриста и переобследуется не реже чем раз в 60 дней. «Практика» — как всё работает в реальности: наблюдения заявителей, всегда с датой и с оговоркой «по сообщениям заявителей», причём факт считается устаревшим не позже чем через 90 дней.
Заменяет ли Legalka KB юридическую консультацию?
Нет — Legalka KB это не юридическая консультация, а собранные и структурированные данные. Даже когда бот отвечает уверенно и со ссылками, стоит перейти по указанным официальным ссылкам и убедиться самому, ведь правила меняются, а окончательное слово всегда за ужендом.