Grant a bar's holder the state a contributor's item shows, at its own machine's key (issue 774)

i3status-rust on g14 and shanks was issued nothing to read ("was issued: none", 148 times): ReadsGranted derived a
holder's reads from contributions' data alone, and design 57 L3 moved power's draw block to an item
(mesh-catalog ca8d6f33: shows: state, state: power.draw). ReadsGranted now reads a module's items of a kind the
holder's seat receives too, their attributes in a contribution's data shape, always at the machine's own key
(ADR 0260), never another's. Both callers, the controller's busrecords and mesh-grants' records.go, get it
through ReadsGranted with no change of their own.
This commit is contained in:
2026-10-30 18:35:54 +01:00
parent ef1ec1c935
commit 206f794eb3
2 changed files with 39 additions and 1 deletions
+29 -1
View File
@@ -155,7 +155,9 @@ var stateKeyName = regexp.MustCompile(`^[a-z0-9][a-z0-9-]*$`)
// ReadsGranted is the state a holder reads because modules on its machine offer it in pieces of a
// kind its seat receives as data (novox/hq ADR 0260), each with the one key the piece shows — the
// machine's own when it names none — sorted and once each. The bus grants the holder these keys and
// machine's own when it names none — sorted and once each. A module's items of such a kind (design 57 L3) grant
// what they show too, always at the machine's own key; an item whose capability the machine lacks grants a key
// that is never written, which is no wider than its own machine's. The bus grants the holder these keys and
// no others: the holder names no contributor, and reads only what is offered to it where it runs.
func ReadsGranted(holder Manifest, onMachine []Manifest, machine string) []StateRead {
seen := map[StateRead]bool{}
@@ -183,6 +185,21 @@ func ReadsGranted(holder Manifest, onMachine []Manifest, machine string) []State
}
}
}
// A moved contributor's items of the kind (design 57 L3): what each shows, read from its attributes as a
// contribution's data, and always this machine's own key (ADR 0260), never another's (issue 774:
// power's draw block became an item and i3status-rust was issued nothing).
for _, it := range m.Items {
if it.Collection != "contribution:"+s.Name+":"+r.Kind {
continue
}
for _, sr := range r.Shape.Reads(itemData(it)) {
sr.Key = machine
if module, _, err := ReadState(sr.Read); err == nil && module == m.Module && module != holder.Module &&
stateKeyName.MatchString(sr.Key) {
seen[sr] = true
}
}
}
}
}
}
@@ -199,6 +216,17 @@ func ReadsGranted(holder Manifest, onMachine []Manifest, machine string) []State
return out
}
// itemData is an item's attributes in the shape of a contribution's data: each at the top and among the options, where
// a shape's Reads looks for what a piece shows (barBlockReads: shows, options.state).
func itemData(it Item) map[string]any {
data, options := map[string]any{}, map[string]any{}
for k, v := range it.Attributes {
data[k], options[k] = v, v
}
data["options"] = options
return data
}
// wholeIn is v as a whole number within [lo, hi]; JSON gives every number as a float.
func wholeIn(v any, lo, hi int) (int, bool) {
f, ok := v.(float64)
+10
View File
@@ -394,6 +394,16 @@ func TestAStateBlockIsRenderedForThisMachineAndTheHolderIsGrantedToReadIt(t *tes
if got := ReadsGranted(barHolder(), []Manifest{barHolder()}, "laptop"); len(got) != 0 {
t.Fatalf("a holder alone is granted %v", got)
}
// Issue 774 (design 57 L3): the block as an item grants the same read, at this machine's own key alone, even where
// the item names another machine's.
for _, attrs := range []map[string]string{{"shows": "state", "state": "power.draw"}, {"shows": "state", "state": "power.draw", "key": "other"}} {
moved := Manifest{Module: "power", State: []StateDeclaration{{Name: "draw"}}, Items: []Item{{
Collection: "contribution:node-bar:block", Name: "power-draw", IfCapability: "power-meter", Attributes: attrs}}}
if got := ReadsGranted(barHolder(), []Manifest{barHolder(), moved}, "laptop"); len(got) != 1 ||
got[0] != (StateRead{Read: "power.draw", Key: "laptop"}) {
t.Errorf("the holder is granted %v by the item %v", got, attrs)
}
}
}
func TestAModuleOffersItsOwnStateOnly(t *testing.T) {