返回 DeepSeek-Reasonix
todo_declarations.go
根目录 / internal / evidence / todo_declarations.go
1 package evidence
2
3 import (
4 "encoding/json"
5 "strings"
6 )
7
8 // MatchStep resolves a step citation against the existing task list.
9 func MatchStep(step string, todos []TodoItem) (TodoStepMatch, bool) {
10 m := matchTodoStep(step, todos)
11 return m, m.Found
12 }
13
14 // ReplayTodoList leaves new model states intact and reads legacy lists with
15 // their original serial normalization. Neither path rewrites stored messages.
16 func ReplayTodoList(todos []TodoItem, output string) []TodoItem {
17 var result struct {
18 Todos []struct {
19 Content string `json:"content"`
20 Status string `json:"status"`
21 } `json:"todos"`
22 }
23 if json.Unmarshal([]byte(output), &result) == nil && result.Todos != nil {
24 canonical := make([]TodoItem, len(result.Todos))
25 for i, item := range result.Todos {
26 canonical[i] = TodoItem{Content: item.Content, Status: item.Status}
27 }
28 return canonical
29 }
30 if strings.HasPrefix(output, "Model task list updated:") {
31 return append([]TodoItem(nil), todos...)
32 }
33 return NormalizeSerialTodos(todos)
34 }
35
36 const ModelCompletionDeclarationPrefix = "Model completion declaration recorded for todo "
37
38 // ReplayTodoCompletion preserves legacy serial updates while replaying new
39 // declarations exactly as they happened, without advancing an unrelated item.
40 func ReplayTodoCompletion(todos []TodoItem, index int, output string) bool {
41 if strings.HasPrefix(output, ModelCompletionDeclarationPrefix) {
42 return CompleteDeclaredTodo(todos, index)
43 }
44 return AdvanceSerialTodo(todos, index)
45 }
46
47 // CompleteDeclaredTodo updates only the selected item, without advancing others.
48 func CompleteDeclaredTodo(todos []TodoItem, index int) bool {
49 if index < 0 || index >= len(todos) || todos[index].Status == "completed" {
50 return false
51 }
52 todos[index].Status = "completed"
53 return true
54 }
55
55 lines GO