Documentation
¶
Overview ¶
dedup.go:重复调用断路器(Ring 0)。同一轮内,同一能力用完全相同的参数 反复调用是弱模型的高频退化形态(实测:同参 python 连打十几次、同参 read_result 打转,直到 max steps 把轮次拖死)。L1 只祈使"报错不要同参 重试",对"成功但反复调"没有硬约束——这里补上:
第 2 次重复 → 照常执行,结果后附加提醒; 第 3 次起 → 不再执行,回放上次结果并要求换路径。
重复的判定分两档:纯工具 = 同参**且**同结果(结果确定,变化说明是 轮询类,重置计数);kind=skill = **仅同参**——技能结果是子循环模型 生成的自然语言,每次措辞都不同,按结果判定永不触发(实测同参 mutating 技能连执行 5 次),而同轮内同参重调技能几乎必然是退化。
计数按 (执行域, 能力, 参数) 分键,存轮内状态袋(runctx.TurnState), 轮结束即弃;参数一变即重置。无轮语义(未经 agent 入口装袋)不介入。
deliver.go:交付物捕获(Ring 0)。标记了 Deliver 语义的能力返回后, 原文存底(复用结果暂存后端)并收进轮级 sink,给模型的结果前缀注入 引用标记——终答引用 #dN 即原文随行,大脑不再拥有转述权。 设计:docs/deliverable-channel-plan.md;链位:Dedup 内侧(回放不重捕)、 Digest 内侧(捕获的是未消化原文)。
nested.go:组件内部模型调用的 callback 切面。digest 摘要、压缩摘要、 守卫弹回等"包装器内部再调模型"的场景,graph 节点切面只覆盖最外层 Generate,内层调用对进度/tracing 不可见(实测一次 46s 的黑箱 span 里 藏着三次弹回)。按 eino 文档建议:内层调用用 ReuseHandlers 换 RunInfo 并自行上报 OnStart/OnEnd/OnError,使其成为独立可见的子 span。
progress.go:能力执行的进度事件发射门(Ring 0)。
事件从能力包装层发射而非 eino 回调:这里拿得到 capability.Meta 的 真值(Ref.Kind/Domain/Name)——skill 和 tool 在 eino 眼里都是 Tool, 只有能力层分得清。模型事件仍由 observe 切面发射(observe.ProgressEvents 已不再发 Tool 事件,两边不双发)。无订阅零开销(EmitProgress 判 nil)。
Package loop 提供主循环的运行时保障(Ring 0):提示词分层拼装、 上下文压缩、预算控制、审批拦截、结构化输出。这些是"模型没得选的 规则"——如果做成工具,模型可以选择不用,保证就不存在了。
review.go:生成评审统一层(Ring 0)。借 eino ADK ShouldRetry 的洞察—— 质量否决与重试是同一个接缝——把伪调用/空头承诺/计划收口/重复调用等 守卫收敛为"一个有界评审循环 + 有序评审器列表":
尝试生成 → 依序征询 Reviewer(首个非 Accept 生效) Accept → 放行;Force → 以 Replace 收束(不再评审); Retry → Append 纠正 / Rewrite 改写输入,受全局预算与退避约束。
全局重试预算取代旧守卫链各自计数的乘法放大(2×2×2 无全局闸); 顺序从包装嵌套的隐式约定变为显式列表;新增守卫 = 写一个纯函数。 守卫是纠偏不是硬闸:预算耗尽后放行最后一次输出。 轮次终止级错误(TurnTerminal/HITL 中断)直接透传,不进评审—— 那是给框架看的信号,不是给模型看的质量问题。 设计全文见 docs/review-model-design.md。
Index ¶
- Constants
- Variables
- func BudgetModel(m model.ToolCallingChatModel) model.ToolCallingChatModel
- func CheckedFinish(m model.ToolCallingChatModel, checks ...func(context.Context) string) model.ToolCallingChatModel
- func Compactor(m model.ToolCallingChatModel, cfg CompactionConfig) engine.MessageModifier
- func ControlTools(caps []capability.Capability) []capability.Capability
- func ConversationSnapshot(ctx context.Context) []*schema.Message
- func DedupCalls(caps []capability.Capability) []capability.Capability
- func DeliverResults(caps []capability.Capability) []capability.Capability
- func DeniedCallsCheck(ctx context.Context) string
- func DigestResults(caps []capability.Capability, m model.ToolCallingChatModel, ...) []capability.Capability
- func FinishGuard(m model.ToolCallingChatModel) model.ToolCallingChatModel
- func ForkMessages(ctx context.Context, task *schema.Message) []*schema.Message
- func GateApproval(caps []capability.Capability, mode ApprovalMode) []capability.Capability
- func GateApprovalCtx(caps []capability.Capability) []capability.Capability
- func ProgressTools(caps []capability.Capability) []capability.Capability
- func ReadResult() capability.Capability
- func RecordTools(caps []capability.Capability) []capability.Capability
- func RepeatBreak(m model.ToolCallingChatModel) model.ToolCallingChatModel
- func RetryModel(m model.ToolCallingChatModel, cfg RetryConfig) model.ToolCallingChatModel
- func ReviewModel(m model.ToolCallingChatModel, rs ...Reviewer) model.ToolCallingChatModel
- func SafeCut(msgs []*schema.Message, cut int) int
- func Summarize(ctx context.Context, m model.ToolCallingChatModel, cfg CompactionConfig, ...) (string, error)
- func TimeoutTools(caps []capability.Capability, d time.Duration) []capability.Capability
- func TrajectoryMessage(records []ToolRecord, mode RecordMode) *schema.Message
- func Transient(err error) bool
- func TruncateResults(caps []capability.Capability, maxLen int) []capability.Capability
- func TurnHistory(ctx context.Context) []*schema.Message
- func WithApprovalMode(ctx context.Context, mode ApprovalMode) context.Context
- func WithApprovalState(ctx context.Context, st *ApprovalState) context.Context
- func WithBudget(ctx context.Context, g *BudgetGate) context.Context
- func WithControl(ctx context.Context, c *ControlState) context.Context
- func WithConversationSnapshot(ctx context.Context, msgs []*schema.Message) context.Context
- func WithResultStore(ctx context.Context, s *ResultStore) context.Context
- func WithToolRecorder(ctx context.Context, r *ToolRecorder) context.Context
- func WithTurnHistory(ctx context.Context, all []*schema.Message) context.Context
- type ApprovalMode
- type ApprovalPolicy
- type ApprovalRule
- type ApprovalState
- type Attempt
- type BudgetConfig
- type BudgetGate
- type CompactionConfig
- type ControlState
- type Decision
- type DecisionInteractor
- type Duration
- type ErrBudgetExhausted
- type ErrInterrupted
- type PromptLayers
- type RecordMode
- type ResultStore
- type RetryConfig
- type Reviewer
- type StructuredConfig
- type StructuredEnforcer
- type ToolRecord
- type ToolRecorder
- type Verdict
- type VerdictAction
Constants ¶
const DefaultLoopPrompt = loopPromptHead + loopPromptTodo + loopPromptTail
DefaultLoopPrompt 是完整版 L1(工具面含 todo)。
const DefaultLoopPromptNoTodo = loopPromptHead + loopPromptTail
DefaultLoopPromptNoTodo 是 L1 的裁剪变体:去掉任务管理一节,供工具面上 没有 todo 的循环使用(component 内部循环、关闭 todo 的 agent)—— 提示词不承诺工具面上不存在的工具。
const DefaultMaxToolResultLen = 8000
DefaultMaxToolResultLen 是工具结果进入上下文的默认截断长度(rune)。 MCP 等外部工具可能返回任意大的结果,不设防会直接打爆窗口。
const DefaultToolTimeout = 5 * time.Minute
DefaultToolTimeout 是工具单次调用的默认超时。MCP 等外部工具可能 无限悬挂,不设防会挂死整个循环。
const TagRawResult = capability.TagRawResult
TagRawResult 别名 core 的跨层常量(见 capability.TagRawResult); 语义:能力的结果不参与消化(结果本身就是给模型的 受控输出,如 read_result 的分页;供给方也可用它显式豁免)。
Variables ¶
var CompletionNoticeGuard = true
CompletionNoticeGuard 控制"纯完成状态"收口拦截是否生效(真机 A/B 用开关做 对照)。默认开:实测 MiniMax 在多步 + todo 任务上约 1/3 概率把最终消息答成 一句"任务已全部完成"、零实质内容——这是把内容整体替换掉,不是多说一句。
Functions ¶
func BudgetModel ¶
func BudgetModel(m model.ToolCallingChatModel) model.ToolCallingChatModel
BudgetModel 给模型套上预算控制(Ring 0):
- 硬上限:超出即返回 ErrBudgetExhausted,循环终止;
- 软阈值(80%):向输入追加收尾指令,让大脑尽快给出回答而非被硬断。
门闸从 ctx 读取(由 agent 每次运行装入),未装入时透传不设限。 预算按会话隔离,skill/component 内部调用同样计入。
func CheckedFinish ¶
func CheckedFinish(m model.ToolCallingChatModel, checks ...func(context.Context) string) model.ToolCallingChatModel
CheckedFinish 是可插拔收口检查的兼容外观:= 单评审器的 ReviewModel。 检查由装配层注入并自行节流(经 runctx.TurnState);无检查时原样返回。
func Compactor ¶
func Compactor(m model.ToolCallingChatModel, cfg CompactionConfig) engine.MessageModifier
Compactor 返回调用层压缩的 MessageRewriter:历史超过阈值时, 把较早的消息摘要为一条 system 记录,保留最近若干条。
压缩是低频的一次性事件,不是持续重写:一旦压缩,后续调用复用 缓存的(切割点, 摘要)重建视图——前缀稳定,供应商的 prompt cache 在两次压缩之间持续命中;直到视图再次超阈值才做增量归并重压。 摘要失败时保守地返回原历史(压缩是优化,不是正确性前提)。
锚定保护:视图头部除摘要外常驻本段首条用户消息原文——多次归并后 "最初的任务"不漂移。缓存按 (agent, session, 执行域) 分键,并行 调用同一 component 不互相抖动。
func ControlTools ¶
func ControlTools(caps []capability.Capability) []capability.Capability
ControlTools 给能力集套上运行控制切面。应位于审批闸门之外 (中断时连批准都不再询问)、轨迹记录之内(插话是模型看到的内容, 应入记录)。ctx 无控制态时零开销。
func ConversationSnapshot ¶
ConversationSnapshot 返回调用方对话快照,未装入时为 nil。
func DedupCalls ¶
func DedupCalls(caps []capability.Capability) []capability.Capability
DedupCalls 给能力集套上重复调用断路器。
func DeliverResults ¶
func DeliverResults(caps []capability.Capability) []capability.Capability
DeliverResults 给能力集套上交付物捕获。所有能力都过调用计数(direct 判定需要全局调用序);仅 Meta.Deliver 非空的能力做捕获。
func DeniedCallsCheck ¶
DeniedCallsCheck 是收口检查(经 CheckedFinish 注入):本轮存在被用户 拒绝的调用时,弹回一次要求终答如实区分已执行与被拒绝的操作——实测 模型会把被拒的调用也标成"已完成"(诚实性,Ring 0 兜底)。每轮最多一次。
func DigestResults ¶
func DigestResults(caps []capability.Capability, m model.ToolCallingChatModel, over, degradeKeep int) []capability.Capability
func FinishGuard ¶
func FinishGuard(m model.ToolCallingChatModel) model.ToolCallingChatModel
FinishGuard 是"收口守卫"的兼容外观:= 单评审器的 ReviewModel(预算 沿旧值 finishGuardBounces,行为与旧实现逐位一致——既有行为测试是 迁移验收线)。组合装配请直接用 ReviewModel(评审器列表 + 全局预算), 见 docs/review-model-design.md。
func ForkMessages ¶
ForkMessages 组装 fork 起始消息:请求了 fork 且快照存在时,返回 [背景标注 + 快照 + task];否则只返回 [task]。供 skill/子 agent 的 invoke 路径统一调用。
func GateApproval ¶
func GateApproval(caps []capability.Capability, mode ApprovalMode) []capability.Capability
GateApproval 给能力集套上审批闸门:Risk ≥ mutating 的能力在执行前 按 mode 处理。拒绝结果以工具返回值回传模型(而非错误),让大脑 换路径或向用户说明,循环不中断。
func GateApprovalCtx ¶
func GateApprovalCtx(caps []capability.Capability) []capability.Capability
GateApprovalCtx 同 GateApproval,但放行策略在调用时从 ctx 解析 (由 agent 经 WithApprovalMode 装入,缺省 interactive)。skill 与 component 的内部工具面用它套闸:同一能力被不同审批策略的 agent 复用时,各自的模式经 ctx 生效,内部改动操作不再因"skill 边界批准 一次"而裸奔。
func ProgressTools ¶
func ProgressTools(caps []capability.Capability) []capability.Capability
ProgressTools 给能力集套上进度发射(应用在门链最外层:事件时长 对齐"模型发起调用到结果回来"的用户体感,含审批等待)。
func ReadResult ¶
func ReadResult() capability.Capability
ReadResult 构造内置的原文取回工具:配合结果消化使用,按 id 与 offset 分页读取被消化结果的原文。启用消化的工具面应同时挂载它。
func RecordTools ¶
func RecordTools(caps []capability.Capability) []capability.Capability
RecordTools 给能力集套上轨迹记录(应为最外层包装:记录的是模型 实际看到的结果,包括内层闸门的拒绝/超时消息)。ctx 无记录器时零开销。
func RepeatBreak ¶
func RepeatBreak(m model.ToolCallingChatModel) model.ToolCallingChatModel
RepeatBreak 是重复调用模型层终止器的兼容外观:= 单评审器的 ReviewModel。组合装配请直接用 ReviewModel(见 review.go)。
func RetryModel ¶
func RetryModel(m model.ToolCallingChatModel, cfg RetryConfig) model.ToolCallingChatModel
RetryModel 给模型套上瞬时错误重试(指数退避)。只重试限流/瞬时 服务端/网络类错误;预算耗尽、参数错误等确定性失败立即返回。 应包在预算控制内侧:重试属于同一次逻辑调用,不重复计费预算次数。
func ReviewModel ¶
func ReviewModel(m model.ToolCallingChatModel, rs ...Reviewer) model.ToolCallingChatModel
ReviewModel 给模型套上评审循环(全局预算 reviewMaxRetries)。 无评审器时原样返回。
func Summarize ¶
func Summarize(ctx context.Context, m model.ToolCallingChatModel, cfg CompactionConfig, msgs []*schema.Message) (string, error)
Summarize 把一段对话与执行记录压缩为要点摘要。内容策略可经 cfg.Prompt 配置(领域自定义"保留清单"),归并指令由框架追加。 会话滚动摘要持久化(agent 包)复用此函数。
func TimeoutTools ¶
func TimeoutTools(caps []capability.Capability, d time.Duration) []capability.Capability
TimeoutTools 给能力集套上单次调用超时(Ring 0)。超时以工具结果 回传模型(而非错误),让大脑换路径推进,循环不中断;宿主 ctx 被 取消时则原样传播错误。d==0 用默认值,<0 关闭。
两类豁免:审批闸门应在本闸外侧(人工批准的等待不计入执行超时); 带 TagInteractive 的交互类能力(ask_user 等)不套闸——等人回复的 时间不是执行时间。
func TrajectoryMessage ¶
func TrajectoryMessage(records []ToolRecord, mode RecordMode) *schema.Message
TrajectoryMessage 把一轮的工具记录渲染为一条 system 消息,随会话 持久化——下一轮织入后模型知道自己做过什么、看到过什么。 无记录时返回 nil。
func TruncateResults ¶
func TruncateResults(caps []capability.Capability, maxLen int) []capability.Capability
TruncateResults 给能力集套上结果截断闸门(Ring 0):任何工具的 返回超过 maxLen 即截断并附说明,让模型知道内容不完整、可换参数 缩小范围。maxLen==0 用默认值,<0 关闭截断。
func TurnHistory ¶
TurnHistory 返回本轮的全量会话记录,未装入时为 nil。
func WithApprovalMode ¶
func WithApprovalMode(ctx context.Context, mode ApprovalMode) context.Context
WithApprovalMode 把审批模式装入 ctx,对下游 GateApprovalCtx 套闸的 能力生效。
func WithApprovalState ¶
func WithApprovalState(ctx context.Context, st *ApprovalState) context.Context
WithApprovalState 把审批运行态装入 ctx。
func WithBudget ¶
func WithBudget(ctx context.Context, g *BudgetGate) context.Context
WithBudget 把预算门闸装入 ctx,对下游所有 BudgetModel 包装的模型生效。
func WithControl ¶
func WithControl(ctx context.Context, c *ControlState) context.Context
WithControl 把会话控制装入 ctx。
func WithConversationSnapshot ¶
WithConversationSnapshot 把调用方对话快照装入 ctx(agent 每轮装入)。
func WithResultStore ¶
func WithResultStore(ctx context.Context, s *ResultStore) context.Context
WithResultStore 把结果暂存装入 ctx。
func WithToolRecorder ¶
func WithToolRecorder(ctx context.Context, r *ToolRecorder) context.Context
WithToolRecorder 把记录器装入 ctx,对下游 RecordTools 包装的能力生效。
Types ¶
type ApprovalMode ¶
type ApprovalMode string
ApprovalMode 决定改动性操作的放行策略。
const ( // ApprovalAuto 自动放行(可信环境/离线批处理)。 ApprovalAuto ApprovalMode = "auto" // ApprovalInteractive 经 runctx 的交互通道请求批准(CLI/飞书卡片)。 ApprovalInteractive ApprovalMode = "interactive" // ApprovalDeny 一律拒绝(只读部署)。 ApprovalDeny ApprovalMode = "deny" )
type ApprovalPolicy ¶
type ApprovalPolicy struct {
Remember bool `yaml:"remember"`
Rules []ApprovalRule `yaml:"rules"`
}
ApprovalPolicy 是 agent 的审批策略:规则自上而下首条命中生效, 无命中回落 ask。Remember 启用会话级决策记忆(用户选择"总是允许/ 拒绝"后,同会话内同一能力不再重复询问)。
type ApprovalRule ¶
type ApprovalRule struct {
// Ref 是 CapRef 模式(支持通配),空 = 任意能力。
Ref string `yaml:"ref"`
// Args 是参数名 → 值模式(精确、前缀 foo* 或 *),全部命中才算命中;
// 参数缺失视为不命中。空 = 不看参数。
Args map[string]string `yaml:"args"`
// Action 是命中后的动作:allow(免批放行)| ask(照常审批)| deny(直接拒绝)。
Action string `yaml:"action"`
}
ApprovalRule 是一条参数级审批规则。静态 Risk 分级回答不了"同一个 工具因参数而异的危险性"(给自己人发消息 vs 对外发消息),规则把 放行策略下沉到 (能力, 参数) 粒度。
type ApprovalState ¶
type ApprovalState struct {
Mode ApprovalMode
// contains filtered or unexported fields
}
ApprovalState 是 agent 级的审批运行态:模式 + 编译后的策略 + 决策 记忆。由 agent 在每次运行装入 ctx,对主循环与 skill 内部统一生效。
决策记忆两种模式(装配层注入,消费方不感知):kv == nil 用进程内有界 LRU(单副本默认);kv != nil 落 store.KV,"总是允许/拒绝"的决定跨副本 生效——同一会话打到另一副本不再重复询问。键按 (agent, session, 能力) 隔离。
func NewApprovalState ¶
func NewApprovalState(mode ApprovalMode, policy ApprovalPolicy, kv store.KV, ttl time.Duration) (*ApprovalState, error)
NewApprovalState 编译策略并构造运行态,规则非法时报错(fail fast)。 kv 为 nil 时决策记忆留在进程内,非 nil 落外置后端(跨副本一致)。
type Attempt ¶
type Attempt struct {
N int // 第几次尝试(1 起)
Msgs []*schema.Message // 本次实际发送的消息
Out *schema.Message // Err == nil 时有效
Err error
// contains filtered or unexported fields
}
Attempt 是一次模型生成的完整上下文,交给评审器裁决。
type BudgetConfig ¶
type BudgetConfig struct {
MaxModelCalls int `yaml:"max_model_calls" json:"max_model_calls"`
MaxTokens int `yaml:"max_tokens" json:"max_tokens"`
}
BudgetConfig 是单个会话可花费的预算上限,零值字段不限制。
type BudgetGate ¶
type BudgetGate struct {
// contains filtered or unexported fields
}
BudgetGate 是"配置 + 按会话累计"的预算门闸。它由 agent 在每次 运行时装入 ctx,BudgetModel 包装的模型从 ctx 读它扣费——因此 skill/component 内部的模型调用也计入调用方 agent 的会话预算, 不再是治理盲区。
账目后端两种模式(装配层注入,消费方不感知):
- kv == nil:进程内有界 LRU(单副本默认,零依赖);
- kv != nil:落 store.KV(redis 等),同一会话打到不同副本共用一份 账目,预算是真正的分布式硬上限。键按 (agent, session) 隔离。
func NewBudgetGate ¶
func NewBudgetGate(cfg BudgetConfig, kv store.KV, ttl time.Duration) *BudgetGate
NewBudgetGate 创建预算门闸。零值配置 = 只统计不设限;kv 为 nil 用 进程内账目,非 nil 落外置后端(跨副本一致),ttl 为账目保留时长。
type CompactionConfig ¶
type CompactionConfig struct {
// MaxMessages 触发压缩的消息条数阈值。
MaxMessages int `yaml:"max_messages" json:"max_messages"`
// MaxTokens 触发压缩的 token 阈值。优先用供应商回报的真实用量
// 校准(最近一条 assistant 的 Usage + 其后消息的估算),缺用量时
// 按字符估算。
MaxTokens int `yaml:"max_tokens" json:"max_tokens"`
// KeepRecent 压缩后保留的最近消息条数,默认 MaxMessages/2(或 10)。
KeepRecent int `yaml:"keep_recent" json:"keep_recent"`
// Prompt 覆盖摘要的内容策略(保留什么、领域侧重),字面量或
// {ref: cap://prompt...};缺省用内置。归并指令由框架无条件追加,
// 不随本字段被覆盖(增量归并是压缩算法的机制部分)。
Prompt prompt.Value `yaml:"prompt" json:"-"`
// ToolClearOver 启用旧轮工具结果清理(借 eino ADK ToolReduction 的
// Clear 阶段设计):保护窗之外的 tool 消息,内容超过该 rune 数即
// 替换为占位。比整段摘要便宜一个量级——纯字符串操作、零模型调用;
// 先清理后压缩,摘要输入也更小。0 = 关闭。已消化(digest)的结果
// 带取回指针,跳过不清。
ToolClearOver int `yaml:"tool_clear_over" json:"tool_clear_over"`
// ToolClearKeep 清理保护窗:最近 N 条消息不清,默认取 KeepRecent
// (未配压缩时默认 8)。
ToolClearKeep int `yaml:"tool_clear_keep" json:"tool_clear_keep"`
// contains filtered or unexported fields
}
CompactionConfig 控制上下文压缩,两个阈值任一超过即触发。
func (CompactionConfig) Enabled ¶
func (c CompactionConfig) Enabled() bool
Enabled 报告压缩(或工具结果清理)是否启用。
func (CompactionConfig) Keep ¶
func (c CompactionConfig) Keep() int
func (CompactionConfig) Over ¶
func (c CompactionConfig) Over(msgs []*schema.Message) bool
Over 报告消息集是否超过任一阈值。token 维度优先用真实用量校准。
func (*CompactionConfig) ResolvePrompt ¶
ResolvePrompt 在装配期解析摘要提示词引用(锁版本)。未配置时空操作。
type ControlState ¶
type ControlState struct {
// contains filtered or unexported fields
}
ControlState 是会话级的运行控制:让运行中的循环可被叫停(interrupt) 与驾驶(steer)。没有它,"停,别做了"只能排在同会话串行队列后面—— 等任务做完才被读到,为时已晚。
检查点在工具执行边界(Ring 0 的切面,不依赖引擎配合):
- 中断:下一次工具调用前生效,取消信号同时传播给运行 ctx, 终止进行中的模型调用与并行分支;
- 插话:追加到下一个工具结果尾部,模型在下一次观察时读到。
func (*ControlState) BeginTurn ¶
func (c *ControlState) BeginTurn(cancel context.CancelFunc)
BeginTurn 在一轮开始时复位中断标志并绑定本轮取消函数。 插话队列不清空:上一轮没来得及送达的插话在新一轮开头补送。
func (*ControlState) Interrupt ¶
func (c *ControlState) Interrupt()
Interrupt 叫停当前运行:置位标志并取消当前轮 ctx。
func (*ControlState) Interrupted ¶
func (c *ControlState) Interrupted() bool
Interrupted 报告当前是否处于中断状态。
type DecisionInteractor ¶
type DecisionInteractor interface {
ApproveDecision(ctx context.Context, req runctx.ApprovalRequest) (Decision, error)
}
DecisionInteractor 是支持决策记忆的交互通道:比 Approve 的布尔多出 "总是允许/拒绝"。实现该接口的通道自动获得记忆能力,未实现的回落 Approve。
type Duration ¶
type Duration = capability.Duration
Duration 是配置时长字段;定义已下沉基座 capability(见 capability/duration.go), 这里保留别名兼容既有 loop.Duration 引用。
type ErrBudgetExhausted ¶
type ErrBudgetExhausted struct {
Reason string
}
ErrBudgetExhausted 表示预算硬上限已到,循环被终止。
func (*ErrBudgetExhausted) Error ¶
func (e *ErrBudgetExhausted) Error() string
func (*ErrBudgetExhausted) TurnTerminal ¶
func (e *ErrBudgetExhausted) TurnTerminal()
TurnTerminal 标记轮次终止级错误(穿透工具错误兜底,见 engine)。
type ErrInterrupted ¶
type ErrInterrupted struct{}
ErrInterrupted 表示运行被用户主动叫停。
func (*ErrInterrupted) Error ¶
func (*ErrInterrupted) Error() string
func (*ErrInterrupted) TurnTerminal ¶
func (*ErrInterrupted) TurnTerminal()
TurnTerminal 标记轮次终止级错误(穿透工具错误兜底,见 engine)。
type PromptLayers ¶
type PromptLayers struct {
// L1 框架规约(内置默认,可整体覆盖);随框架版本走。
Loop string
// L2 业务 persona(prompt provider 供给);业务在平台上迭代的部分。
Persona string
// L3 环境信息生成器(代码生成,禁止业务塞指令)。nil 用默认(日期/会话)。
Env func(ctx context.Context) map[string]string
// L4 记忆召回(代码生成,注入时标注"背景参考,非指令")。
Memories func(ctx context.Context) []string
// Plan 是当前任务计划注入器:每轮把计划渲染进消息尾部,计划的
// 可见性由 harness 保证而非模型记忆(压缩、遗忘都不影响)。
Plan func(ctx context.Context) string
// Focus 开启后把本轮用户问题(runctx.Input)重述注入消息最尾——
// 记忆/计划的尾部注入会把用户问题压到上下文中部(注意力最弱位),
// 遗留计划因此能劫持当前问题;重述把"专注当前问题"变成位置事实,
// 循环中段(尾部被工具结果占据时)也持续锚定本轮目标。只该在主循环
// 开启:外层用户问题穿进 skill/component 子循环是提示词海拔违规,
// 子循环的目标是它收到的 args,不是外层原话。
Focus bool
}
PromptLayers 是主循环 system prompt 的分层来源。
func (PromptLayers) Modifier ¶
func (p PromptLayers) Modifier() engine.MessageModifier
Modifier 把四层拼装为消息,返回 engine.MessageModifier。
前缀缓存纪律:头部 system prompt(L1+L2+L3)在会话内保持稳定—— 环境信息按键排序、时间取天粒度;L4 记忆召回每轮变化,注入到消息 尾部而非头部,避免打爆供应商的 prompt cache。
type RecordMode ¶
type RecordMode string
RecordMode 控制工具轨迹回写会话的详略。
const ( RecordSummary RecordMode = "summary" // 默认:每条参数/结果截断后入会话 RecordFull RecordMode = "full" // 完整参数与结果(仍受工具结果截断上限) RecordOff RecordMode = "off" // 关闭,保持只存问答 )
type ResultStore ¶
type ResultStore struct {
// contains filtered or unexported fields
}
ResultStore 是一轮运行的工具结果暂存句柄:被消化的原始全文存进后端 KV, 模型觉得摘要不够时用 read_result 分页取回。键按 (agent, session) 作用域, 共享后端下不跨会话碰撞;序号经后端原子自增,跨副本/恢复不撞 id。bytes 是本句柄的软性准入计数(跨副本近似即可,只是防单轮暂存爆量的安全阀)。
func NewResultStore ¶
func NewResultStore(kv store.KV, ttl time.Duration) *ResultStore
NewResultStore 创建一轮运行的结果暂存句柄,绑定注入的后端与保留时长。 kv 为 nil 时返回 nil(该 agent 未配置结果暂存,digest 退化为纯截断)。
func (*ResultStore) List ¶
func (s *ResultStore) List(ctx context.Context) []string
List 返回本 (agent, session) 作用域下可取回的 id(按序,上限 10, 排除内部 #seq 计数键)。read_result miss 时给模型自纠线索。
func (*ResultStore) Put ¶
func (s *ResultStore) Put(ctx context.Context, toolName, text string) string
Put 存入一条原始结果,返回取回 id;超过总量软上限时返回空串。
func (*ResultStore) PutDeliver ¶
func (s *ResultStore) PutDeliver(ctx context.Context, text string) string
PutDeliver 存入一份交付物原文,返回取回 id(d<N>,后端持久序,跨轮 唯一);后端失败返回空串,由 sink 分配轮内降级 id。与 Put 共享单轮 总量软上限。
type RetryConfig ¶
type RetryConfig struct {
// MaxAttempts 是总尝试次数(含首次),0 = 默认 3。
MaxAttempts int `yaml:"max_attempts" json:"max_attempts"`
// BaseDelay 是首次退避时长,按尝试次数指数增长,0 = 默认 500ms。
BaseDelay Duration `yaml:"base_delay" json:"base_delay"`
// MaxDelay 是单次退避上限,0 = 默认 8s。
MaxDelay Duration `yaml:"max_delay" json:"max_delay"`
}
RetryConfig 控制模型调用的瞬时错误重试(Ring 0)。 零值即启用默认策略;MaxAttempts 为 1 或负数时不重试。
type Reviewer ¶
Reviewer 是一个生成质量评审器:纯函数,轮内状态经 runctx.TurnState、 自限计数经 Attempt.Tally,不持有可变字段。
func CheckedReviewer ¶
CheckedReviewer 迁移自 CheckedFinish:装配层注入的收口检查 (todo 计划收口、被拒调用诚实区分等),检查自身负责轮内节流。
func FinishReviewer ¶
func FinishReviewer() Reviewer
FinishReviewer 迁移自 FinishGuard:拦伪调用/空头承诺/叙述式执行; 自限耗尽仍不合格时 Force 打诚实标记(编造不冒充真实执行)。
func RepeatBreakReviewer ¶
func RepeatBreakReviewer() Reviewer
RepeatBreakReviewer 迁移自 RepeatBreak:模型对已拦截热点再犯时, 第 1 次以 tool 消息回填纠正弹回(协议合法),第 2 次强制收束引用 真实缓存结果作答。
type StructuredConfig ¶
type StructuredConfig struct {
Schema string `yaml:"schema" json:"schema"` // JSON Schema 文本
MaxRetries int `yaml:"max_retries" json:"max_retries"`
}
StructuredConfig 要求最终回答符合 JSON Schema(下游是程序时的刚需)。
type StructuredEnforcer ¶
type StructuredEnforcer struct {
// contains filtered or unexported fields
}
StructuredEnforcer 校验并修复模型输出:不符合 schema 时把校验错误 回喂模型重试,直到合规或重试耗尽。校验与重试由代码保证,模型只负责改。
func NewStructuredEnforcer ¶
func NewStructuredEnforcer(cfg StructuredConfig) (*StructuredEnforcer, error)
NewStructuredEnforcer 编译 schema,配置为空时返回 nil(不启用)。
func (*StructuredEnforcer) Enforce ¶
func (e *StructuredEnforcer) Enforce(ctx context.Context, m model.ToolCallingChatModel, answer string) (string, error)
Enforce 校验 answer;不合规时用 m 修复,返回合规的 JSON 文本。
type ToolRecord ¶
ToolRecord 是一次工具调用的记录(模型视角:结果是模型实际看到的, 含审批拒绝/超时等闸门消息)。
type ToolRecorder ¶
type ToolRecorder struct {
// contains filtered or unexported fields
}
ToolRecorder 收集一轮对话内主循环的工具调用,供 agent 回写会话—— 只存"user 输入 + 最终回答"会让下一轮模型不知道自己做过什么、看到 过什么,任务连续性断裂。skill 内部调用不进记录(上下文边界:对 宿主只有 skill 这一次调用与其最终结果)。
type Verdict ¶
type Verdict struct {
Action VerdictAction
// Reason 是触发计数键 + 观测 span 名(review/<reason>),必填于非 Accept。
Reason string
// Append 追加进下次尝试的消息(Retry;弹回纠正的标准形态)。
Append []*schema.Message
// Rewrite 非空时整体替换下次尝试的消息(Retry;改写输入重试,
// 如 429 裁剪/上下文超限截短)。与 Append 二选一,Rewrite 优先。
Rewrite []*schema.Message
// Replace 是 Force 的最终输出。
Replace *schema.Message
// Backoff 是重试前等待(0 = 不等)。
Backoff time.Duration
}
Verdict 是一次评审的结论。
type VerdictAction ¶
type VerdictAction int
VerdictAction 是评审结论的动作。零值 Accept:未触发即放行。
const ( Accept VerdictAction = iota // 放行 Retry // 重试(Append/Rewrite 之一,+可选 Backoff) Force // 强制收束:Replace 为最终输出,不再评审 )