Синтетические примеры для проверки LLM до продакшена
Синтетические примеры для проверки LLM помогают собрать тестовые кейсы, когда реальных данных мало. Разберем шаблоны, ошибки и быстрые проверки.

Почему без тестов легко пропустить сбой
Когда реальных данных мало, риск не снижается. Обычно наоборот: команда хуже видит слабые места и слишком рано верит первым удачным ответам. Если модель один раз хорошо решила задачу на демо, это не значит, что она так же ответит на двадцатом, сотом или самом неудобном запросе.
LLM чаще ломается не на обычных фразах, а на редких случаях. Пользователь пишет с опечатками, смешивает русский и английский, дает неполный контекст, просит почти то же самое, что и раньше, но меняет одну важную деталь. В таких местах модель путает шаги, придумывает факт, забывает ограничение или отвечает слишком уверенно там, где должна уточнить.
Это особенно заметно до запуска, когда логов почти нет. У команды нет живой истории запросов, повторяющихся ошибок и длинного списка жалоб. Пустые логи легко создают ложное чувство безопасности. Кажется, что раз плохих примеров нет, то и проблемы нет. На деле проблемы просто еще не успели проявиться.
Синтетические примеры нужны именно в этот момент. Они не заменяют реальные данные, но дают нормальную стартовую точку. С ними можно заранее проверить, как модель ведет себя на простых, спорных и неприятных запросах, и быстро увидеть, где она нестабильна.
Хороший тестовый набор часто вскрывает то, что демо скрывает. Ответ меняется при той же задаче, если чуть переформулировать вопрос. Модель пропускает важное ограничение в длинном сообщении. Вежливый тон маскирует фактическую ошибку. Редкий сценарий ломает логику целиком. А две похожие модели могут давать разный уровень точности.
Это особенно полезно, когда команда сравнивает несколько моделей перед запуском. Если достаточно сменить base_url и прогнать один и тот же набор запросов, различия видны почти сразу. Без тестового набора выбор часто делают по паре красивых ответов, а это слабая проверка.
Самая частая ошибка проста: люди тестируют только то, что удобно показать. Пользователи так не пишут. Они пишут короче, грязнее и страннее. Если учесть это заранее, первый продакшен проходит спокойнее, а правок после запуска становится меньше.
Когда синтетика действительно помогает
Синтетика особенно полезна в самом начале, когда команде нужно быстро ответить на простой вопрос: модель вообще решает вашу задачу или просто красиво ошибается. На этом этапе не нужен идеальный датасет. Нужен набор запросов, который помогает заметить слабые места до первого релиза.
Лучше всего это работает для первых прогонов и сравнения моделей между собой. Если вы запускаете один и тот же набор через несколько моделей, разница видна сразу: где ответ точнее, где модель уходит в фантазии, где теряет формат, а где слишком смело советует опасные действия. Для такого сравнения тестовые кейсы полезнее, чем длинные споры на созвоне.
Есть и более приземленная причина. Во многих командах реальные данные нельзя свободно брать в тесты. Это обычная ситуация для банков, клиник, телекома и госсектора. Переписка клиентов, заявки, внутренние документы, персональные данные - все это часто закрыто правилами, договорами или требованиями по хранению данных внутри страны.
В таких условиях синтетика дает безопасный старт. Можно проверить формат ответов и бизнес-логику без доступа к живым логам, сравнить несколько моделей на одинаковых сценариях, показать риски юристам и безопасности, а еще собрать базовый набор до интеграции с продом.
Но у синтетики есть предел. Она почти всегда чище реальной жизни. Пользователи пишут с ошибками, перескакивают между темами, путают даты, добавляют лишние детали и иногда давят на модель. Если слишком долго опираться только на выдуманные кейсы, команда начинает тестировать удобный мир, а не настоящий.
Поэтому не стоит собирать набор только из правильных, вежливых и аккуратных запросов. Добавьте шум. Пусть один пользователь пишет обрывками, другой просит то, чего система не должна делать, третий смешивает русский и английский. Уже на первом прогоне станет видно, насколько модель держится в реальном разговоре.
Синтетика хороша как первая ступень. Она помогает быстро отсеять слабые варианты и не трогать чувствительные данные раньше времени. Следом нужна проверка на живых, пусть и обезличенных, примерах.
Откуда брать сюжеты для кейсов
Сюжеты лучше собирать не из списка функций, а из реальных задач пользователя. Люди не думают в терминах "поиск тарифа" или "проверка статуса". Они пишут: "Почему у меня списали больше обычного?", "Мне срочно нужен лимит", "Как закрыть карту, если я не в стране?" Именно такие формулировки и дают нормальные кейсы для LLM.
Лучше всего начать с мест, где уже есть живой язык клиентов. Обычно хватает писем в поддержку, чатов с оператором, скриптов колл-центра, жалоб, эскалаций и поисковых запросов по базе знаний. Из них быстро видно, как люди задают один и тот же вопрос десятью разными способами. Для тестов это важнее, чем полный каталог функций. Модель должна понимать намерение, а не угадывать ответ по идеальной формулировке.
Если вы готовите ассистента для банка, телекома или госслужбы в Казахстане, двуязычие нельзя откладывать. В наборе должны быть вопросы на русском, на казахском и в смешанном виде. В реальности человек легко пишет: "Карта заблокталды, что делать?" или "Рассрочка бар ма для этого товара?" Если тесты идут только на чистом русском, картина получится слишком красивой.
Частые запросы дают основу, но на них нельзя останавливаться. Добавьте редкие случаи, где ошибка стоит дорого: возврат денег, раскрытие персональных данных, неверный совет по лимитам, путаница с документами, обещание того, чего сервис не делает. Такие кейсы встречаются реже, но именно они потом ломают запуск.
Нужны и неудобные варианты ввода. Люди делают опечатки, присылают одно слово, отправляют пустое сообщение, пишут капсом или со злостью. Модель, которая уверенно отвечает только на аккуратные запросы, в продакшене быстро теряет форму.
Полезный прием простой: для каждой частой задачи собрать по 5-7 формулировок. Одну обычную, одну короткую, одну с ошибками, одну раздраженную, одну смешанную по языку. Так набор начинает напоминать жизнь, и уже на этом этапе видно, где оценка перед запуском будет честной, а где тесты пока слишком стерильны.
Как собрать первый набор
Первый набор не должен быть большим. Если реальных логов мало, лучше собрать кейсы вокруг ситуаций, где ошибка сразу бьет по деньгам, срокам или жалобам пользователей.
Для первого прохода обычно хватает 5-7 сценариев. Полной картины это не даст, но грубые сбои покажет быстро: модель путает правила, придумывает факты или пропускает важное ограничение.
Рабочая последовательность выглядит так:
- Выберите сценарии с высоким риском. Смотрите на случаи, где неверный ответ ведет к лишней выплате, ошибке в документе, нарушению политики или повторному обращению в поддержку.
- Для каждого сценария запишите цель пользователя одной короткой фразой. Не "получить консультацию", а "узнать статус заявки", "посчитать сумму", "проверить лимит".
- Сделайте 3-5 вариантов одного и того же запроса. Один пользователь пишет кратко, другой дает половину истории, третий ошибается в формулировке или смешивает два вопроса в одном сообщении.
- Добавьте контекст: роль пользователя, дату, сумму, продукт, канал обращения и любые ограничения, которые влияют на ответ.
- Сложите все в одну таблицу. Не держите кейсы в заметках и чатах, иначе команда быстро запутается в версиях.
Контекст часто решает все. Запрос "Можно ли провести платеж сегодня?" без деталей почти бесполезен. Тот же запрос от кассира 31.12 на сумму 4 900 000 тенге при лимите 5 000 000 уже можно проверять нормально.
Удобный шаблон может выглядеть так:
| Сценарий | Запрос | Контекст | Ожидание |
|---|---|---|---|
| Платеж по лимиту | Можно ли провести платеж сегодня? | Роль: кассир; дата: 31.12; сумма: 4 900 000; лимит: 5 000 000 | Модель подтверждает возможность платежа и ссылается на лимит |
| Статус заявки | Что с моей заявкой? | Роль: клиент; заявка подана вчера; номер не указан | Модель просит недостающий идентификатор и не выдумывает статус |
В колонке "Ожидание" лучше писать проверяемый результат. Не абстрактное "ответить хорошо", а конкретное поведение: запросить недостающие данные, не придумывать номер договора, не обещать действие без подтверждения.
Если команда гоняет этот набор через несколько моделей, сравнивать ответы становится намного проще. Сразу видно, где модель держит правило, а где ломается уже на третьем варианте той же просьбы.
Как записывать ожидаемый результат
Ожидаемый результат лучше формулировать не как "идеальный ответ", а как действие модели. Иначе вы начнете оценивать одну удачную фразу, а не поведение в целом. Для теста полезнее запись вроде "если в запросе не хватает данных, модель просит уточнение", чем готовый абзац, который она якобы должна повторить почти слово в слово.
Плохой ожидаемый результат звучит размыто: "ответит вежливо и правильно". Хороший задает проверяемое поведение: "называет только известные факты, не придумывает номер заказа, задает один уточняющий вопрос и отвечает в трех пунктах". Тогда набор становится рабочим инструментом, а не коллекцией красивых ответов.
Запреты тоже стоит писать прямо в карточке кейса. Если их не зафиксировать, проверяющий начнет додумывать правила на ходу. Обычно хватает 2-4 явных ограничений: не выдумывать факт, не выходить из роли, не давать совет вне разрешенной зоны, не обещать действие, которое система не умеет делать.
Для оценки подойдет простая шкала:
- Верно - модель сделала то, что требовалось, и не нарушила запреты.
- Частично - общий смысл верный, но она пропустила шаг, добавила лишнее или слегка ушла от формата.
- Отказ - модель правильно отказалась отвечать там, где отвечать нельзя.
- Эскалация - модель передала случай человеку или в другой канал, если этого требовало правило.
Не смешивайте все в одну оценку. Один и тот же ответ может быть точным по сути, но слабым по форме. Поэтому отдельно смотрите на точность, формат и тон. Точность отвечает на вопрос "правда ли это". Формат проверяет структуру: список, JSON, краткий ответ, ограничение по длине. Тон важен там, где роль влияет на доверие и риск, например в поддержке, банке или медицине.
Кто ставит оценку, лучше решить до первой проверки. Если один аналитик считает ответ "частично", а второй ставит "верно", вы не поймете, стала модель лучше или спорите о вкусе. Обычно команде хватает коротких правил на одну страницу и 3-5 разобранных примеров. После этого любой проверяющий судит кейс по одним и тем же признакам.
Как сделать набор похожим на жизнь
Модель редко ломается на аккуратных промптах из таблицы. Она чаще ошибается на живой речи, где человек спешит, перескакивает между мыслями и сам себе противоречит. Поэтому синтетические кейсы должны быть чуть неровными, а не "учебно правильными".
Смешайте запросы разной длины. Один пользователь пишет: "Где мой счет?" Другой присылает семь строк, где вместе лежат номер заказа, жалоба, лишняя история и просьба "ответить коротко". Если в наборе есть только средние по длине запросы, вы не увидите, как модель ведет себя на краях.
Добавляйте разговорные слова, опечатки, пропуски и шум. Люди пишут "ща", "не грузит", "это то что вчера было", забывают даты и путают названия. Еще они вставляют детали, которые не помогают задаче: "я уже три раза звонил", "я сейчас в дороге", "ответьте без формальностей". Хороший тест проверяет, умеет ли модель отделять нужное от фона.
Отдельно полезно проверять смену темы в одном диалоге. Пользователь может начать с возврата товара, а через два сообщения спросить, сохранились ли его прошлые заявки. Если модель держит только последний вопрос, она теряет нить. Если тащит весь диалог целиком, может ответить не на то.
Стоит намеренно вставлять двусмысленность и конфликтующие факты. Например, в первом сообщении человек пишет, что заказ еще не пришел, а в следующем жалуется на брак в полученном товаре. В такой ситуации хорошая модель не выдумывает ответ, а уточняет, что именно произошло.
Минимум для живого набора такой:
- несколько очень коротких запросов без контекста
- несколько длинных диалогов с лишними деталями
- кейсы, где тема меняется по ходу разговора
- примеры с противоречиями и неясными формулировками
- запросы с перегруженным контекстом, где важная деталь спрятана в середине
Если кейс выглядит слишком чисто, он почти всегда слишком легкий. Набор начинает походить на реальность, когда модель вынуждена не просто продолжать текст, а разбирать беспорядок, задавать уточняющий вопрос и не путать факты.
Пример: помощник банка перед запуском
Банковский чат-бот редко ломается на красивых демо-вопросах. Проблемы начинаются на бытовых сообщениях, где клиент путает термины, пишет на ходу и ждет быстрый ответ. Поэтому тесты лучше строить не вокруг идеальных запросов, а вокруг путаницы, спешки и спорных ситуаций.
Допустим, команда готовит помощника для мобильного банка. Первый кейс: клиент спрашивает лимит перевода, но в тексте смешивает карту и счет. Если бот уверенно отвечает про лимит по карте, когда вопрос был про счет, это уже не мелкая неточность. Такой ответ только усилит путаницу. В хорошем сценарии модель сначала уточняет, о чем именно идет речь, и только потом отвечает.
Второй кейс стоит сделать менее аккуратным. Клиент пишет с ошибками: "срочно скажите почему не уходит денги перевот нужен щас". Здесь команда смотрит не только на смысл, но и на тон. Бот не должен раздражаться, читать нотации или теряться из-за опечаток. Нормальный ответ короткий: признать срочность, запросить нужный минимум данных и, если речь идет о риске блокировки или платежном сбое, быстро передать человека оператору.
Третий кейс полезен для проверки границ. Клиент просит совет по спорной операции, например стоит ли отменять перевод, который уже "висит", или можно ли оспорить списание прямо сейчас. Тут опасно, когда модель начинает советовать слишком смело. Команда должна проверить четыре вещи: где бот может ответить сам по правилам банка, где обязан позвать оператора, как он объясняет передачу без сухого отказа и не придумывает ли процедуры, которых на самом деле нет.
После прогона обычно всплывают слабые места. Один промпт заставляет модель чаще задавать уточняющий вопрос. Другое правило запрещает ей гадать, если клиент смешал продукт, канал или статус операции. Такой тест дает не абстрактную оценку, а понятный список правок: где сократить ответ, где добавить эскалацию, а где убрать слишком уверенный тон.
Где команды ошибаются чаще всего
Самая частая ошибка проста: команда пишет удобные вопросы. Короткие, чистые, без двусмысленности. На таком наборе модель почти всегда выглядит лучше, чем в реальной работе. Потом в продакшене приходят обрывки фраз, смешанные языки, лишние детали, и запас уверенности быстро заканчивается.
С синтетическими кейсами это случается постоянно. Люди невольно придумывают примеры, которые сами же и хотят пройти. Если запрос читается слишком гладко, это повод насторожиться. Хороший тест часто немного раздражает: в нем есть шум, неясность или конфликт условий.
Еще одна ошибка - смотреть на стиль и пропускать факт. Ответ может быть вежливым, ровным и хорошо написанным, но при этом содержать неверную сумму, неверную дату или выдуманное правило. Для бизнеса это опаснее, чем сухой тон. Если помощник банка красиво объяснил несуществующую комиссию, это плохой ответ, даже если текст приятно читать.
Часто набор растет в длину, но не в ширину. Команда берет один сюжет и переписывает его десятью способами. Формально кейсов стало больше, а проверка почти не изменилась. Если у вас 40 примеров про восстановление пароля и только 2 про отказ, эскалацию и работу с персональными данными, набор перекошен.
Полезно делить требования на две группы. В обязательные входят фактическая точность, соблюдение запретов, нужный формат и безопасность. В желательные - тон, краткость, порядок пунктов и подача. Когда эти группы смешивают, оценка ломается. Модель может не пройти тест из-за формулировки, хотя по сути ответила верно. Или наоборот, пройти проверку за счет гладкого текста, хотя нарушила важное правило.
Еще один частый промах - не обновлять набор после изменений. Команда меняет системный промпт, включает новый роутинг модели или переводит часть трафика на другую конфигурацию, а тесты оставляет старыми. После этого старая оценка уже мало что значит. Набор должен меняться вместе с системой, иначе он проверяет прошлую версию, а не текущую.
Быстрая проверка набора
Хороший тестовый набор можно проверить за 15-20 минут. Если на это уходит полдня, набор почти всегда перегружен: слишком много похожих кейсов, размытые ожидания или неудобный формат. Для первой оценки перед запуском лучше иметь компактный набор, который команда понимает с первого взгляда.
Сначала посмотрите на состав. В наборе должны быть обычные запросы, редкие случаи и граничные ситуации. Если есть только типовые примеры, модель покажет красивый результат на демо и сломается на первом странном запросе. Если есть только сложные случаи, вы не поймете, как она ведет себя в повседневной работе.
Для синтетических кейсов работает простое правило: каждый пример должен помещаться в одну короткую запись. В ней достаточно трех полей - запрос пользователя, контекст и ожидаемое действие модели. Ожидаемое действие лучше писать как проверяемое правило, а не как впечатление. Не "ответ звучит уверенно", а "просит уточнение", "не выдумывает тариф", "передает заявку оператору".
Короткий чеклист выглядит так:
- в наборе есть базовые, редкие и граничные случаи;
- у каждого кейса есть запрос, контекст и ожидаемое действие;
- два проверяющих ставят одну и ту же оценку по одним правилам;
- весь набор лежит в одном файле, например CSV или JSONL;
- этот же файл можно прогнать на нескольких моделях без ручной правки.
Практичный формат всегда выигрывает. Один файл проще хранить в репозитории, обновлять после новых ошибок и запускать повторно. Если команда сравнивает несколько моделей через один OpenAI-совместимый шлюз, один и тот же набор можно прогонять по очереди без переписывания интеграции.
Что делать после первой проверки
Первый прогон редко дает чистую картину. Обычно он показывает не среднее качество, а места, где модель ведет себя странно: отвечает слишком уверенно, уходит от формата или путается в простом правиле.
Сразу сохраняйте все спорные ответы. Не только явные провалы, но и случаи, где команда спорит: "это уже ошибка или еще терпимо?" Такие примеры потом приносят больше пользы, чем десяток очевидных тестов.
Для каждого спорного случая полезно фиксировать четыре вещи: исходный запрос, ответ модели, что именно смутило команду и какой ответ вы теперь считаете приемлемым. Так быстро появляется рабочий журнал решений, а не просто папка с неудачными ответами. Через пару итераций он становится основой следующего набора.
Дальше стоит заменить часть синтетики живыми примерами. Даже хороший искусственный набор со временем начинает "учить под тест", а не под реальную работу. Если доступ к данным ограничен, берите обезличенные логи, короткие фрагменты диалогов или вручную переписанные запросы из реальных сценариев.
Часто хватает 20-30% живых кейсов, чтобы увидеть разницу. Например, в банковом помощнике синтетический вопрос про лимит карты обычно аккуратный и полный, а реальный пользователь пишет: "почему опять не проходит". На таких коротких и нервных запросах слабые места видны сразу.
Еще один полезный шаг - прогнать один и тот же набор на двух-трех моделях. Не меняйте промпт, температуру и правила оценки, иначе сравнение получится шумным. Смотрите не только на средний балл, но и на профиль ошибок: одна модель лучше держит формат, другая реже выдумывает факты, третья дает сопоставимое качество дешевле.
Если команде нужно быстро проверять несколько моделей без переписывания интеграции, AI Router может упростить работу. Это OpenAI-совместимый API-шлюз для бизнеса Казахстана и Центральной Азии: можно переключать модели через один endpoint api.airouter.kz и запускать тот же набор с теми же SDK, кодом и промптами.
После этого не расширяйте тесты хаотично. Добавляйте только те кейсы, которые поймали живую ошибку или закрывают новый риск. Такой набор растет медленнее, но он намного честнее.
Часто задаваемые вопросы
Зачем вообще нужны синтетические примеры, если логов почти нет?
Потому что пустые логи легко обманывают. Когда живых запросов почти нет, команда видит только удачные демо и пропускает сбои на редких, грязных и двусмысленных сообщениях.
Синтетика дает стартовую проверку: можно заранее увидеть, где модель путает шаги, выдумывает факт или не просит уточнение.
В какой момент синтетика дает больше всего пользы?
Лучше всего она работает до первого релиза и при сравнении нескольких моделей. Вы прогоняете один и тот же набор и сразу видите, кто чаще держит формат, кто уходит в фантазии и кто ошибается на спорных кейсах.
Если реальные данные закрыты правилами или содержат персональные данные, синтетика позволяет начать тесты без риска.
Откуда брать сюжеты для тестовых кейсов?
Берите не список функций, а реальные формулировки задач. Для этого подходят письма в поддержку, чаты с оператором, жалобы, эскалации, скрипты колл-центра и поисковые запросы по базе знаний.
Смотрите, как люди задают один и тот же вопрос разными словами. Именно такие варианты лучше проверяют понимание намерения.
Нужно ли добавлять казахский и смешанные запросы?
Да, особенно если продукт работает в Казахстане. Пользователи спокойно смешивают русский, казахский и английский в одном сообщении, и модель должна это выдерживать.
Если вы тестируете только чистый русский, результат выйдет слишком красивым. Добавьте хотя бы часть кейсов со смешанной речью и обычными опечатками.
Сколько кейсов нужно для первого набора?
Для первого прохода обычно хватает 5–7 рискованных сценариев и по 3–5 формулировок на каждый. Этого достаточно, чтобы быстро поймать грубые сбои и не утонуть в таблице.
Не гонитесь за объемом. Небольшой, но честный набор полезнее сотни однотипных примеров.
Как правильно записывать ожидаемый результат?
Пишите не идеальный ответ, а поведение модели. Например: она просит недостающие данные, не выдумывает номер заявки, не обещает действие без подтверждения и отвечает в нужном формате.
Так проверяющий оценивает не красивую фразу, а то, как модель ведет себя на задаче.
Как сделать набор похожим на реальные запросы?
Сделайте кейсы неровными. Добавьте короткие сообщения без контекста, длинные запросы с лишними деталями, смену темы в диалоге, противоречия и опечатки.
Если пример выглядит слишком аккуратно, он почти всегда слишком легкий. Живой набор должен немного мешать модели, а не подыгрывать ей.
Где команды ошибаются чаще всего?
Часто команды пишут удобные вопросы, которые сами хотят пройти. Еще они смотрят на вежливый стиль и пропускают фактическую ошибку, или раздувают набор за счет десятков почти одинаковых кейсов.
Другая частая проблема — не обновлять тесты после смены промпта, роутинга или модели. Тогда набор проверяет уже не ту систему, что стоит в работе.
Как быстро понять, что тестовый набор получился нормальным?
Проверьте, что в наборе есть обычные, редкие и граничные случаи, а у каждого кейса записаны запрос, контекст и ожидаемое действие. После этого дайте двум людям оценить несколько примеров по одним и тем же правилам.
Если они ставят похожие оценки и весь набор помещается в один файл, им уже удобно пользоваться в работе.
Что делать после первого прогона модели?
Сохраняйте все спорные ответы и превращайте их в новые кейсы. Затем заменяйте часть синтетики обезличенными живыми примерами, чтобы набор не учил модель только под тест.
Если вы сравниваете несколько моделей, гоняйте один и тот же файл без смены промпта и правил оценки. Через OpenAI-совместимый шлюз вроде AI Router это особенно удобно: можно менять модель, не переписывая интеграцию.