返回 DeepSeek-Reasonix
execution_projection.go
根目录 / internal / session / execution_projection.go
1 package session
2
3 import "reasonix/internal/provider"
4
5 // rejectedToolResult contains only host-recorded identities and state, never
6 // tool bodies or model-authored claims about whether a call executed.
7 type rejectedToolResult struct {
8 ToolCallID string `json:"toolCallId"`
9 Name string `json:"name"`
10 State provider.ToolRunState `json:"state"`
11 }
12
13 func noteRejectedToolResult(p *Projection, m provider.Message) {
14 if m.ID == "" {
15 return
16 }
17 // Upserts replace authority as well as content: a later executed/unknown
18 // result must not inherit an earlier refusal for the same message identity.
19 delete(p.RejectedToolResults, m.ID)
20 if m.LocalOnly || m.Role != provider.RoleTool || m.ToolCallID == "" || m.Name == "" {
21 return
22 }
23 if m.ToolRunState != provider.ToolRunNotStarted && m.ToolRunState != provider.ToolRunCancelled {
24 return
25 }
26 if p.RejectedToolResults == nil {
27 p.RejectedToolResults = make(map[string]rejectedToolResult)
28 }
29 p.RejectedToolResults[m.ID] = rejectedToolResult{ToolCallID: m.ToolCallID, Name: m.Name, State: m.ToolRunState}
30 }
31
32 // restoreRejectedToolResults operates on a detached execution snapshot. The
33 // executor needs this proof for RepairRejectedArguments before ModelMessages
34 // removes local metadata at the outbound provider boundary. Canonical arguments
35 // and the stored wire projection stay unchanged.
36 func restoreRejectedToolResults(p *Projection) {
37 if len(p.RejectedToolResults) == 0 {
38 return
39 }
40 for i := range p.ModelMessages {
41 m := &p.ModelMessages[i]
42 if m.LocalOnly || m.Role != provider.RoleTool || m.ToolRunState != "" {
43 continue
44 }
45 evidence, ok := p.RejectedToolResults[m.ID]
46 if !ok || evidence.ToolCallID != m.ToolCallID || evidence.Name != m.Name {
47 continue
48 }
49 if evidence.State == provider.ToolRunNotStarted || evidence.State == provider.ToolRunCancelled {
50 m.ToolRunState = evidence.State
51 }
52 }
53 }
54
54 lines GO