NODEDC_1C/IN/TZ_LLM_Normalizer_v2.0.2.md

468 lines
13 KiB
Markdown
Raw Blame History

This file contains ambiguous Unicode characters

This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.

TZ_LLM_Normalizer_v2.0.2.md
Ниже даю **ТЗ на новый вариант — `Normalizer v2.0.2`**.
Это уже не про “ещё лучше понять бухгалтерию”, а про **доводку устойчивости исполнения** после последнего жирного прогона.
---
# ТЗ: `Normalizer v2.0.2`
## Stability / No-Route / Schema Hardening
---
## 1. Контекст этапа
После перехода на `v2.0.1` система показала правильный вектор:
* `schema_validation_pass_rate = 96.15`
* `scope_in_scope_rate = 92.31`
* `clarification_required_rate = 15.38`
* `out_of_scope` отрабатывается
* нормальные in-scope вопросы в большинстве случаев проходят без лишнего clarification
Комментарий:
Это уже лучше, чем бесконечный prompt-tuning `v1.x`, потому что новая схема стала:
* устойчивее к новым формулировкам;
* лучше разделять допустимый/недопустимый контур;
* меньше душить нормальные вопросы уточнениями.
Но после жирного прогона видны три конкретные проблемы:
1. `schema_validation_pass_rate` упала с 100 до 96.15
2. `no_route_fragment_rate = 20.69` — слишком много
3. часть внутренних состояний (`fallback_type`, `execution_readiness`, `soft_assumptions`) согласованы неидеально
---
## 2. Цель этапа
Довести `v2.0.1` до более устойчивой рабочей версии `v2.0.2`, не меняя базовую архитектуру.
Цели:
* вернуть `schema_validation_pass_rate` к `100`
* разобраться с природой `no_route`
* сделать внутреннюю policy-логику согласованной
* не сломать уже хорошие свойства:
* scope gating
* out-of-scope filtering
* умеренный clarification rate
* decomposition-first подход
---
## 3. Главный принцип этапа
На этом этапе **не надо**:
* снова тюнить под конкретные 26 вопросов;
* переписывать всю prompt-логику;
* возвращаться к `v1.x`;
* пытаться “угадать всё лучше через ещё один prompt”.
Нужно:
* сделать систему **строже и честнее на уровне исполнения**;
* понять, где `no_route` правильный, а где это недонастроенный mapping;
* сделать output pipeline согласованным и стабильным.
Комментарий:
Это уже этап **операционной жёсткости**, а не “семантической магии”.
---
# 4. Что именно надо чинить
---
## 4.1. Проблема A: schema validation не 100
### Симптом
В последнем прогоне:
* `schema_validation_pass_rate = 96.15`
* кейс `BQ-001` не прошёл валидацию
* был retry (`request_count_for_case = 2`)
### Требование
Нужно вернуть:
* `schema_validation_pass_rate = 100`
### Что сделать
1. Разобрать `BQ-001` целиком:
* raw question
* raw model output
* parsed object
* validation error
* retry output
2. Выявить точную причину:
* field missing
* wrong enum
* wrong nested type
* prompt overflow / malformed json
* parser inconsistency
3. Исправить причину на системном уровне, а не точечно под кейс.
### Ожидаемый артефакт
Файл:
`docs/v2_0_2_schema_forensic.md`
Комментарий:
Schema loss даже в одном кейсе — это нельзя игнорировать.
Это технический риск уровня “сломается в проде в неожиданный момент”.
---
## 4.2. Проблема B: слишком много `no_route`
### Симптом
* `no_route_fragment_rate = 20.69`
* `route_distribution.no_route = 6`
### Требование
Разделить все `no_route` случаи на две категории:
### A. Legit no-route
Когда реально нельзя безопасно отправить дальше:
* fragment out-of-scope;
* fragment слишком неопределённый;
* fragment требует clarification;
* fragment семантически распознан, но не относится к исполняемому бухгалтерскому действию.
### B. Missing route mapping
Когда fragment уже in-scope и достаточно понятен, но код не умеет подобрать маршрут.
### Что сделать
1. Выгрузить все fragments с `no_route`
2. Для каждого сделать ручную классификацию:
* `legit_no_route`
* `missing_mapping`
3. Если это `missing_mapping`, добавить deterministic mapping rule
4. Если это `legit_no_route`, зафиксировать policy явно
### Ожидаемый артефакт
Файл:
`docs/v2_0_2_no_route_audit.md`
Комментарий:
Сейчас `no_route` — это ещё слишком “чёрный ящик”.
Нужно сделать так, чтобы каждый такой случай был объясним.
---
## 4.3. Проблема C: несогласованность execution state
### Симптом
Есть кейсы, где:
* `fallback_type = none`
* `predicted_clarification_required = false`
* но `executable_with_soft_assumptions_fragments = 0`
Например:
* `BQ-007`
* `BQ-024`
### Что это значит
Внутренняя state machine не полностью согласована.
### Требование
Согласовать следующие статусы между собой:
* `domain_relevance`
* `execution_readiness`
* `predicted_clarification_required`
* `fallback_type`
* `route_decision`
* `soft_assumption_used`
### Целевая логика
Если fragment:
* in-scope
* не clarification
* не out-of-scope
* и route выбран
то должно быть явно видно:
* либо `execution_readiness = executable`
* либо `execution_readiness = executable_with_soft_assumptions`
Не должно быть “исполняем, но readiness не поднят”.
### Ожидаемый артефакт
Файл:
`docs/v2_0_2_execution_state_machine.md`
---
# 5. Что изменить в схеме
## 5.1. Явно ввести `execution_readiness`
Если ещё не введено как обязательное поле — сделать обязательным.
```json id="mgbtkn"
{
"execution_readiness": "executable | executable_with_soft_assumptions | needs_clarification | no_route"
}
```
## 5.2. Явно ввести `route_status`
```json id="6sdd3j"
{
"route_status": "routed | no_route"
}
```
## 5.3. Явно ввести `no_route_reason`
Если `route_status = no_route`, обязателен reason:
```json id="y0eqbg"
{
"no_route_reason": "out_of_scope | insufficient_specificity | missing_mapping | unsupported_fragment_type"
}
```
Комментарий:
Это очень важно.
Без этого вы будете бесконечно смотреть на `no_route` как на аморфную массу.
---
# 6. Что изменить в коде
---
## 6.1. Добавить post-normalization state resolver
Сделать отдельный кодовый слой после ответа LLM:
```text id="kcynfd"
resolve_fragment_execution_state(fragment, session_context) -> resolved_fragment
```
Он должен:
1. нормализовать readiness;
2. нормализовать route_status;
3. ставить `no_route_reason`;
4. приводить `fallback_type` в согласованное состояние.
---
## 6.2. Ввести deterministic `no_route` policy
Если fragment:
* in-scope
* и не clarification
* и есть достаточно route-critical flags
то `no_route` запрещён.
В таком случае должен выбираться маршрут.
`no_route` разрешён только если:
* fragment реально вне контура;
* fragment реально недостаточно определён;
* fragment unsupported by current route map.
---
## 6.3. Добавить trace completeness check
Сейчас у вас раньше был кейс с пустым trace view.
Нужно проверить, что для каждого run сохраняется:
* raw input
* raw model output
* parsed fragments
* resolved execution state
* final route per fragment
Если trace неполный — логировать это как системную ошибку.
---
# 7. Что изменить в promptах
На этом этапе prompt менять минимально.
Нужно только:
* добавить требование, чтобы fragment-level output был полным и непротиворечивым;
* не трогать общий semantic слой без нужды.
### Добавить в developer prompt
```text id="xlg5ut"
Every in-scope fragment must produce a consistent execution state.
If a fragment is routable, mark it as executable or executable_with_soft_assumptions.
Do not leave routable fragments in an unresolved execution state.
If a fragment cannot be routed, provide an explicit no_route_reason.
```
Комментарий:
Это не semantic tuning, а дисциплина outputа.
---
# 8. Новый eval для `v2.0.2`
Нужен уже не просто набор “сложных вопросов”, а **размеченный eval по policy**.
## 8.1. Состав eval
Собрать 20 кейсов:
### Блок A — routable in-scope
8 кейсов
Ожидание:
* in-scope
* no clarification
* route selected
* no `no_route`
### Блок B — legit clarification
4 кейса
Ожидание:
* in-scope
* clarification needed
### Блок C — out-of-scope
4 кейса
Ожидание:
* out-of-scope
* no route
* fallback out_of_scope
### Блок D — borderline / soft assumptions
4 кейса
Ожидание:
* in-scope
* executable_with_soft_assumptions
* route selected
---
## 8.2. Новые метрики
Обязательно считать:
* `schema_validation_pass_rate`
* `scope_detection_accuracy`
* `route_resolution_accuracy`
* `no_route_precision`
* `false_no_route_rate`
* `execution_state_consistency_rate`
* `clarification_precision`
* `clarification_recall`
---
# 9. Целевые показатели
Минимально приемлемо:
* `schema_validation_pass_rate = 100`
* `execution_state_consistency_rate >= 95`
* `false_no_route_rate <= 10`
* `route_resolution_accuracy` заметно выше текущего
* `clarification_required_rate` не выше текущего на in-scope одноходовых кейсах
Хорошо:
* `false_no_route_rate <= 5`
* `execution_state_consistency_rate = 100`
---
# 10. Что нельзя делать
Codex запрещено:
1. снова возвращать один главный `intent_class` как основу всего;
2. снова лечить всё через few-shot под эти 26 вопросов;
3. занижать `no_route` искусственно, просто проставляя маршрут куда угодно;
4. выключать fallback/out-of-scope;
5. игнорировать единичный schema fail как “неважный”.
---
# 11. Артефакты
Codex должен выдать:
1. `docs/v2_0_2_schema_forensic.md`
2. `docs/v2_0_2_no_route_audit.md`
3. `docs/v2_0_2_execution_state_machine.md`
4. `schemas/normalized_query_v2_0_2.json`
5. `prompts/developer/normalizer_v2_0_2.txt`
6. `reports/v2_0_2_eval_plan.md`
---
# 12. Короткий смысл этапа
`v2.0.2` — это версия не про “лучше понимать язык”, а про:
* **не ломать схему**
* **не терять route без объяснения**
* **сделать внутренние состояния честными и жёсткими**
* **перестать иметь серые зоны между clarification / no-route / executable**
---
# 13. Практический итог
После `v2.0.2` вы должны получить систему, где для каждого fragment всегда понятно:
* он в контуре или нет;
* он исполним или нет;
* если не исполним — почему;
* если исполним — с какими допущениями;
* какой route выбран;
* если route не выбран — по какой строго указанной причине.
Это уже будет нормальный инженерный фундамент, а не “LLM что-то там решила”.
---