This repository has been archived on 2026-11-02. You can view files and clone it. You cannot open issues or pull requests or push a commit.
Files
mesh-controller/internal/catalogue/uplink_verbs_test.go
T
jochen 3e9a38f81b
mesh/merge-gate pass: builds build-agent, mesh-controller, route-proxy → ace, g14, novox, shanks; no bus step; every machine composes with the change as it…
mesh/repo-check pass: its merge-check.sh passed
mesh/delivery-group group feat/node-uplink-verbs ready: every member ready, and composed together they pass
mesh/delivery superseded: a newer head of the same pull request
Mark the uplink seat's verbs optional, the one mechanism, and keep every optional verb out of the seat row
Staged duplicated Verb.Optional. Optional, though, was still seeded into the row,
where the mark is not kept: read back, the delivery seat's checks verb and these
would be required of every holder, and an older controller would require them
too. Stored leaves optional verbs out, and the working set takes them from the
compiled seat, still optional.
2026-10-07 20:18:05 +02:00

94 lines
3.3 KiB
Go

package catalogue
import (
"slices"
"strings"
"testing"
)
// The node-uplink seat's verbs (novox/hq ADR 0241): promised and routed, optional — not yet a condition of
// holding — so the holders of today still hold it, a holder may name them, and nothing it does not promise.
// And an optional verb is never stored in the seat's row (Verb.Optional): a controller that reads the row
// back must still find it optional, and one older than the verb must not find it at all.
func uplinkSeat(t *testing.T) Seat {
t.Helper()
for _, s := range DefaultSeats() {
if s.Name == "node-uplink" {
return s
}
}
t.Fatal("no node-uplink seat")
return Seat{}
}
func TestTheUplinkSeatPromisesItsVerbsAndRequiresNoneYet(t *testing.T) {
seat := uplinkSeat(t)
var names []string
for _, v := range seat.Serves {
names = append(names, v.Name)
if !v.Optional {
t.Errorf("%s is required already", v.Name)
}
}
if !slices.Equal(names, []string{"resolvers", "links"}) {
t.Fatalf("node-uplink promises %v", names)
}
today := Manifest{Module: "networkmanager", Version: "1", Claims: []Claim{{Name: "node-uplink", Scope: ScopeNode}}}
if err := CanHold(today, seat); err != nil {
t.Fatalf("a holder that serves no verb yet is refused: %v", err)
}
serving := today
serving.Claims = []Claim{{Name: "node-uplink", Scope: ScopeNode, Serves: []string{"resolvers", "links"}}}
if err := CanHold(serving, seat); err != nil {
t.Fatalf("a holder serving both is refused: %v", err)
}
typo := today
typo.Claims = []Claim{{Name: "node-uplink", Scope: ScopeNode, Serves: []string{"resolver"}}}
if err := CanHold(typo, seat); err == nil || !strings.Contains(err.Error(), "does not promise") {
t.Fatalf("a verb the seat does not promise was accepted: %v", err)
}
}
func TestAnOptionalVerbIsNeverStoredAndComesBackOptionalFromTheBinary(t *testing.T) {
seat := uplinkSeat(t)
if stored := seat.Stored(); len(stored.Serves) != 0 {
t.Fatalf("the row would keep %v", stored.Serves)
}
before := seats
t.Cleanup(func() { seats = before })
optionalBoth := func(want int) {
t.Helper()
for _, s := range Seats() {
if s.Name != "node-uplink" {
continue
}
if len(s.Serves) != want {
t.Fatalf("the working set's node-uplink serves %+v", s.Serves)
}
holder := Manifest{Module: "networkmanager", Version: "1", Claims: []Claim{{Name: "node-uplink", Scope: ScopeNode}}}
for _, v := range s.Serves {
if v.Name != "operators-own" {
if !v.Optional {
t.Fatalf("%s came back required", v.Name)
}
} else {
holder.Claims[0].Serves = []string{"operators-own"}
}
}
if err := CanHold(holder, s); err != nil {
t.Fatalf("a holder serving none of the optional verbs is refused: %v", err)
}
}
}
// A row as the store keeps it: no protocol of its own.
UseSeats([]Seat{{Name: "node-uplink", Scope: ScopeNode}, {Name: "node-service-manager", Scope: ScopeNode}})
optionalBoth(2)
// A row with a verb an operator added: it keeps it and gains the optional ones.
UseSeats([]Seat{{Name: "node-uplink", Scope: ScopeNode, Serves: []Verb{{Name: "operators-own"}}}})
optionalBoth(3)
// A row that stored the verb before it was marked (or by an older seeding): read back, still optional.
UseSeats([]Seat{{Name: "node-uplink", Scope: ScopeNode, Serves: []Verb{{Name: "resolvers"}, {Name: "links"}}}})
optionalBoth(2)
}