mesh-grants: prove the haves fallback lets the indexer serve the seat list's verb
Issue 1966: the seat list is read through mesh-catalog's seat-definitions, which got no responders only because nothing was placed. A row shows that, the assignments view unanswered, the indexer placed by its have (its real manifest) is composed to hear mesh.seat.mesh-catalog.* and its membership serving seat-definitions is published, while the seat list stays unread and other modules still wait for it. Claude-Session: https://claude.ai/code/session_01NcbgfFfQ4Z9UE5jK32PmE5
This commit is contained in:
@@ -2542,6 +2542,42 @@ func TestGrants(t *testing.T) {
|
||||
if !strings.Contains(refused, "manifest of mod-x: it waits for the seat list") {
|
||||
t.Errorf("another module is not held: %v", p.Last().Refused)
|
||||
}
|
||||
|
||||
// Issue 1966: the assignments view unanswered, the indexer placed by its have alone (its real manifest, claiming
|
||||
// mesh-catalog and serving seat-definitions) is composed to serve the seat's verbs, in the list and its membership,
|
||||
// while the seat list stays unread: the bootstrap reaches the verb that reads the list without opening the gate.
|
||||
indexer, err := os.ReadFile("../mesh-delivery-indexer/module.json")
|
||||
if err != nil {
|
||||
t.Fatal(err)
|
||||
}
|
||||
fb := fixture()
|
||||
fb.refused[grants.ReadAssignments] = true
|
||||
fb.manifestOf("mesh-delivery-indexer", string(indexer))
|
||||
fb.put(grants.ReadHave, "novox.node", map[string]any{"v": 1})
|
||||
fb.put(grants.ReadHave, "novox.mesh-delivery-indexer", nodeengine.HaveByNodeModuleValue{V: keys.Version, Phase: nodeengineclient.PhaseRunning, Health: nodeengineclient.HealthOK})
|
||||
gate := &seatGate{}
|
||||
fp := partOn(fb)
|
||||
fp.SeatList = gate
|
||||
res := fp.Compose()
|
||||
if strings.Contains(strings.Join(res.Refused, "\n"), "manifest of mesh-delivery-indexer:") {
|
||||
t.Fatalf("the indexer is held in a pass placed by the haves: %v", res.Refused)
|
||||
}
|
||||
listRecs, _ := grants.ListRecords(grants.ReadInputs(fb, &grants.Manifests{}))
|
||||
users, err := grants.ComposeUsers(listRecs)
|
||||
if err != nil {
|
||||
t.Fatal(err)
|
||||
}
|
||||
at := slices.IndexFunc(users, func(u grants.User) bool { return u.User == "novox.mesh-delivery-indexer" })
|
||||
if at < 0 || !slices.ContainsFunc(users[at].Subscribe, func(s string) bool { return strings.HasPrefix(s, "mesh.seat.mesh-catalog.") }) {
|
||||
t.Fatalf("novox.mesh-delivery-indexer is not composed to hear the seat's verbs: %+v", users)
|
||||
}
|
||||
raw := fb.own[grants.StateMemberships]["novox.mesh-delivery-indexer"]
|
||||
if !slices.Contains(res.Published, "novox.mesh-delivery-indexer") || !strings.Contains(string(raw), "seat-definitions") {
|
||||
t.Errorf("the indexer's membership serving seat-definitions was not published: %v, %s", res.Published, raw)
|
||||
}
|
||||
if !strings.Contains(strings.Join(res.Refused, "\n"), "manifest of mod-x: it waits for the seat list") {
|
||||
t.Errorf("the seat list was opened by a pass placed by the haves: %v", res.Refused)
|
||||
}
|
||||
})
|
||||
|
||||
// DLV-G1, 1966/AC32-AC33 (novox/hq ADR 0595 §1, §7; design 25 § 12.2): the bus module's created writes the binding into
|
||||
|
||||
Reference in New Issue
Block a user