Files
mrcharles 8614827d44 loop: shared bounded-turn core accepts history + knobs (ServeTurn)
Turn machinery refactored so the upcoming serve front door reuses it
instead of copying it: the round loop is now runTurn over arbitrary
message history with an optional tool palette and forwarded max_tokens/
temperature. The serve path (ServeTurn) is stateless chat over client
history with tools hard-off: a tool call the model produces anyway is
refused as a tool result, never executed. Also exposes the model router
(so serve can build its catalog) and a sorted class list; llm requests
can now carry temperature.

💘 Generated with Crush

Assisted-by: Crush:glm-5.2
2026-08-29 01:07:47 -05:00

80 lines
2.4 KiB
Go

// Package models implements MODEL ROUTING v0: a static, config-only map from
// task class -> tier alias -> concrete proxy model. There is deliberately no
// heuristic code: the tier map in harness.toml is the whole contract, and an
// unknown class is a hard error so routing stays auditable.
package models
import (
"fmt"
"sort"
)
// Router resolves task classes to concrete model names.
type Router struct {
tiers map[string]string // tier alias -> concrete model
classes map[string]string // task class -> tier alias
defaultTier string
}
// Decision records one routing outcome for the REPORT trail.
type Decision struct {
Class string
Tier string
Model string
}
// NewRouter validates the config maps and returns a Router.
func NewRouter(tiers, classes map[string]string, defaultTier string) (*Router, error) {
if len(tiers) == 0 {
return nil, fmt.Errorf("models: tier map is empty")
}
if _, ok := tiers[defaultTier]; !ok {
return nil, fmt.Errorf("models: default tier %q has no model entry", defaultTier)
}
for class, tier := range classes {
if _, ok := tiers[tier]; !ok {
return nil, fmt.Errorf("models: class %q points at unknown tier %q", class, tier)
}
}
return &Router{tiers: tiers, classes: classes, defaultTier: defaultTier}, nil
}
// Resolve maps a task class to its tier and concrete model. An empty class
// falls back to the default tier; an unknown class is an error.
func (r *Router) Resolve(class string) (Decision, error) {
tier := r.defaultTier
if class != "" {
t, ok := r.classes[class]
if !ok {
return Decision{}, fmt.Errorf("models: unknown task class %q (add it to [models.classes] in harness.toml)", class)
}
tier = t
}
model, ok := r.tiers[tier]
if !ok {
return Decision{}, fmt.Errorf("models: tier %q has no model entry", tier)
}
return Decision{Class: class, Tier: tier, Model: model}, nil
}
// Tiers returns the sorted tier aliases known to the router.
func (r *Router) Tiers() []string {
out := make([]string, 0, len(r.tiers))
for k := range r.tiers {
out = append(out, k)
}
sort.Strings(out)
return out
}
// Classes returns the sorted task classes known to the router (the
// `harness serve` model catalog is derived from it: one model per class).
func (r *Router) Classes() []string {
out := make([]string, 0, len(r.classes))
for k := range r.classes {
out = append(out, k)
}
sort.Strings(out)
return out
}