From 8255640d00b3c46db8b4a51dbc1201f919a533d2 Mon Sep 17 00:00:00 2001 From: jochen Date: Wed, 11 Nov 2026 22:10:19 +0100 Subject: [PATCH] G findings: claude-code, mesh-provisioner, distribution, mesh-config and gitea declare the writer's three events MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit The writer listens to mesh-conditions.findings-asked, so each also consumes it, as the modules that moved before. Builds: design 47 G A-30, §383, §686 Claude-Session: https://claude.ai/code/session_01JG73KEq4zoDfM9WtYpcQgZ --- .../cmd/claude-code/config_test.go | 2 +- modules/claude-code/module.json | 17 ++++++++++++++- .../internal/holder/holder_test.go | 2 +- modules/distribution/module.json | 17 ++++++++++++++- modules/gitea/module.json | 17 ++++++++++++++- modules/mesh-config/module.json | 19 ++++++++++++++++- .../cmd/mesh-provisioner/provisioner_test.go | 8 ++++++- modules/mesh-provisioner/module.json | 21 +++++++++++++++++-- 8 files changed, 94 insertions(+), 9 deletions(-) diff --git a/modules/claude-code/cmd/claude-code/config_test.go b/modules/claude-code/cmd/claude-code/config_test.go index 5cdbc2238..948fb3c9b 100644 --- a/modules/claude-code/cmd/claude-code/config_test.go +++ b/modules/claude-code/cmd/claude-code/config_test.go @@ -279,7 +279,7 @@ func TestTheManifestListsEveryToolServed(t *testing.T) { // the controller, and no read of the indexer's or the assigner's state (ADR 0615 §1): their views are consumed. if !slices.Equal(m.Invokes, []string{"seat:mesh-hand-acts.warranted", "seat:mesh-hand-acts.hand-act", "seat:mesh-catalog.seat-definitions", ModulesTool, ManifestsTool, AssignmentsTool}) || !slices.Equal(m.Reads, []string{"claude-licence-manager.bindings"}) || - !slices.Equal(m.Consumes, []string{"mesh-delivery-indexer.views.modules", "mesh-delivery-indexer.views.manifests", "mesh-delivery-assigner.views.assignments", "mesh-catalog.seat-definition-changed", "mesh-catalog.seat-definition-removed"}) { + !slices.Equal(m.Consumes, []string{"mesh-delivery-indexer.views.modules", "mesh-delivery-indexer.views.manifests", "mesh-delivery-assigner.views.assignments", "mesh-catalog.seat-definition-changed", "mesh-catalog.seat-definition-removed", "mesh-conditions.findings-asked"}) { t.Errorf("invokes = %v, reads = %v, consumes = %v", m.Invokes, m.Reads, m.Consumes) } if src, _ := os.ReadFile("proposals.go"); !strings.Contains(string(src), `"seat:mesh-hand-acts.warranted"`) || diff --git a/modules/claude-code/module.json b/modules/claude-code/module.json index 7bfbd71fd..5a0b83f2f 100644 --- a/modules/claude-code/module.json +++ b/modules/claude-code/module.json @@ -11,6 +11,20 @@ { "name": "gitea-read", "optional": true + }, + { + "name": "finding-events", + "storage": "stream", + "template": "events", + "options": { + "events": [ + "finding-written.*", + "finding-cleared.*", + "findings-stated.*" + ], + "max-age-days": 7, + "max-mib": 16 + } } ], "binds": { @@ -35,7 +49,8 @@ "mesh-delivery-indexer.views.manifests", "mesh-delivery-assigner.views.assignments", "mesh-catalog.seat-definition-changed", - "mesh-catalog.seat-definition-removed" + "mesh-catalog.seat-definition-removed", + "mesh-conditions.findings-asked" ], "state": [ "servers", diff --git a/modules/distribution/internal/holder/holder_test.go b/modules/distribution/internal/holder/holder_test.go index c428e942b..332a3757e 100644 --- a/modules/distribution/internal/holder/holder_test.go +++ b/modules/distribution/internal/holder/holder_test.go @@ -865,7 +865,7 @@ func TestTheHolderOfTheTwoImageSeats(t *testing.T) { if _, ok := claims[OldSeat]; !ok { t.Error("the old seat mesh-artifact-store is no longer claimed while its window is open") } - if !reflect.DeepEqual(m.Consumes, []string{"mesh-delivery-view.delivered", "node-engine.manifest-reads-changed"}) { + if !reflect.DeepEqual(m.Consumes, []string{"mesh-delivery-view.delivered", "node-engine.manifest-reads-changed", "mesh-conditions.findings-asked"}) { t.Errorf("consumes = %v, want delivered and manifest-reads-changed (the windows' wakes)", m.Consumes) } // E14: the registry container, on the loopback, is listed before the program, so the port is free when it starts. diff --git a/modules/distribution/module.json b/modules/distribution/module.json index 04b974bbb..0642df247 100644 --- a/modules/distribution/module.json +++ b/modules/distribution/module.json @@ -67,7 +67,8 @@ ], "consumes": [ "mesh-delivery-view.delivered", - "node-engine.manifest-reads-changed" + "node-engine.manifest-reads-changed", + "mesh-conditions.findings-asked" ], "config": { "callers": { @@ -132,6 +133,20 @@ "max-age-days": 7, "max-mib": 16 } + }, + { + "name": "finding-events", + "storage": "stream", + "template": "events", + "options": { + "events": [ + "finding-written.*", + "finding-cleared.*", + "findings-stated.*" + ], + "max-age-days": 7, + "max-mib": 16 + } } ], "capabilities": [ diff --git a/modules/gitea/module.json b/modules/gitea/module.json index 5255a55f8..dd8276509 100644 --- a/modules/gitea/module.json +++ b/modules/gitea/module.json @@ -34,6 +34,20 @@ "options": { "history": 1 } + }, + { + "name": "finding-events", + "storage": "stream", + "template": "events", + "options": { + "events": [ + "finding-written.*", + "finding-cleared.*", + "findings-stated.*" + ], + "max-age-days": 7, + "max-mib": 16 + } } ], "contributes": { @@ -657,6 +671,7 @@ "git.branch-moved", "git.pull-updated", "git.pull-closed", - "git.pull-merged" + "git.pull-merged", + "mesh-conditions.findings-asked" ] } diff --git a/modules/mesh-config/module.json b/modules/mesh-config/module.json index 5e65b3fc8..5c772339f 100644 --- a/modules/mesh-config/module.json +++ b/modules/mesh-config/module.json @@ -33,7 +33,8 @@ "mesh-delivery-indexer.views.predefined", "mesh-delivery-indexer.views.config-candidates", "mesh-delivery-assigner.views.assignments", - "mesh-delivery-assigner.views.wants" + "mesh-delivery-assigner.views.wants", + "mesh-conditions.findings-asked" ], "invokes": [ "seat:mesh-hand-acts.hand-act", @@ -124,5 +125,21 @@ ], "retention": "history" } + ], + "requires": [ + { + "name": "finding-events", + "storage": "stream", + "template": "events", + "options": { + "events": [ + "finding-written.*", + "finding-cleared.*", + "findings-stated.*" + ], + "max-age-days": 7, + "max-mib": 16 + } + } ] } diff --git a/modules/mesh-provisioner/cmd/mesh-provisioner/provisioner_test.go b/modules/mesh-provisioner/cmd/mesh-provisioner/provisioner_test.go index 886324ebb..fd6cbc2d8 100644 --- a/modules/mesh-provisioner/cmd/mesh-provisioner/provisioner_test.go +++ b/modules/mesh-provisioner/cmd/mesh-provisioner/provisioner_test.go @@ -290,6 +290,12 @@ func TestTheManifestDeclaresWhatTheCodeKeeps(t *testing.T) { if err != nil { t.Fatal(err) } + // the writer's three events are declared (design 47 G A-30) + for _, ev := range []string{"finding-written.*", "finding-cleared.*", "findings-stated.*"} { + if !strings.Contains(string(raw), `"`+ev+`"`) { + t.Errorf("the manifest does not declare %s", ev) + } + } var m struct { Module string `json:"module"` RunsAs string `json:"runs-as"` @@ -364,7 +370,7 @@ func TestTheManifestDeclaresWhatTheCodeKeeps(t *testing.T) { } if !slices.Equal(m.Invokes, []string{AssignmentsTool, WantsTool, ModulesTool, ManifestsTool, "seat:mesh-hand-acts.hand-act"}) || !slices.Equal(m.Consumes, []string{"mesh-delivery-assigner.views.assignments", "mesh-delivery-assigner.views.wants", - "mesh-delivery-indexer.views.modules", "mesh-delivery-indexer.views.manifests"}) { + "mesh-delivery-indexer.views.modules", "mesh-delivery-indexer.views.manifests", "mesh-conditions.findings-asked"}) { t.Errorf("invokes %v, consumes %v", m.Invokes, m.Consumes) } // It composes nothing (ADR 0593 §8): no config value is read to make a plan. diff --git a/modules/mesh-provisioner/module.json b/modules/mesh-provisioner/module.json index c35a14b64..fb3326069 100644 --- a/modules/mesh-provisioner/module.json +++ b/modules/mesh-provisioner/module.json @@ -40,7 +40,8 @@ "mesh-delivery-assigner.views.assignments", "mesh-delivery-assigner.views.wants", "mesh-delivery-indexer.views.modules", - "mesh-delivery-indexer.views.manifests" + "mesh-delivery-indexer.views.manifests", + "mesh-conditions.findings-asked" ], "tools": [ "provisioner_provisions", @@ -105,5 +106,21 @@ ] } ] - } + }, + "requires": [ + { + "name": "finding-events", + "storage": "stream", + "template": "events", + "options": { + "events": [ + "finding-written.*", + "finding-cleared.*", + "findings-stated.*" + ], + "max-age-days": 7, + "max-mib": 16 + } + } + ] }