9.9 KiB
V2IntentRouter Architecture
1. Архитектура
Текущий V2IntentRouter реализован как LLM-first router.
Deterministic-слой не выбирает маршрут по умолчанию и используется только для:
- preprocessing
- validation ответа LLM
- fallback, если LLM не ответил или вернул невалидный маршрут
Актуальные компоненты:
-
router.pyГлавная точка входа и оркестратор пайплайна. -
modules/normalizer.pyНормализация текста запроса вnormalized_query. -
modules/target_terms.pyИзвлечение retrieval-orientedtarget_terms,endpoint_paths,matched_aliases,alias_docs. -
modules/anchors.pyИзвлечениеanchorsи marker-сигналов для fallback и downstream retrieval. -
routers/route_catalog.pyКаталог допустимых маршрутов (allowed_routes). -
routers/llm.pyОсновной LLM-router. Получает нормализованный запрос,target_terms,anchorsи список допустимых маршрутов. -
routers/validator.pyDeterministic validator для enum-значений, комбинации маршрута и базовой нормализацииconfidence. -
routers/confidence.pyПост-обработка confidence после ответа LLM. -
routers/fallback.pyFallback-маршрутизация, если LLM не ответил или ответ не прошёл validator. -
routers/prompts.ymlPrompt-контракт для LLM-router.
2. Контракт
Вход
user_query: str
Выход
V2RouteResult:
routing_domain: strintent: strsubintent: struser_query: strnormalized_query: strtarget_terms: list[str]anchors: V2RouteAnchorsconfidence: floatrouting_mode: strllm_router_used: boolreason_short: str
V2RouteAnchors:
entity_names: list[str]file_names: list[str]endpoint_paths: list[str]target_doc_hints: list[str]matched_aliases: list[str]process_domain: str | Noneprocess_subdomain: str | None
3. Поддерживаемые домены, интенты и сабинтенты
Домены
DOCSGENERAL
Интенты
DOC_EXPLAINGENERAL_QA
Сабинтенты
SUMMARYFIND_FILES
Допустимые маршруты
GENERAL / GENERAL_QA / SUMMARYDOCS / DOC_EXPLAIN / SUMMARYDOCS / DOC_EXPLAIN / FIND_FILES
Эти маршруты централизованно заданы в routers/route_catalog.py.
4. Актуальный флоу
Пайплайн обработки запроса:
router.pyпринимаетuser_query.modules/normalizer.pyстроитnormalized_query.modules/target_terms.pyизвлекает:target_termsendpoint_pathsmatched_aliasesalias_docs
modules/anchors.pyстроит:anchorsfile_markersarchitecture_markerslogic_markersdomain_markersendpoint_markers
router.pyсобираетQueryFeatures.routers/llm.pyвызывается как основной селектор маршрута.routers/validator.pyпроверяет:- что значения входят в допустимые enum
- что комбинация маршрута разрешена
- что
confidenceможно привести кfloat
routers/confidence.pyкорректирует confidence на основе силы сигналов.- Если ответ LLM валиден, возвращается
V2RouteResultсrouting_mode="llm_default". - Если LLM не ответил, вернул сломанный JSON или невалидный маршрут,
routers/fallback.pyстроит fallback route:FIND_FILES, если естьfile_markersDOCS / DOC_EXPLAIN / SUMMARY, если есть docs-oriented anchors- иначе
GENERAL / GENERAL_QA / SUMMARY
5. Компоненты по флоу
router.py
-
Задача Оркестрировать полный routing pipeline.
-
Как решает Последовательно вызывает:
- normalizer
- target terms extractor
- anchor extractor
- LLM router
- validator
- confidence adjuster
- fallback router
-
Вход
user_query: str -
Выход
V2RouteResult
modules/normalizer.py
-
Задача Привести запрос к стабильной форме для анализа.
-
Как решает Схлопывает лишние пробелы через
" ".join(...split()). -
Вход
user_query: str -
Выход
normalized_query: str
modules/target_terms.py
-
Задача Построить чистое retrieval-поле
target_terms. -
Как решает Использует позитивную модель отбора и включает в
target_termsтолько:- endpoint paths
- identifier-like tokens
- alias canonical terms
- domain terms
Исключаются:
- question words
- intent words
- filler/noisy words
- marker words
- короткие токены
< 3, если это не endpoint или alias - битые path-like токены
Дополнительно:
- lowercase
- trim punctuation по краям
- dedupe
- ограничение до
7элементов - приоритет: endpoints → identifiers → aliases → domain terms
-
Вход
normalized_query: str -
Выход
TargetTermsAnalysis:target_termsendpoint_pathsmatched_aliasesalias_docs
modules/anchors.py
-
Задача Построить
anchorsи marker-сигналы, не смешивая их сtarget_terms. -
Как решает Извлекает:
entity_namesиз PascalCase-like токеновfile_namesтолько по жёстким правилам:*.md,*.yaml,*.yml,*.jsondocs/...,doc/...,documentation/...
endpoint_pathsизTargetTermsAnalysistarget_doc_hintsиз alias docs, endpoint map и marker-сигналов
Marker-сигналы живут отдельно:
file_markersarchitecture_markerslogic_markersdomain_markersendpoint_markers
-
Вход
normalized_query: strTargetTermsAnalysis
-
Выход
AnchorAnalysis
routers/route_catalog.py
-
Задача Держать один источник истины для допустимых маршрутов.
-
Как решает Возвращает:
- список
allowed_routesдля payload LLM - проверку допустимости комбинации
routing_domain + intent + subintent
- список
routers/llm.py
-
Задача Выбрать маршрут через LLM как основной селектор.
-
Как решает Формирует JSON payload из:
normalized_querytarget_termsanchorsallowed_routes
Затем:
- вызывает LLM
- парсит JSON
- возвращает сырой candidate route без deterministic business-routing
-
Вход
normalized_query: strtarget_terms: list[str]anchors: dict
-
Выход
dict | None
routers/validator.py
-
Задача Deterministic validation ответа LLM.
-
Как решает Проверяет:
- что
routing_domain,intent,subintentзаполнены - что комбинация маршрута входит в
route_catalog - что
confidenceможно привести к числу
- что
-
Вход
dict | None -
Выход Валидированный
dict | None
routers/confidence.py
-
Задача Сделать confidence осмысленным после ответа LLM.
-
Как решает Корректирует confidence:
-0.1, если нет strong anchors-0.1, если запрос короткий или vague+0.05, если есть явный signal (file_markers,endpoint_paths,endpoint_markers)- затем clamp в диапазон
0.0..1.0
-
Вход
confidence: floatQueryFeatures
-
Выход
confidence: float
routers/fallback.py
-
Задача Построить deterministic fallback, если LLM невалиден.
-
Как решает Правила:
- есть
file_markers→DOCS / DOC_EXPLAIN / FIND_FILES - есть docs-signals (
endpoint_paths,target_doc_hints,matched_aliases, marker groups) →DOCS / DOC_EXPLAIN / SUMMARY - иначе →
GENERAL / GENERAL_QA / SUMMARY
- есть
-
Вход
user_query: strQueryFeaturesanchors: V2RouteAnchorsllm_attempted: bool
-
Выход
V2RouteResult
routers/prompts.yml
-
Задача Задать LLM-router контракт ответа и guidance по confidence.
-
Как решает Ограничивает модель только
allowed_routesи требует JSON с полями:routing_domainintentsubintentconfidencereason_short
6. Ключевые инварианты
- LLM является default router.
- Deterministic-слой не принимает основной routing decision.
target_termsсодержат только retrieval-useful terms.anchorsне содержатterms./healthи другие endpoint paths не должны попадать вfile_names, если это не файл с расширением.file_namesсодержат только реальные file/doc paths.- Fallback используется только если LLM недоступен или вернул невалидный маршрут.