diff --git a/internal/assembly/boot/effect_setting_tool_test.go b/internal/assembly/boot/effect_setting_tool_test.go index 6fdaa29c66..8f1dc8e5d7 100644 --- a/internal/assembly/boot/effect_setting_tool_test.go +++ b/internal/assembly/boot/effect_setting_tool_test.go @@ -172,7 +172,7 @@ func TestEffectTheModelCannotProposeAGuardedSetting(t *testing.T) { default: } result := rec.toolResult() - for _, want := range []string{"setting.guarded", "(fix: setting op=open id=permissions.mode)"} { + for _, want := range []string{"setting.guarded", "(fix: tool:setting op=open id=permissions.mode)"} { if !strings.Contains(result, want) { t.Fatalf("tool result = %q, want %q", result, want) } diff --git a/internal/assembly/boot/persona_setting_tool_effect_test.go b/internal/assembly/boot/persona_setting_tool_effect_test.go index 867ac9b321..bde5f7ac8a 100644 --- a/internal/assembly/boot/persona_setting_tool_effect_test.go +++ b/internal/assembly/boot/persona_setting_tool_effect_test.go @@ -32,7 +32,7 @@ func TestEffectSettingToolCannotChangeOrDiscloseUserPersona(t *testing.T) { default: } result := rec.toolResult() - for _, want := range []string{"setting.guarded", "(fix: setting op=open id=" + tc.id + ")"} { + for _, want := range []string{"setting.guarded", "(fix: tool:setting op=open id=" + tc.id + ")"} { if !strings.Contains(result, want) { t.Fatalf("tool result = %q, want %q", result, want) } diff --git a/internal/contract/tool/refusal_test.go b/internal/contract/tool/refusal_test.go index 5c1e427a59..e464d9afa5 100644 --- a/internal/contract/tool/refusal_test.go +++ b/internal/contract/tool/refusal_test.go @@ -7,7 +7,7 @@ import ( func TestARefusalRendersTheSettingThatWouldLiftIt(t *testing.T) { r := Refusal{Code: "peer.disabled", Message: "Messages between sessions are off.", Remedy: &Remedy{Op: RemedyPropose, Setting: "peers.enabled", Value: json.RawMessage(`true`)}} - want := "Messages between sessions are off. (refusal: peer.disabled) (fix: setting op=propose id=peers.enabled value=true)" + want := "Messages between sessions are off. (refusal: peer.disabled) (fix: tool:setting op=propose id=peers.enabled value=true)" if got := r.String(); got != want { t.Fatalf("got %q, want %q", got, want) } @@ -15,7 +15,7 @@ func TestARefusalRendersTheSettingThatWouldLiftIt(t *testing.T) { func TestARemedyThatOnlyOpensCarriesNoValue(t *testing.T) { r := Refusal{Code: "x.y", Remedy: &Remedy{Op: RemedyOpen, Setting: "permissions.mode", Value: json.RawMessage(`"yolo"`)}} - if got, want := r.String(), "(refusal: x.y) (fix: setting op=open id=permissions.mode)"; got != want { + if got, want := r.String(), "(refusal: x.y) (fix: tool:setting op=open id=permissions.mode)"; got != want { t.Fatalf("got %q, want %q", got, want) } } diff --git a/internal/contract/tool/setting.go b/internal/contract/tool/setting.go index c70557d863..c85d94f89b 100644 --- a/internal/contract/tool/setting.go +++ b/internal/contract/tool/setting.go @@ -25,9 +25,9 @@ const ( func (r Remedy) String() string { if r.Op == RemedyPropose && len(r.Value) > 0 { - return fmt.Sprintf("setting op=%s id=%s value=%s", r.Op, r.Setting, r.Value) + return fmt.Sprintf("tool:setting op=%s id=%s value=%s", r.Op, r.Setting, r.Value) } - return fmt.Sprintf("setting op=%s id=%s", r.Op, r.Setting) + return fmt.Sprintf("tool:setting op=%s id=%s", r.Op, r.Setting) } // SettingInfo is one row of what the model may learn about a setting. diff --git a/internal/tools/builtin/setting.go b/internal/tools/builtin/setting.go index 50174f8511..b261fdd4b6 100644 --- a/internal/tools/builtin/setting.go +++ b/internal/tools/builtin/setting.go @@ -19,7 +19,7 @@ type settingTool struct{ link *tool.SettingsLink } func (*settingTool) Name() string { return "setting" } func (*settingTool) Description() string { - return "Find and change the user's own settings. op=list finds settings by words of their id (for example \"peers dispatch\"). op=propose asks the user to confirm one change: give the id, the new value and a short reason; nothing changes until the user answers, and the result says what changed or that they declined. op=open points the user at a setting that only they may change. Use it when a refusal ends with (fix: setting ...), or when a tool you need is not offered because a switch is off. Do not change a setting the task did not call for." + return "Find and change the user's own settings. op=list finds settings by words of their id (for example \"peers dispatch\"). op=propose asks the user to confirm one change: give the id, the new value and a short reason; nothing changes until the user answers, and the result says what changed or that they declined. op=open points the user at a setting that only they may change. Use it when a refusal ends with (fix: tool:setting ...), or when a tool you need is not offered because a switch is off. Do not change a setting the task did not call for." } func (*settingTool) Schema() json.RawMessage { return json.RawMessage(`{"type":"object","properties":{"op":{"type":"string","enum":["list","propose","open"]},"query":{"type":"string","description":"Words of the setting's id, for op=list"},"id":{"type":"string","description":"The setting's id, for propose and open"},"value":{"description":"The new value as JSON, for op=propose"},"reason":{"type":"string","description":"Why the change helps the user, shown on the card, for op=propose"}},"required":["op"],"additionalProperties":false}`)