| 1 | package provider |
| 2 | |
| 3 | import ( |
| 4 | "encoding/json" |
| 5 | "reflect" |
| 6 | "strings" |
| 7 | "testing" |
| 8 | ) |
| 9 | |
| 10 | func TestPresentedFilesStayInProjectionButNeverEnterProviderBytes(t *testing.T) { |
| 11 | base := []Message{{Role: RoleTool, Name: "present", ToolCallID: "call-present", Content: "Presented game.html"}} |
| 12 | stored := append([]Message(nil), base...) |
| 13 | stored[0].PresentedFiles = NewPresentedFilesMetadata([]PresentedFile{{Path: "game.html", Description: "Game"}}) |
| 14 | persisted, err := json.Marshal(stored[0]) |
| 15 | if err != nil { |
| 16 | t.Fatal(err) |
| 17 | } |
| 18 | if !strings.Contains(string(persisted), `"presented_files":{"version":1,"files":[`) { |
| 19 | t.Fatalf("presented files are not in the versioned metadata envelope: %s", persisted) |
| 20 | } |
| 21 | |
| 22 | projection := ProjectionMessages(stored) |
| 23 | if !reflect.DeepEqual(projection[0].PresentedFiles, stored[0].PresentedFiles) { |
| 24 | t.Fatalf("ProjectionMessages dropped presented files: %+v", projection[0]) |
| 25 | } |
| 26 | want, err := json.Marshal(ModelMessages(base)) |
| 27 | if err != nil { |
| 28 | t.Fatal(err) |
| 29 | } |
| 30 | got, err := json.Marshal(ModelMessages(stored)) |
| 31 | if err != nil { |
| 32 | t.Fatal(err) |
| 33 | } |
| 34 | if string(got) != string(want) { |
| 35 | t.Fatalf("presented file metadata changed provider bytes\n got: %s\nwant: %s", got, want) |
| 36 | } |
| 37 | if stored[0].PresentedFiles == nil || len(stored[0].PresentedFiles.Files) != 1 { |
| 38 | t.Fatal("projection mutated the stored transcript") |
| 39 | } |
| 40 | } |
| 41 | |
| 42 | func TestUnknownPresentedFilesMetadataVersionFailsClosed(t *testing.T) { |
| 43 | var message Message |
| 44 | if err := json.Unmarshal([]byte(`{"role":"tool","presented_files":{"version":2,"files":[{"path":"future.bin"}]}}`), &message); err != nil { |
| 45 | t.Fatal(err) |
| 46 | } |
| 47 | if files := PresentedFileList(message.PresentedFiles); len(files) != 0 { |
| 48 | t.Fatalf("future metadata version was treated as trusted: %#v", files) |
| 49 | } |
| 50 | } |
| 51 |