83 lines
3.3 KiB
Go
83 lines
3.3 KiB
Go
package main
|
|
|
|
import (
|
|
"slices"
|
|
"strings"
|
|
"testing"
|
|
"time"
|
|
|
|
"git.novox.be/novox/mesh-sdk/go/asks"
|
|
|
|
"github.com/novox/mesh-controller/internal/conditions"
|
|
)
|
|
|
|
func chosenWarrant() *asks.Warrant {
|
|
return &asks.Warrant{Ask: "instr-1", Asker: "claude-code", Outcome: asks.OutcomeChosen, Option: "approve",
|
|
Label: "Approve", Level: asks.Approve, Channel: "telegram", Proofs: []string{"P1"},
|
|
By: &asks.Person{Who: asks.Operator, Kind: "telegram", Identity: "42", Verified: "user id verified"},
|
|
At: time.Date(2026, 10, 10, 4, 0, 0, 0, time.UTC), AskDigest: "sha256:ab"}
|
|
}
|
|
|
|
// What is recorded of a module's act on a warrant is the router's word (novox/hq ADR 0274): who chose, how and
|
|
// with which proofs; the caller gives only what it did. Nothing is recorded without a person's choice.
|
|
func TestAWarrantIsRecordedFromTheRoutersRecordAlone(t *testing.T) {
|
|
act, err := warrantedAct("claude-code", "instr-1", "node-tools.shanks", "chosen", chosenWarrant())
|
|
if err != nil {
|
|
t.Fatal(err)
|
|
}
|
|
if act.ID != "warrant-claude-code-instr-1" || act.Verb != handActWarrant || act.Cause != conditions.CauseOperatorAnswer ||
|
|
act.By != "the operator, as telegram identity 42" || act.Ask != "instr-1" || !slices.Equal(act.Proofs, []string{"P1"}) ||
|
|
!strings.Contains(act.Why, "the operator, via telegram (user id verified), chose Approve") ||
|
|
!strings.Contains(act.RequestedBy, "node-tools.shanks") ||
|
|
!slices.Equal(act.Args, []string{"the operator chose Approve on claude-code's ask instr-1"}) {
|
|
t.Fatalf("recorded as %+v", act)
|
|
}
|
|
for name, c := range map[string]struct {
|
|
asker, ask, state string
|
|
w func() *asks.Warrant
|
|
}{
|
|
"no record": {"claude-code", "instr-1", "", func() *asks.Warrant { return nil }},
|
|
"still open": {"claude-code", "instr-1", "open", chosenWarrant},
|
|
"another asker's": {"messenger", "instr-1", "chosen", chosenWarrant},
|
|
"another ask's": {"claude-code", "instr-2", "chosen", chosenWarrant},
|
|
"the controller's": {"mesh-controller", "instr-1", "chosen", chosenWarrant},
|
|
"not a module": {"Claude Code", "instr-1", "chosen", chosenWarrant},
|
|
"expired": {"claude-code", "instr-1", "expired", func() *asks.Warrant {
|
|
w := chosenWarrant()
|
|
w.Outcome, w.By = asks.OutcomeExpired, nil
|
|
return w
|
|
}},
|
|
"no digest": {"claude-code", "instr-1", "chosen", func() *asks.Warrant {
|
|
w := chosenWarrant()
|
|
w.AskDigest = ""
|
|
return w
|
|
}},
|
|
} {
|
|
if _, err := warrantedAct(c.asker, c.ask, "x", c.state, c.w()); err == nil {
|
|
t.Errorf("%s: recorded", name)
|
|
}
|
|
}
|
|
}
|
|
|
|
func TestTheWarrantedVerbRunsTheWarrantLineWithoutAWhy(t *testing.T) {
|
|
if _, err := argvFor("warranted", map[string]any{"asker": "claude-code", "ask": "instr-1", "what": "a word of the caller's"}); err == nil {
|
|
t.Error("the caller's own words were taken into the record")
|
|
}
|
|
argv, err := argvFor("warranted", map[string]any{"asker": "claude-code", "ask": "instr-1"})
|
|
if err != nil {
|
|
t.Fatal(err)
|
|
}
|
|
if !slices.Equal(argv, []string{"hand-act", "warrant", "--asker", "claude-code", "--ask", "instr-1"}) {
|
|
t.Fatalf("%v", argv)
|
|
}
|
|
if repairingCommand(argv) != "" {
|
|
t.Error("recording a person's answer is taken for a repair")
|
|
}
|
|
if terminalOnly(argv) != nil {
|
|
t.Error("the verb is kept for the terminal")
|
|
}
|
|
if _, err := argvFor("warranted", map[string]any{"asker": "claude-code"}); err == nil {
|
|
t.Error("a call naming no ask was taken")
|
|
}
|
|
}
|