Builders, the artifact store's tools and distribution read and write the registry reference form through the registry clients' reference package, and name the sweep seat from its contract (ADR 0634 §4, S-8; issue 1966)

catalogue's SeatReference, InRegistrySeat, Routed, Recorded, InArtifactStore and ArtifactSweepSeat leave mesh-sdk;
each package gives the two registry seats' names from their contracts (or the build step's copies of them).

Claude-Session: https://claude.ai/code/session_01NcbgfFSnn24M3GcqttoU7i
This commit is contained in:
2026-11-05 17:26:32 +01:00
parent 2978dd5bed
commit 82d00aeb5e
17 changed files with 63 additions and 38 deletions
@@ -32,8 +32,8 @@ import (
"git.novox.be/novox/mesh-contracts/health-and-repair/go/clients/meshconditionsclient"
"git.novox.be/novox/mesh-contracts/health-and-repair/go/clients/meshhandactsclient"
meshconditions "git.novox.be/novox/mesh-contracts/health-and-repair/go/seats/meshconditions"
artifactref "git.novox.be/novox/mesh-delivery/contracts/go/clients/containerimageregistryclient/reference"
stdio "git.novox.be/novox/mesh-sdk/go"
"git.novox.be/novox/mesh-sdk/go/catalogue"
"git.novox.be/novox/mesh-sdk/go/views"
)
@@ -220,8 +220,8 @@ func KeepSet(builds []Build, wants []Want) map[string]*Ref {
out := map[string]*Ref{}
for _, b := range builds {
for _, a := range b.Artifacts {
reference := canonical(catalogue.Recorded(a.Reference))
if _, ours := catalogue.InArtifactStore(reference); !ours || a.Kind == "package" {
reference := canonical(registryForms.Recorded(a.Reference))
if _, ours := registryForms.InArtifactStore(reference); !ours || a.Kind == "package" {
continue
}
r := out[reference]
@@ -386,7 +386,7 @@ func Mirrors(v *View, builds []Build, kept map[string][]string, against map[stri
continue
}
for d := range v.L.Repos[name].Revisions {
r := catalogue.ArtifactStoreScheme + name + "@" + d
r := artifactref.ArtifactStoreScheme + name + "@" + d
out[r] = &Ref{Reference: r, Kind: "image"}
}
}
@@ -400,7 +400,7 @@ func Mirrors(v *View, builds []Build, kept map[string][]string, against map[stri
continue
}
for _, base := range bases {
if m := out[catalogue.Recorded(base)]; m != nil {
if m := out[registryForms.Recorded(base)]; m != nil {
m.Builds = append(m.Builds, b)
why := kept[b.Key]
if len(why) > 0 {
@@ -448,7 +448,7 @@ func (j *judged) records(repository string, collected bool) *Records {
}
}
r.Counts[state]++
if (repository != "" && !strings.HasPrefix(strings.TrimPrefix(ref.Reference, catalogue.ArtifactStoreScheme), repository)) ||
if (repository != "" && !strings.HasPrefix(strings.TrimPrefix(ref.Reference, artifactref.ArtifactStoreScheme), repository)) ||
(state == "collected" && !collected) {
continue
}
@@ -650,7 +650,7 @@ func (h *Holder) sayGone(j *judged, refs []string, how string) {
// artifacts-gone against its own key.
func namedBy(b Build, r string) string {
for _, a := range b.Artifacts {
if rec := catalogue.Recorded(a.Reference); canonical(rec) == r {
if rec := registryForms.Recorded(a.Reference); canonical(rec) == r {
return rec
}
}
@@ -678,7 +678,7 @@ func (h *Holder) Held(refs []string) (HeldAnswer, error) {
return HeldAnswer{}, fmt.Errorf("held judges at most 64 references at once, and %d were given", len(refs))
}
for _, r := range refs {
if _, ours := catalogue.InArtifactStore(r); !ours {
if _, ours := registryForms.InArtifactStore(r); !ours {
return HeldAnswer{}, fmt.Errorf("%s is not a reference into the mesh's artifact store (artifact-store://...): nothing was asked", r)
}
}
@@ -744,7 +744,7 @@ func (h *Holder) ImagesOf(node string, address string) (Images, error) {
images := []string{}
for _, a := range b.Artifacts {
if (a.Kind == "image" || a.Kind == "upstream") && a.Reference != "" {
images = append(images, catalogue.Routed(catalogue.Recorded(a.Reference), address))
images = append(images, registryForms.Routed(registryForms.Recorded(a.Reference), address))
}
}
pinned, err := h.Pinned(b.Manifest)
@@ -845,8 +845,8 @@ func inStoreAt(image, address string) string {
if address == "" || !strings.HasPrefix(image, address+"/") || !strings.Contains(image, "@sha256:") {
return ""
}
r := catalogue.Recorded(image)
if _, ours := catalogue.InArtifactStore(r); !ours {
r := registryForms.Recorded(image)
if _, ours := registryForms.InArtifactStore(r); !ours {
return ""
}
return r
@@ -879,7 +879,7 @@ func (h *Holder) Observe(ctx context.Context) error {
var refs []string
for _, a := range b.Artifacts {
if a.Kind == "image" {
refs = append(refs, catalogue.Recorded(a.Reference))
refs = append(refs, registryForms.Recorded(a.Reference))
}
}
// And what its manifest pins by itself under the store's address, as the controller judged S25.
@@ -22,7 +22,9 @@ import (
meshconditions "git.novox.be/novox/mesh-contracts/health-and-repair/go/seats/meshconditions"
stdio "git.novox.be/novox/mesh-sdk/go"
"git.novox.be/novox/mesh-sdk/go/catalogue"
artifactref "git.novox.be/novox/mesh-delivery/contracts/go/clients/containerimageregistryclient/reference"
reg "git.novox.be/novox/mesh-delivery/contracts/go/seats/containerimageregistry"
ociseat "git.novox.be/novox/mesh-delivery/contracts/go/seats/ociartifactregistry"
)
// memBus is the holder's bus in memory: states by name, each key's history, and what was published.
@@ -110,9 +112,9 @@ func (d *memDoor) seat(key string, body any) (json.RawMessage, error) {
var in struct{ Name, Digest, Reason string }
_ = json.Unmarshal(raw, &in)
seat, verb, _ := strings.Cut(strings.TrimPrefix(key, "seat:"), ".")
ref := catalogue.ArtifactStoreScheme + in.Name + "@" + in.Digest
ref := artifactref.ArtifactStoreScheme + in.Name + "@" + in.Digest
if seat == "oci-artifact-registry" {
ref = catalogue.ArtifactStoreScheme + in.Name + "/blobs/" + in.Digest
ref = artifactref.ArtifactStoreScheme + in.Name + "/blobs/" + in.Digest
}
d.calls = append(d.calls, key+" "+in.Name+"@"+in.Digest+" "+in.Reason)
if err := d.refuse[verb+" "+ref]; err != nil {
@@ -308,8 +310,8 @@ func TestTheSeatKeepsTheFiveNewestAndTheWantedAndSweepsWithNoLease(t *testing.T)
for _, n := range []int{2, 3} {
key, _ := builds.BuilderBuildKey("letta", fp(n))
raw, _ := builds.EncodeBuilderBuild(builds.BuilderBuild{State: builds.BuildDone, Manifest: strings.Repeat("d", 64), Artifacts: []builds.BuiltArtifact{
{Name: "image", Kind: "image", Digest: digestOf(imageRef("letta", n)), Reference: catalogue.SeatReference("container-image-registry", "letta", "image", digestOf(imageRef("letta", n)))},
{Name: "files", Kind: "archive", Digest: digestOf(archiveRef("letta", n)), Reference: catalogue.SeatReference("oci-artifact-registry", "letta", "files", digestOf(archiveRef("letta", n)))}}})
{Name: "image", Kind: "image", Digest: digestOf(imageRef("letta", n)), Reference: artifactref.SeatReference(reg.Seat, "letta", "image", digestOf(imageRef("letta", n)))},
{Name: "files", Kind: "archive", Digest: digestOf(archiveRef("letta", n)), Reference: artifactref.SeatReference(ociseat.Seat, "letta", "files", digestOf(archiveRef("letta", n)))}}})
_ = b.Put(BuildsRead, key, json.RawMessage(raw))
}
}
@@ -1,6 +1,6 @@
package main
// The seat mesh-artifact-sweep's verbs (novox/hq ADR 0571 clause 2; catalogue.ArtifactSweepSeat), each a tool named
// The seat mesh-artifact-sweep's verbs (novox/hq ADR 0571 clause 2; sweep.Seat), each a tool named
// `artifact-store.<verb>` as the runtime serves a seat's verb, answering as the controller's verb answered: {output,
// ok, answer}.
@@ -8,8 +8,8 @@ import (
"fmt"
"strings"
sweep "git.novox.be/novox/mesh-delivery/contracts/go/seats/meshartifactsweep"
stdio "git.novox.be/novox/mesh-sdk/go"
"git.novox.be/novox/mesh-sdk/go/catalogue"
)
// verbAnswer is the controller's verbs' answer shape, which the builder and docker read (answerOf).
@@ -21,7 +21,7 @@ type verbAnswer struct {
// SeatTools are the seat's verbs over h; s reads the store's listing for mirrors.
func SeatTools(h *Holder, s *Store) []stdio.Tool {
seat := catalogue.ArtifactSweepSeat + "."
seat := sweep.Seat + "."
return []stdio.Tool{
{Name: seat + "artifacts", Description: "Every artifact the mesh made that the store holds: kept and why, eligible, " +
"or with collected those it no longer holds.",
@@ -2,6 +2,7 @@ package main
import (
reg "git.novox.be/novox/mesh-delivery/contracts/go/seats/containerimageregistry"
sweep "git.novox.be/novox/mesh-delivery/contracts/go/seats/meshartifactsweep"
"git.novox.be/novox/mesh-sdk/go/catalogue"
"git.novox.be/novox/mesh-sdk/go/seatlist/seatlisttest"
"git.novox.be/novox/mesh-sdk/go/views"
@@ -489,15 +490,15 @@ func TestTheToolsServedAreTheToolsTheManifestNames(t *testing.T) {
}
var verbs []string
for _, tl := range SeatTools(&Holder{}, &Store{}) {
verbs = append(verbs, strings.TrimPrefix(tl.Name, catalogue.ArtifactSweepSeat+"."))
verbs = append(verbs, strings.TrimPrefix(tl.Name, sweep.Seat+"."))
}
catalogue.UseSeats(catalogue.SeatsFromDefinitions(seatlisttest.Definitions()))
seat, _ := catalogue.SeatNamed(catalogue.ArtifactSweepSeat)
seat, _ := catalogue.SeatNamed(sweep.Seat)
var contract []string
for _, v := range seat.Serves {
contract = append(contract, v.Name)
}
if len(m.Claims) != 1 || m.Claims[0].Name != catalogue.ArtifactSweepSeat || !reflect.DeepEqual(m.Claims[0].Serves, verbs) ||
if len(m.Claims) != 1 || m.Claims[0].Name != sweep.Seat || !reflect.DeepEqual(m.Claims[0].Serves, verbs) ||
!reflect.DeepEqual(verbs, contract) {
t.Errorf("claims %+v, serves %v, the seat's verbs %v", m.Claims, verbs, contract)
}
@@ -16,6 +16,7 @@ import (
"git.novox.be/novox/mesh-contracts/health-and-repair/go/clients/meshconditionsclient"
meshconditions "git.novox.be/novox/mesh-contracts/health-and-repair/go/seats/meshconditions"
artifactref "git.novox.be/novox/mesh-delivery/contracts/go/clients/containerimageregistryclient/reference"
ociseat "git.novox.be/novox/mesh-delivery/contracts/go/seats/ociartifactregistry"
"git.novox.be/novox/mesh-sdk/go/catalogue"
@@ -146,3 +147,7 @@ func keptWhy(r *Ref) string {
}
return "kept: " + strings.Join(r.Why, "; ")
}
// registryForms reads and routes a reference of the registry form, with the two registry seats' names from their contracts
// (the registry clients' reference forms, novox/hq ADR 0605 §9, ADR 0634 §4).
var registryForms = artifactref.Seats{Image: reg.Seat, Object: ociseat.Seat}
+1
View File
@@ -3,6 +3,7 @@ module artifactstoretools
go 1.26.0
require (
git.novox.be/novox/mesh-delivery/contracts/go/clients/containerimageregistryclient v0.0.0-00010101000000-000000000000
git.novox.be/novox/mesh-delivery/contracts/go/seats/meshartifactsweep v0.0.0-00010101000000-000000000000
git.novox.be/novox/mesh-contracts/placement/go/seats/meshwants v0.0.0-00010101000000-000000000000
git.novox.be/novox/mesh-contracts/go/seats/nodeengine v0.0.0-00010101000000-000000000000