node-engine.composition shows the node's own fields and what the last pass held (issue 774)

Reading ace's node composition gave four resources twice and no way to see that one revision named no provisioner
client's account. The verb now shows, for module node, the revision's provisioner account beside what runs names, its
adoption, how many identities, groups and libraries it names, and each module the composer's last pass held with why.

Claude-Session: https://claude.ai/code/session_01JG73KG7AfSdh6FP8VrBqCn
This commit is contained in:
2026-11-04 01:50:21 +01:00
parent f7abd05981
commit f7129fdb41
5 changed files with 60 additions and 0 deletions
+32
View File
@@ -6,6 +6,7 @@ import (
"fmt"
"git.novox.be/novox/mesh-sdk/go/catalogue"
"git.novox.be/novox/mesh-sdk/go/declaration"
"git.novox.be/novox/mesh-sdk/go/delivery"
"github.com/novox/mesh-host/internal/judge"
)
@@ -32,6 +33,26 @@ type CompositionView struct {
Judged JudgedView `json:"judged"`
// Diff is every resource that differs from what runs, when asked.
Diff []judge.ResourceChange `json:"diff,omitempty"`
// Own is, of the node's own composition (module node), its own fields beside what runs names (issue 774: ace's
// own composition dropped the provisioner client's account, and nothing read could show it).
Own *OwnView `json:"own,omitempty"`
}
// OwnView is the node's own fields of a composition (delivery.NodeOwn) beside what runs of them, and what the node's
// composer held in its last pass.
type OwnView struct {
// Provisioner is the account the provisioner's client runs as, as the revision read names it; RunsProvisioner as
// what runs names it. Empty: the declaration names none, and every filled write is refused.
Provisioner string `json:"provisioner_account"`
RunsProvisioner string `json:"runs_provisioner_account,omitempty"`
// Adoption is the revision's adoption: the node adopted, and which of its modules are taken; nil for a converged node.
Adoption *declaration.Adoption `json:"adoption,omitempty"`
// Identities, Groups and Libraries count what the revision names of each.
Identities int `json:"identities,omitempty"`
Groups int `json:"groups,omitempty"`
Libraries int `json:"libraries,omitempty"`
// Held is each module the node's composer held in its last pass, with why.
Held map[string]string `json:"held,omitempty"`
}
// WantView is a want as the verb shows it.
@@ -171,6 +192,17 @@ func (a *Agent) Composition(ctx context.Context, module, digest string, diff boo
}
view.Runs = rv
}
if module == NodeModule {
o := read.C.Own
view.Own = &OwnView{Provisioner: o.Provisioner, Adoption: o.Adoption, Identities: len(o.Identities), Groups: len(o.Groups),
Libraries: len(o.Libraries)}
if running != nil {
view.Own.RunsProvisioner = running.Own.Provisioner
}
if a.env.Held != nil {
view.Own.Held = a.env.Held()
}
}
j := judge.JudgeMove(running, read.C)
view.Judged = JudgedView{Judgement: string(j.Judgement), Words: j.Words}
if a.env.SelfComposed && a.env.Policy != nil && module != NodeModule && (!w.Present || w.Want.Yes != read.Dig) {