package broker import ( "slices" "testing" "git.novox.be/novox/mesh-sdk/go/announce" ) // D3 (ADR 0495 clause 3, ADR 0513 §3; issue 1790): a reader's `reads` is granted where the owner announced the state // readable, refused where it announced and did not, and granted as before where the owner announced nothing yet. func TestAReadIsGrantedFromItsOwnersAnnouncement(t *testing.T) { announced := map[string]announce.States{ "owner": {Module: "owner", States: []announce.State{{Name: "open", Readable: true}, {Name: "closed"}}}, } granted, refused := ReadsAnnounced([]string{"owner.open", "owner.closed", "owner.unsaid", "quiet.any"}, announced) if !slices.Equal(granted, []string{"owner.open", "quiet.any"}) || !slices.Equal(refused, []string{"owner.closed", "owner.unsaid"}) { t.Fatalf("granted %v, refused %v", granted, refused) } r := Records{Announced: announced, Assigned: map[string][]Declared{"one": {{Module: "reader", Reads: granted, ReadsRefused: refused}}}} if got := NotAnnounced(r); !slices.Equal(got, []string{"quiet"}) { t.Fatalf("not yet announced: %v", got) } } // D1 (ADR 0495 clause 2): the controller announces every bucket of its own, and readable exactly the record mirrors (the // declared packages the pacman module reads among them, ADR 0507 §5), the chain's buckets, the checks running and the // plans building. func TestTheControllerAnnouncesWhatItKeeps(t *testing.T) { s := ControllerAnnouncement("novox") if _, err := announce.Encode(s); err != nil { t.Fatal(err) } var readable []string for _, k := range s.States { if k.Readable { readable = append(readable, k.Name) } } want := []string{ChainBuilds, ChecksRunning, MirrorDeclaredConfig, PlansBuilding, MirrorPredefined, ChainRollouts, MirrorAssignments, MirrorDeclaredPackages} slices.Sort(want) if !slices.Equal(readable, want) { t.Fatalf("readable %v, want %v", readable, want) } for _, name := range []string{"lease", "calls", "states-announced", "merge-window"} { if !s.Keeps(name) || s.Readable(name) { t.Errorf("%s: kept %v, readable %v", name, s.Keeps(name), s.Readable(name)) } } perms, err := PermissionsFor(Principal{Kind: KindController}) if err != nil { t.Fatal(err) } if !slices.Contains(perms.Publish, announce.Subject(ControllerSeat)) { t.Fatal("the controller may not say what it keeps") } } // D2: every account that keeps state may say so on its own subject, a process account included, and no other's. func TestAnAccountKeepingStateMaySayWhatItKeeps(t *testing.T) { keeper, err := PermissionsFor(Principal{Kind: KindModule, Node: "one", Module: "keeper", PasswordHash: "x", State: []string{"things"}}) if err != nil { t.Fatal(err) } if !slices.Contains(keeper.Publish, announce.Subject("keeper")) || slices.Contains(keeper.Publish, announce.Subject("other")) { t.Fatalf("the keeper's announcement grants: %v", keeper.Publish) } process, err := PermissionsFor(Principal{Kind: KindProcess, Node: "one", Module: "keeper", Process: "send", PasswordHash: "x", State: []string{"sends"}}) if err != nil { t.Fatal(err) } if !slices.Contains(process.Publish, announce.Subject("keeper")) { t.Fatal("a process keeping state may not say what it keeps") } none, err := PermissionsFor(Principal{Kind: KindModule, Node: "one", Module: "stateless", PasswordHash: "x"}) if err != nil { t.Fatal(err) } if slices.Contains(none.Publish, announce.Subject("stateless")) { t.Fatal("a module keeping nothing may say it keeps something") } }