78 lines
5.2 KiB
Markdown
78 lines
5.2 KiB
Markdown
## Context
|
||
|
||
ISS-014 是一次 L4 Chat 重构的总设计来源,但实施被拆成 11 个必须串行归档的 OpenSpec changes。阶段 0 不切换公开协议或 Agent 运行链,只创建后续阶段复用的类型化契约、安全前置、失败语义和 focused baseline。
|
||
|
||
现有代码已经具备 `runId` Trace、工具调用审计、no-evidence 精确引用、Verifier/Composer fallback 和模块化 RAG,但这些能力分散在 `ChatService`、Hook、ThreadLocal、Tool 和 JSON 字符串中。Spring AI Alibaba 已提供 `ToolInterceptor`、结构化输出类型、工具执行超时、调用限额 Hook 和 `ReactAgent.interrupt`;Spring AI 底层 retry 默认最多 10 次,不能直接满足 ISS-014 的显式 Harness 重试矩阵。
|
||
|
||
## Goals / Non-Goals
|
||
|
||
**Goals:**
|
||
|
||
- 生成后续阶段可直接复用的 Java contract types 和枚举,不实现新 Agent 执行链。
|
||
- 冻结 Tool ID、双状态、Draft、Knowledge Answer、Fallback、previous turn、SSE、重试和取消语义。
|
||
- 冻结 MySQL fail-closed 允许子集和安全前置。
|
||
- 移除仓库脚本和主配置中的明文凭据并建立改造前 focused baseline。
|
||
- 保证 ISS-014、OpenSpec、devflow 术语和 11 个阶段门禁一致。
|
||
|
||
**Non-Goals:**
|
||
|
||
- 不接入 Harness、Diagnosis Agent、EvidenceGuard 或 SemanticGuard 运行时。
|
||
- 不修改 Controller 协议、旧 ChatService 行为、Redis invocation store 或数据库表。
|
||
- 不实现 RAG/日志/MySQL Tool 投影。
|
||
- 不运行完整 live E2E。
|
||
|
||
## Decisions
|
||
|
||
### Contract types are reusable runtime inputs
|
||
|
||
阶段 0 创建位于 `com.superbiz.agent.harness.contract` 的轻量 record/enum,而不是只写文档或引入 JSON Schema 引擎。后续 ReactAgent `outputType`、Harness validator、持久化和 SSE DTO 可以直接复用这些类型,减少同一字段在多个阶段重复定义。
|
||
|
||
### Framework Tool Call ID is canonical
|
||
|
||
`tool_call_id` 使用框架协议 ID。Harness 后续只校验非空、长度/字符安全和 Run 内唯一性,不生成第二套 ID。Redis Key 仍按 `runId + toolCallId` 隔离,真实性来自当前 Run 的 canonical record,而不是 ID 本身。
|
||
|
||
### Invocation lifecycle and evidence outcome are orthogonal
|
||
|
||
`InvocationStatus=PROJECTING/READY/ERROR` 只描述调用与投影生命周期;`EvidenceStatus=EVIDENCE_FOUND/NO_EVIDENCE/ERROR` 描述结果语义。`NO_EVIDENCE` 只允许绑定 `AnalysisKind=NEGATIVE_OBSERVATION`,并必须保留查询范围和零匹配信息。
|
||
|
||
### Diagnosis and knowledge answer contracts stay separate
|
||
|
||
Diagnosis Draft 使用 Analysis ID 与 Tool Call IDs;KNOWLEDGE_QUERY 使用 answer items,每项绑定一次 lookup 的 Tool Call ID 和返回的 document IDs。Harness 后续验证精确成员关系并确定性展开引用。首版 KNOWLEDGE_QUERY 不进入 SemanticGuard。
|
||
|
||
### Safe published context belongs to Diagnosis Run
|
||
|
||
`diagnosis_run` 是 `intent/release_outcome/published_result` 的持久化真理源。只有同 Session 最近一个 `DIAGNOSIS + SUCCESS` 且 published result 非空的 Run 可形成 previous turn。Published result 只含用户查询、已发布结论、范围、限制和 RAG 文档元数据。
|
||
|
||
### Cancellation is observable and layered
|
||
|
||
取消请求立即阻止新模型/Tool 轮次和最终 Draft 释放;框架中断、可控 Future/JDBC 取消尽力执行;已进入同步 `ChatModel.call` 的请求依靠底层 HTTP timeout。Run 终态通过原子状态转换保证唯一,晚到结果被丢弃,不宣称无法证明的底层硬取消。
|
||
|
||
### Harness owns all retries
|
||
|
||
底层 SDK/HTTP/数据库 retry 必须关闭或压为一次 attempt。Intent Router 和 SemanticGuard 的第二次 attempt 由 Harness 显式执行并审计。阶段 0 只冻结矩阵;阶段 2 实现执行器和配置。
|
||
|
||
### Stage boundaries are release boundaries
|
||
|
||
阶段 4 和 6A 仅内部运行;阶段 6B 在 Guards 已完成后原子切换公开入口。每个 change 必须 Archive 并 Git commit 后才能进入下一项,阶段 7 才执行统一 live E2E。
|
||
|
||
## Risks / Trade-offs
|
||
|
||
- [Risk] Contract records过早绑定实现细节 → Mitigation:只包含跨阶段稳定字段,不包含 Redis、JPA 或框架对象。
|
||
- [Risk] Spring AI provider 对 Tool Call ID 行为不同 → Mitigation:阶段 3A 使用 Fake Model 和当前 DeepSeek 路径验证,缺失或重复时 fail closed。
|
||
- [Risk] 同步模型调用不能立即取消 → Mitigation:明确 layered semantics、HTTP timeout 和晚到结果丢弃,不把状态更新等同底层资源已终止。
|
||
- [Risk] 设计冻结测试增加维护成本 → Mitigation:只保留 focused serialization/validation tests,不复制完整 E2E。
|
||
- [Risk] 明文凭据可能已泄露 → Mitigation:仓库中移除并要求外部轮换;轮换证据记录在 acceptance。
|
||
|
||
## Migration Plan
|
||
|
||
1. 创建 contract types、契约测试和阶段台账,不接运行链。
|
||
2. 清理查询脚本凭据,改为环境变量注入。
|
||
3. 记录 focused baseline;Archive 本 change。
|
||
4. 后续 10 个 change 逐步实现,并在各自 Archive 时同步对应运行 capability specs。
|
||
|
||
Rollback:阶段 0 没有公开行为变化;可删除新增 contract package/tests 并恢复文档。已经轮换的凭据不得回滚为旧值。
|
||
|
||
## Open Questions
|
||
|
||
无。所有影响实现的用户决策已经在 `decisions.md` 中确认。
|