router: introduce typed ingress boundary and route producer observability
First behavior-preserving slice of the Maven redesign. Establishes explicit ingress/routing boundaries and enough observability to refactor later without changing current routing, action, clarification, or execution semantics. Types introduced: - NormalizedInput (internal/router/source.go): Text + InputSource, the typed ingress boundary replacing raw string at the turn entry. - InputSource (internal/router/source.go): channel provenance enum (tap:voice, tap:text). Reuses the existing turnSource distinction. - RouteProducer (internal/router/intent.go): which cascade stage produced the decision (grammar, heads, llm, classifier). Changes: - Decision carries a Producer RouteProducer field, set at each cascade stage (grammar, heads, LLM, classifier). - turnRoute carries NormalizedInput instead of bare text string. - runTurn takes NormalizedInput instead of (text, src). - decision.Record carries InputSource and RouteProducer for observability; RoutingTrace persists route_producer (migration #27). - turnSource is now a type alias for router.InputSource. Behavior preserved: - Stage-0 grammars unchanged: same order, same matching, same confidence. - Cascade fallthrough order unchanged (grammar → heads → llm → classifier). - Clarification behavior unchanged. - Action dispatch unchanged. - No new linguistic normalization.
This commit is contained in:
@@ -76,3 +76,26 @@ func ValidSource(s Source) bool {
|
||||
}
|
||||
return false
|
||||
}
|
||||
|
||||
// InputSource — which channel this utterance arrived on. The same provenance
|
||||
// vocabulary facts use (internal/event). Threaded through the turn because a
|
||||
// turn can write a fact, and a fact that lies about where it came from is
|
||||
// worse than no fact: provenance is the first column read when asking why a
|
||||
// daemon-wide setting is the way it is.
|
||||
type InputSource string
|
||||
|
||||
const (
|
||||
// InputSourceVoice — a real microphone (PushToTalk).
|
||||
InputSourceVoice InputSource = "tap:voice"
|
||||
// InputSourceText — mavweb /api/chat, telegram, or any text entry point.
|
||||
InputSourceText InputSource = "tap:text"
|
||||
)
|
||||
|
||||
// NormalizedInput — the typed ingress boundary for a turn. Text is the raw
|
||||
// utterance after STT (voice) or as typed (text). Source identifies the
|
||||
// channel. This slice performs no new linguistic normalization: text and voice
|
||||
// paths continue to converge onto the same turn path as they did before.
|
||||
type NormalizedInput struct {
|
||||
Text string
|
||||
Source InputSource
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user