The assigner's state and verb placement are assignments, with its events, tools, views and every caller; the assigner copies the retired state at its start (issue 1966)
Claude-Session: https://claude.ai/code/session_01NcbgfFSnn24M3GcqttoU7i
This commit is contained in:
@@ -4,20 +4,22 @@ import (
|
||||
"bytes"
|
||||
"context"
|
||||
"encoding/json"
|
||||
"maps"
|
||||
"mesh-delivery-view/internal/view"
|
||||
"os"
|
||||
"path/filepath"
|
||||
"slices"
|
||||
"strings"
|
||||
"testing"
|
||||
"time"
|
||||
|
||||
"git.novox.be/novox/mesh-contracts/go/clients/meshmoduleassignerclient"
|
||||
"git.novox.be/novox/mesh-contracts/go/seats/meshmoduleassigner"
|
||||
occ "git.novox.be/novox/mesh-contracts/operator-and-conversation/go/clients/operatorchannelclient"
|
||||
oc "git.novox.be/novox/mesh-contracts/operator-and-conversation/go/seats/operatorchannel"
|
||||
"git.novox.be/novox/mesh-contracts/placement/go/clients/meshmoduleassignerclient"
|
||||
"git.novox.be/novox/mesh-contracts/placement/go/clients/meshwantsclient"
|
||||
"git.novox.be/novox/mesh-contracts/placement/go/seats/meshmoduleassigner"
|
||||
"git.novox.be/novox/mesh-delivery/contracts/go/clients/meshcatalogclient"
|
||||
"git.novox.be/novox/mesh-delivery/contracts/go/clients/meshdeliveryclient"
|
||||
"git.novox.be/novox/mesh-delivery/contracts/go/clients/meshwantsclient"
|
||||
"git.novox.be/novox/mesh-delivery/contracts/go/seats/meshcatalog"
|
||||
"git.novox.be/novox/mesh-delivery/contracts/go/seats/meshdelivery"
|
||||
"git.novox.be/novox/mesh-delivery/modules/mesh-delivery-assigner/asks"
|
||||
@@ -27,11 +29,13 @@ import (
|
||||
func serve(t *testing.T) string {
|
||||
t.Helper()
|
||||
m := view.New()
|
||||
placed, err := meshmoduleassignerclient.EncodePlacement(meshmoduleassigner.Placement{Node: "a", Modules: []meshmoduleassigner.PlacedModule{{Module: "x"}}})
|
||||
placed, err := meshmoduleassignerclient.AssignmentsValues(meshmoduleassigner.Assignments{Node: "a", Modules: []meshmoduleassigner.PlacedModule{{Module: "x"}}})
|
||||
if err != nil {
|
||||
t.Fatal(err)
|
||||
}
|
||||
m.Apply(view.Entry{Bucket: view.PlacementBucket, Key: "placement.a", Value: placed})
|
||||
for _, k := range slices.Sorted(maps.Keys(placed)) { // a key per module, then the node key
|
||||
m.Apply(view.Entry{Bucket: view.AssignmentsBucket, Key: k, Value: placed[k]})
|
||||
}
|
||||
dir, err := os.MkdirTemp(os.Getenv("TMPDIR"), "c")
|
||||
if err != nil {
|
||||
t.Fatal(err)
|
||||
|
||||
@@ -13,9 +13,9 @@ import (
|
||||
"git.novox.be/novox/mesh-contracts/go/clients/nodeengineclient"
|
||||
"git.novox.be/novox/mesh-contracts/go/seats/nodeengine"
|
||||
"git.novox.be/novox/mesh-contracts/health-and-repair/go/clients/meshwatchdogsclient"
|
||||
"git.novox.be/novox/mesh-contracts/placement/go/clients/meshwantsclient"
|
||||
"git.novox.be/novox/mesh-contracts/provisioning/go/clients/meshprovisionerclient"
|
||||
"git.novox.be/novox/mesh-delivery/contracts/go/clients/meshcatalogclient"
|
||||
"git.novox.be/novox/mesh-delivery/contracts/go/clients/meshwantsclient"
|
||||
"git.novox.be/novox/mesh-delivery/contracts/go/seats/meshcatalog"
|
||||
"git.novox.be/novox/mesh-delivery/modules/mesh-delivery-builder/builds"
|
||||
"git.novox.be/novox/mesh-delivery/modules/mesh-delivery-indexer/takein"
|
||||
|
||||
@@ -6,23 +6,25 @@ import (
|
||||
"context"
|
||||
"encoding/json"
|
||||
"io"
|
||||
"maps"
|
||||
"mesh-delivery-view/internal/view"
|
||||
"os"
|
||||
"path/filepath"
|
||||
"slices"
|
||||
"strings"
|
||||
"testing"
|
||||
"time"
|
||||
|
||||
"git.novox.be/novox/mesh-contracts/go/clients/meshmoduleassignerclient"
|
||||
"git.novox.be/novox/mesh-contracts/go/clients/nodeengineclient"
|
||||
"git.novox.be/novox/mesh-contracts/go/seats/meshmoduleassigner"
|
||||
"git.novox.be/novox/mesh-contracts/go/seats/nodeengine"
|
||||
"git.novox.be/novox/mesh-contracts/health-and-repair/go/clients/meshwatchdogsclient"
|
||||
occ "git.novox.be/novox/mesh-contracts/operator-and-conversation/go/clients/operatorchannelclient"
|
||||
oc "git.novox.be/novox/mesh-contracts/operator-and-conversation/go/seats/operatorchannel"
|
||||
"git.novox.be/novox/mesh-contracts/placement/go/clients/meshmoduleassignerclient"
|
||||
"git.novox.be/novox/mesh-contracts/placement/go/clients/meshwantsclient"
|
||||
"git.novox.be/novox/mesh-contracts/placement/go/seats/meshmoduleassigner"
|
||||
"git.novox.be/novox/mesh-delivery/contracts/go/clients/meshcatalogclient"
|
||||
"git.novox.be/novox/mesh-delivery/contracts/go/clients/meshdeliveryclient"
|
||||
"git.novox.be/novox/mesh-delivery/contracts/go/clients/meshwantsclient"
|
||||
"git.novox.be/novox/mesh-delivery/contracts/go/seats/meshcatalog"
|
||||
"git.novox.be/novox/mesh-delivery/contracts/go/seats/meshdelivery"
|
||||
"git.novox.be/novox/mesh-delivery/modules/mesh-delivery-assigner/asks"
|
||||
@@ -70,7 +72,7 @@ func TestProcessWholeSeesTheBuckets(t *testing.T) { // 1134/AC8
|
||||
ctx, cancel := context.WithTimeout(context.Background(), 60*time.Second)
|
||||
defer cancel()
|
||||
kvs := map[string]jetstream.KeyValue{}
|
||||
for _, b := range []string{view.HaveBucket, view.PlacementBucket, view.PresenceBucket, view.StuckBucket} {
|
||||
for _, b := range []string{view.HaveBucket, view.AssignmentsBucket, view.PresenceBucket, view.StuckBucket} {
|
||||
kv, err := js.CreateKeyValue(ctx, jetstream.KeyValueConfig{Bucket: b, History: 5})
|
||||
if err != nil {
|
||||
t.Fatal(err)
|
||||
@@ -90,20 +92,22 @@ func TestProcessWholeSeesTheBuckets(t *testing.T) { // 1134/AC8
|
||||
}
|
||||
return b
|
||||
}
|
||||
// The seat's placement (issue 774, ADR 0549 §3): x and y on a, nothing on b.
|
||||
placeValue := func(node string, modules ...string) []byte {
|
||||
p := meshmoduleassigner.Placement{Node: node}
|
||||
// The seat's assignments (issue 774, ADR 0549 §3): x and y on a, nothing on b.
|
||||
place := func(node string, modules ...string) {
|
||||
p := meshmoduleassigner.Assignments{Node: node}
|
||||
for _, m := range modules {
|
||||
p.Modules = append(p.Modules, meshmoduleassigner.PlacedModule{Module: m})
|
||||
}
|
||||
v, err := meshmoduleassignerclient.EncodePlacement(p)
|
||||
values, err := meshmoduleassignerclient.AssignmentsValues(p)
|
||||
if err != nil {
|
||||
t.Fatal(err)
|
||||
}
|
||||
return v
|
||||
for _, k := range slices.Sorted(maps.Keys(values)) { // a key per module, then the node key
|
||||
put(view.AssignmentsBucket, k, values[k])
|
||||
}
|
||||
}
|
||||
put(view.PlacementBucket, "placement.a", placeValue("a", "x", "y"))
|
||||
put(view.PlacementBucket, "placement.b", placeValue("b"))
|
||||
place("a", "x", "y")
|
||||
place("b")
|
||||
put(view.HaveBucket, "a.x", haveValue("b1", nodeengineclient.PhaseChecking, nodeengineclient.HealthWaits))
|
||||
put(view.HaveBucket, "b.x", haveValue("b1", nodeengineclient.PhaseRunning, nodeengineclient.HealthOK))
|
||||
|
||||
@@ -182,7 +186,7 @@ func TestProcessWholeShowsWhatTheWatchmanSays(t *testing.T) { // 1168/AC5
|
||||
ctx, cancel := context.WithTimeout(context.Background(), 60*time.Second)
|
||||
defer cancel()
|
||||
kvs := map[string]jetstream.KeyValue{}
|
||||
for _, b := range []string{view.HaveBucket, view.PlacementBucket, view.PresenceBucket, view.StuckBucket} {
|
||||
for _, b := range []string{view.HaveBucket, view.AssignmentsBucket, view.PresenceBucket, view.StuckBucket} {
|
||||
kv, err := js.CreateKeyValue(ctx, jetstream.KeyValueConfig{Bucket: b, History: 5})
|
||||
if err != nil {
|
||||
t.Fatal(err)
|
||||
@@ -269,7 +273,7 @@ func TestProcessWholeShowsTheIndexersBucketsOnceTheyExist(t *testing.T) { // 124
|
||||
}
|
||||
ctx, cancel := context.WithTimeout(context.Background(), 60*time.Second)
|
||||
defer cancel()
|
||||
for _, b := range []string{view.HaveBucket, view.PlacementBucket, view.PresenceBucket, view.StuckBucket} {
|
||||
for _, b := range []string{view.HaveBucket, view.AssignmentsBucket, view.PresenceBucket, view.StuckBucket} {
|
||||
if _, err := js.CreateKeyValue(ctx, jetstream.KeyValueConfig{Bucket: b, History: 5}); err != nil {
|
||||
t.Fatal(err)
|
||||
}
|
||||
|
||||
@@ -1,4 +1,4 @@
|
||||
// Command mesh-delivery-view is the operator's view of delivery (novox/hq ADR 0429 §3): it watches the have, the seat's placement
|
||||
// Command mesh-delivery-view is the operator's view of delivery (novox/hq ADR 0429 §3): it watches the have, the seat's assignments
|
||||
// and builds buckets on its own bus credential, derives one row per module and node in memory, and serves them on a
|
||||
// local socket (for mesh-delivery-cli) and on a local web page. It starts, stops or retries nothing; the one thing it writes is the operator's answer to an ask that needs no proof of who
|
||||
// answered, under `<ask key>.view` in its bucket answers (ADR 0528 clause 6).
|
||||
@@ -21,9 +21,9 @@ import (
|
||||
"syscall"
|
||||
"time"
|
||||
|
||||
sdkfindings "git.novox.be/novox/mesh-contracts/health-and-repair/go/clients/meshconditionsclient/findings"
|
||||
"git.novox.be/novox/mesh-delivery/modules/mesh-delivery-builder/builds"
|
||||
"git.novox.be/novox/mesh-delivery/modules/mesh-delivery-view/viewstate"
|
||||
sdkfindings "git.novox.be/novox/mesh-contracts/health-and-repair/go/clients/meshconditionsclient/findings"
|
||||
"git.novox.be/novox/mesh-delivery/sdk/trunk"
|
||||
"git.novox.be/novox/mesh-sdk/go/process"
|
||||
"git.novox.be/novox/mesh-sdk/go/views"
|
||||
@@ -126,7 +126,7 @@ func run(ctx context.Context, getenv func(string) string, logOut io.Writer) erro
|
||||
}
|
||||
}
|
||||
open := buckets{js: js, reader: reader}
|
||||
for _, bucket := range []string{view.HaveBucket, view.PlacementBucket, view.PresenceBucket, view.StuckBucket, view.CandidatesBucket, view.ModulesBucket, view.AsksBucket, view.AnswersBucket, builds.BuilderBuildsBucket, view.AssignerWantsBucket, view.SourceBucket, view.AssignerAsksBucket, viewstate.ViewAnswersBucket, view.TakenBucket} {
|
||||
for _, bucket := range []string{view.HaveBucket, view.AssignmentsBucket, view.PresenceBucket, view.StuckBucket, view.CandidatesBucket, view.ModulesBucket, view.AsksBucket, view.AnswersBucket, builds.BuilderBuildsBucket, view.AssignerWantsBucket, view.SourceBucket, view.AssignerAsksBucket, viewstate.ViewAnswersBucket, view.TakenBucket} {
|
||||
go follow(ctx, open, bucket, false, model, logger)
|
||||
}
|
||||
// The modules' and the source's history give each fingerprint's first commit and each head's source revision (ADR 0556).
|
||||
@@ -185,7 +185,7 @@ var (
|
||||
// owner's read tool (as the view's invokes names it) and views family (its events on the shared events stream); the
|
||||
// view's tools ask the other six through the owners' read tools on each call.
|
||||
var ownersFollowed = []struct{ owner, state, tool string }{
|
||||
{view.AssignerModule, view.PlacementState, view.AssignerModule + ".assigner_read_placement"},
|
||||
{view.AssignerModule, view.AssignmentsState, view.AssignerModule + ".assigner_read_assignments"},
|
||||
{view.AssignerModule, "wants", view.AssignerModule + ".assigner_read_wants"},
|
||||
{view.AssignerModule, "asks", view.AssignerModule + ".assigner_read_asks"},
|
||||
{view.IndexerModule, "candidates", view.IndexerModule + ".indexer_read_candidates"},
|
||||
|
||||
@@ -7,9 +7,9 @@ require (
|
||||
git.novox.be/novox/mesh-contracts/go/clients/nodeengineclient v0.0.0-00010101000000-000000000000
|
||||
git.novox.be/novox/mesh-contracts/health-and-repair/go/clients/meshwatchdogsclient v0.0.0-00010101000000-000000000000
|
||||
git.novox.be/novox/mesh-contracts/identity-and-access/go/clients/meshvaultclient v0.0.0-00010101000000-000000000000
|
||||
git.novox.be/novox/mesh-contracts/placement/go/clients/meshmoduleassignerclient v0.0.0-00010101000000-000000000000
|
||||
git.novox.be/novox/mesh-contracts/placement/go/clients/meshwantsclient v0.0.0-00010101000000-000000000000
|
||||
git.novox.be/novox/mesh-contracts/placement/go/seats/meshmoduleassigner v0.0.0-00010101000000-000000000000
|
||||
git.novox.be/novox/mesh-contracts/go/clients/meshmoduleassignerclient v0.0.0-00010101000000-000000000000
|
||||
git.novox.be/novox/mesh-delivery/contracts/go/clients/meshwantsclient v0.0.0-00010101000000-000000000000
|
||||
git.novox.be/novox/mesh-contracts/go/seats/meshmoduleassigner v0.0.0-00010101000000-000000000000
|
||||
git.novox.be/novox/mesh-delivery/contracts/go/clients/meshcatalogclient v0.0.0-00010101000000-000000000000
|
||||
git.novox.be/novox/mesh-delivery/contracts/go/clients/meshdeliveryclient v0.0.0-00010101000000-000000000000
|
||||
git.novox.be/novox/mesh-delivery/contracts/go/seats/meshcatalog v0.0.0-00010101000000-000000000000
|
||||
@@ -58,7 +58,7 @@ require (
|
||||
git.novox.be/novox/mesh-contracts/health-and-repair/go/seats/meshhandacts v0.0.0-00010101000000-000000000000 // indirect
|
||||
git.novox.be/novox/mesh-contracts/health-and-repair/go/seats/meshwatchdogs v0.0.0-00010101000000-000000000000 // indirect
|
||||
git.novox.be/novox/mesh-contracts/identity-and-access/go/seats/meshvault v0.0.0-00010101000000-000000000000 // indirect
|
||||
git.novox.be/novox/mesh-contracts/placement/go/seats/meshwants v0.0.0-00010101000000-000000000000 // indirect
|
||||
git.novox.be/novox/mesh-delivery/contracts/go/seats/meshwants v0.0.0-00010101000000-000000000000 // indirect
|
||||
git.novox.be/novox/mesh-delivery/contracts/go/clients/containerimageregistryclient v0.0.0-00010101000000-000000000000 // indirect
|
||||
git.novox.be/novox/mesh-delivery/contracts/go/seats/containerimageregistry v0.0.0-00010101000000-000000000000 // indirect
|
||||
git.novox.be/novox/mesh-delivery/contracts/go/seats/ociartifactregistry v0.0.0-00010101000000-000000000000 // indirect
|
||||
|
||||
@@ -11,8 +11,8 @@ import (
|
||||
"time"
|
||||
|
||||
oc "git.novox.be/novox/mesh-contracts/operator-and-conversation/go/seats/operatorchannel"
|
||||
"git.novox.be/novox/mesh-contracts/placement/go/clients/meshwantsclient"
|
||||
"git.novox.be/novox/mesh-delivery/contracts/go/clients/meshcatalogclient"
|
||||
"git.novox.be/novox/mesh-delivery/contracts/go/clients/meshwantsclient"
|
||||
"git.novox.be/novox/mesh-delivery/modules/mesh-delivery-assigner/asks"
|
||||
"git.novox.be/novox/mesh-delivery/modules/mesh-delivery-view/viewstate"
|
||||
)
|
||||
|
||||
@@ -4,9 +4,9 @@ import (
|
||||
"strings"
|
||||
"testing"
|
||||
|
||||
"git.novox.be/novox/mesh-contracts/placement/go/clients/meshwantsclient"
|
||||
"git.novox.be/novox/mesh-delivery/contracts/go/clients/meshcatalogclient"
|
||||
"git.novox.be/novox/mesh-delivery/contracts/go/clients/meshdeliveryclient"
|
||||
"git.novox.be/novox/mesh-delivery/contracts/go/clients/meshwantsclient"
|
||||
"git.novox.be/novox/mesh-delivery/modules/mesh-delivery-view/viewstate"
|
||||
)
|
||||
|
||||
|
||||
@@ -2,7 +2,7 @@ package view
|
||||
|
||||
import (
|
||||
"git.novox.be/novox/mesh-contracts/go/seats/nodeengine"
|
||||
"git.novox.be/novox/mesh-contracts/placement/go/clients/meshwantsclient"
|
||||
"git.novox.be/novox/mesh-delivery/contracts/go/clients/meshwantsclient"
|
||||
"git.novox.be/novox/mesh-sdk/go/motion"
|
||||
)
|
||||
|
||||
|
||||
@@ -35,8 +35,8 @@ const (
|
||||
IndexerConfigCandidatesState = "config-candidates"
|
||||
|
||||
// The assigner's states.
|
||||
PlacementState = "placement"
|
||||
PlacementBucket = AssignerModule + "_" + PlacementState
|
||||
AssignmentsState = "assignments"
|
||||
AssignmentsBucket = AssignerModule + "_" + AssignmentsState
|
||||
AssignerWantsBucket = AssignerModule + "_wants"
|
||||
AssignerAsksBucket = AssignerModule + "_asks"
|
||||
|
||||
|
||||
@@ -7,9 +7,9 @@ import (
|
||||
|
||||
"git.novox.be/novox/mesh-contracts/go/clients/nodeengineclient"
|
||||
"git.novox.be/novox/mesh-contracts/go/seats/nodeengine"
|
||||
"git.novox.be/novox/mesh-contracts/placement/go/clients/meshwantsclient"
|
||||
"git.novox.be/novox/mesh-delivery/contracts/go/clients/meshcatalogclient"
|
||||
"git.novox.be/novox/mesh-delivery/contracts/go/clients/meshdeliveryclient"
|
||||
"git.novox.be/novox/mesh-delivery/contracts/go/clients/meshwantsclient"
|
||||
"git.novox.be/novox/mesh-delivery/contracts/go/seats/meshcatalog"
|
||||
"git.novox.be/novox/mesh-delivery/contracts/go/seats/meshdelivery"
|
||||
"git.novox.be/novox/mesh-delivery/modules/mesh-delivery-indexer/takein"
|
||||
|
||||
@@ -16,8 +16,8 @@ import (
|
||||
|
||||
"git.novox.be/novox/mesh-contracts/go/clients/nodeengineclient"
|
||||
"git.novox.be/novox/mesh-contracts/identity-and-access/go/clients/meshvaultclient"
|
||||
"git.novox.be/novox/mesh-contracts/placement/go/clients/meshwantsclient"
|
||||
"git.novox.be/novox/mesh-delivery/contracts/go/clients/meshcatalogclient"
|
||||
"git.novox.be/novox/mesh-delivery/contracts/go/clients/meshwantsclient"
|
||||
"git.novox.be/novox/mesh-delivery/contracts/go/seats/meshcatalog"
|
||||
"git.novox.be/novox/mesh-delivery/modules/mesh-delivery-builder/builds"
|
||||
"git.novox.be/novox/mesh-delivery/modules/mesh-delivery-indexer/takein"
|
||||
|
||||
@@ -12,7 +12,7 @@ import (
|
||||
"git.novox.be/novox/mesh-contracts/health-and-repair/go/clients/meshwatchdogsclient"
|
||||
mcseat "git.novox.be/novox/mesh-contracts/health-and-repair/go/seats/meshconditions"
|
||||
healers "git.novox.be/novox/mesh-contracts/health-and-repair/go/seats/meshhealers"
|
||||
"git.novox.be/novox/mesh-contracts/placement/go/clients/meshwantsclient"
|
||||
"git.novox.be/novox/mesh-delivery/contracts/go/clients/meshwantsclient"
|
||||
"git.novox.be/novox/mesh-sdk/go/motion"
|
||||
)
|
||||
|
||||
|
||||
@@ -11,10 +11,10 @@ import (
|
||||
|
||||
"git.novox.be/novox/mesh-contracts/go/clients/nodeengineclient"
|
||||
"git.novox.be/novox/mesh-contracts/health-and-repair/go/clients/meshwatchdogsclient"
|
||||
"git.novox.be/novox/mesh-contracts/placement/go/clients/meshwantsclient"
|
||||
"git.novox.be/novox/mesh-contracts/provisioning/go/clients/meshprovisionerclient"
|
||||
"git.novox.be/novox/mesh-delivery/contracts/go/clients/meshcatalogclient"
|
||||
"git.novox.be/novox/mesh-delivery/contracts/go/clients/meshdeliveryclient"
|
||||
"git.novox.be/novox/mesh-delivery/contracts/go/clients/meshwantsclient"
|
||||
"git.novox.be/novox/mesh-delivery/contracts/go/seats/meshcatalog"
|
||||
"git.novox.be/novox/mesh-delivery/modules/mesh-delivery-builder/builds"
|
||||
"git.novox.be/novox/mesh-delivery/modules/mesh-delivery-indexer/takein"
|
||||
|
||||
@@ -11,15 +11,15 @@ import (
|
||||
"sync"
|
||||
"time"
|
||||
|
||||
"git.novox.be/novox/mesh-contracts/go/clients/meshmoduleassignerclient"
|
||||
"git.novox.be/novox/mesh-contracts/go/clients/nodeengineclient"
|
||||
"git.novox.be/novox/mesh-contracts/go/seats/nodeengine"
|
||||
"git.novox.be/novox/mesh-contracts/health-and-repair/go/clients/meshwatchdogsclient"
|
||||
occ "git.novox.be/novox/mesh-contracts/operator-and-conversation/go/clients/operatorchannelclient"
|
||||
oc "git.novox.be/novox/mesh-contracts/operator-and-conversation/go/seats/operatorchannel"
|
||||
"git.novox.be/novox/mesh-contracts/placement/go/clients/meshmoduleassignerclient"
|
||||
"git.novox.be/novox/mesh-contracts/placement/go/clients/meshwantsclient"
|
||||
"git.novox.be/novox/mesh-delivery/contracts/go/clients/meshcatalogclient"
|
||||
"git.novox.be/novox/mesh-delivery/contracts/go/clients/meshdeliveryclient"
|
||||
"git.novox.be/novox/mesh-delivery/contracts/go/clients/meshwantsclient"
|
||||
"git.novox.be/novox/mesh-delivery/contracts/go/seats/meshcatalog"
|
||||
"git.novox.be/novox/mesh-delivery/contracts/go/seats/meshdelivery"
|
||||
"git.novox.be/novox/mesh-delivery/modules/mesh-delivery-assigner/asks"
|
||||
@@ -235,7 +235,7 @@ type UnreadableRow struct {
|
||||
// Model holds the rows' inputs in memory and nothing else: a restart fills it again from the buckets' last values.
|
||||
type Model struct {
|
||||
mu sync.Mutex
|
||||
placed *meshmoduleassignerclient.Placed // the seat's placement (the assigner's state, ADR 0567, ADR 0549 §3)
|
||||
placed *meshmoduleassignerclient.Placed // the seat's assignments (the assigner's state, ADR 0567, ADR 0549 §3)
|
||||
builds map[string]buildEntry // by <module>.build.<id>
|
||||
groups map[string]groupEntry // the indexer's candidates, by group
|
||||
modules map[string]moduleEntry // the indexer's modules, by module
|
||||
@@ -282,10 +282,10 @@ type stuckEntry struct {
|
||||
err string
|
||||
}
|
||||
|
||||
// pair is a module the seat's placement puts on a node.
|
||||
// pair is a module the seat's assignments puts on a node.
|
||||
type pair struct{ Node, Module string }
|
||||
|
||||
// placedPairs is every module the seat's placement puts on a node, by node then module. The caller holds mu.
|
||||
// placedPairs is every module the seat's assignments puts on a node, by node then module. The caller holds mu.
|
||||
func (m *Model) placedPairs() []pair {
|
||||
byNode := m.placed.ByNode()
|
||||
var out []pair
|
||||
@@ -542,8 +542,8 @@ func (m *Model) apply(e Entry) {
|
||||
}
|
||||
st, err := meshwatchdogsclient.DecodeStuck(e.Value)
|
||||
m.stuck[e.Key] = stuckEntry{value: st, err: errText(err)}
|
||||
case PlacementBucket:
|
||||
// A key that does not read places nothing on its node; the seat's verb placement says why.
|
||||
case AssignmentsBucket:
|
||||
// A key that does not read places nothing on its node; the seat's verb assignments says why.
|
||||
_, _, _ = m.placed.Put(e.Key, e.Value, e.Deleted, e.At)
|
||||
case CandidatesBucket:
|
||||
if e.Deleted {
|
||||
|
||||
@@ -8,16 +8,16 @@ import (
|
||||
"testing"
|
||||
"time"
|
||||
|
||||
"git.novox.be/novox/mesh-contracts/go/clients/meshmoduleassignerclient"
|
||||
"git.novox.be/novox/mesh-contracts/go/clients/nodeengineclient"
|
||||
"git.novox.be/novox/mesh-contracts/go/seats/meshmoduleassigner"
|
||||
"git.novox.be/novox/mesh-contracts/go/seats/nodeengine"
|
||||
mcc "git.novox.be/novox/mesh-contracts/health-and-repair/go/clients/meshconditionsclient"
|
||||
"git.novox.be/novox/mesh-contracts/health-and-repair/go/clients/meshwatchdogsclient"
|
||||
mcseat "git.novox.be/novox/mesh-contracts/health-and-repair/go/seats/meshconditions"
|
||||
healers "git.novox.be/novox/mesh-contracts/health-and-repair/go/seats/meshhealers"
|
||||
"git.novox.be/novox/mesh-contracts/placement/go/clients/meshmoduleassignerclient"
|
||||
"git.novox.be/novox/mesh-contracts/placement/go/clients/meshwantsclient"
|
||||
"git.novox.be/novox/mesh-contracts/placement/go/seats/meshmoduleassigner"
|
||||
"git.novox.be/novox/mesh-delivery/contracts/go/clients/meshcatalogclient"
|
||||
"git.novox.be/novox/mesh-delivery/contracts/go/clients/meshwantsclient"
|
||||
"git.novox.be/novox/mesh-sdk/go/keys"
|
||||
"git.novox.be/novox/mesh-sdk/go/motion"
|
||||
)
|
||||
@@ -37,20 +37,20 @@ func haveE(t *testing.T, node, module string, v []byte, at time.Time) Entry {
|
||||
return Entry{Bucket: HaveBucket, Key: node + "." + module, Value: v, At: at}
|
||||
}
|
||||
|
||||
// place is the seat's placement of node, as the assigner keeps it (ADR 0567): the modules placed there.
|
||||
// place is the seat's assignments of node, as the assigner keeps it (ADR 0567): the modules placed there.
|
||||
func place(t *testing.T, node string, modules ...string) Entry {
|
||||
t.Helper()
|
||||
p := meshmoduleassigner.Placement{Node: node}
|
||||
p := meshmoduleassigner.Assignments{Node: node}
|
||||
for _, m := range modules {
|
||||
p.Modules = append(p.Modules, meshmoduleassigner.PlacedModule{Module: m})
|
||||
}
|
||||
// Its node key, which names the modules placed (research 072 row 37).
|
||||
values, err := meshmoduleassignerclient.PlacementValues(p)
|
||||
values, err := meshmoduleassignerclient.AssignmentsValues(p)
|
||||
if err != nil {
|
||||
t.Fatal(err)
|
||||
}
|
||||
key, _ := meshmoduleassignerclient.NodeKey(node)
|
||||
return Entry{Bucket: PlacementBucket, Key: key, Value: values[key], At: t0}
|
||||
return Entry{Bucket: AssignmentsBucket, Key: key, Value: values[key], At: t0}
|
||||
}
|
||||
|
||||
func find(t *testing.T, s Snapshot, node, module string) Row {
|
||||
@@ -100,7 +100,7 @@ func TestRowsPerAssignedModuleAndNode(t *testing.T) { // 1134/AC1
|
||||
}
|
||||
}
|
||||
|
||||
func TestLeftBehindIsWhatThePlacementDoesNotPut(t *testing.T) { // 1134/AC3, issue 774 (the seat's placement)
|
||||
func TestLeftBehindIsWhatTheAssignmentsDoesNotPut(t *testing.T) { // 1134/AC3, issue 774 (the seat's assignments)
|
||||
m := New()
|
||||
fill(m, base(t)...)
|
||||
fill(m, place(t, "b", "x")) // z taken off b
|
||||
@@ -113,11 +113,11 @@ func TestLeftBehindIsWhatThePlacementDoesNotPut(t *testing.T) { // 1134/AC3, iss
|
||||
fill(m, haveE(t, "a", "w", have(t, "b9", nodeengineclient.PhaseRunning, nodeengineclient.HealthOK, ""), t0)) // placed nowhere
|
||||
s = m.Snapshot()
|
||||
if find(t, s, "a", "w").Status != StatusLeftBehind || s.Counted() != 4 {
|
||||
t.Fatalf("a have with no placement: %+v counted %d", find(t, s, "a", "w"), s.Counted())
|
||||
t.Fatalf("a have with no assignments: %+v counted %d", find(t, s, "a", "w"), s.Counted())
|
||||
}
|
||||
fill(m, Entry{Bucket: PlacementBucket, Key: "b.node", Deleted: true})
|
||||
fill(m, Entry{Bucket: AssignmentsBucket, Key: "b.node", Deleted: true})
|
||||
if s := m.Snapshot(); s.Counted() != 2 || find(t, s, "b", "x").Status != StatusLeftBehind {
|
||||
t.Fatalf("b's placement deleted: counted %d, %+v", s.Counted(), s.Rows)
|
||||
t.Fatalf("b's assignments deleted: counted %d, %+v", s.Counted(), s.Rows)
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
@@ -9,9 +9,9 @@ import (
|
||||
"git.novox.be/novox/mesh-contracts/go/clients/nodeengineclient"
|
||||
"git.novox.be/novox/mesh-contracts/go/seats/nodeengine"
|
||||
"git.novox.be/novox/mesh-contracts/health-and-repair/go/clients/meshwatchdogsclient"
|
||||
"git.novox.be/novox/mesh-contracts/placement/go/clients/meshwantsclient"
|
||||
"git.novox.be/novox/mesh-delivery/contracts/go/clients/meshcatalogclient"
|
||||
"git.novox.be/novox/mesh-delivery/contracts/go/clients/meshdeliveryclient"
|
||||
"git.novox.be/novox/mesh-delivery/contracts/go/clients/meshwantsclient"
|
||||
"git.novox.be/novox/mesh-delivery/contracts/go/seats/meshcatalog"
|
||||
"git.novox.be/novox/mesh-delivery/contracts/go/seats/meshdelivery"
|
||||
)
|
||||
@@ -244,7 +244,7 @@ func TestARowReadsTheWantWhenTheAssignmentNamesNoBuild(t *testing.T) {
|
||||
// and a have nothing is assigned to keeps the module's name.
|
||||
func TestADottedModuleNameIsFoundAndKept(t *testing.T) {
|
||||
m := New()
|
||||
// The seat's placement refuses a dotted module name (mesh-sdk meshmoduleassigner.Placement), so such a module is never placed:
|
||||
// The seat's assignments refuses a dotted module name (mesh-sdk meshmoduleassigner.Assignments), so such a module is never placed:
|
||||
// its have is a row left behind under its own name.
|
||||
fill(m, place(t, "ace"), wantE(t, "ace", "novox.be", meshwantsclient.Want{Fp: fpNew}), haveFP(t, "ace", "novox.be", fpNew, nodeengineclient.HealthOK),
|
||||
haveFP(t, "ace", "old.name", fpNew, nodeengineclient.HealthOK))
|
||||
|
||||
@@ -109,7 +109,7 @@ func TestManifestIsTakenAndReadsOnly(t *testing.T) { // 1134/AC7
|
||||
}
|
||||
// The indexer's and the assigner's states are asked of their owners' read tools (design 25 § 12.2), the six the process
|
||||
// follows then heard on their views families (ADR 0615 §1, §5; DLV-M4).
|
||||
if want := []string{"mesh-delivery-assigner.assigner_read_asks", "mesh-delivery-assigner.assigner_read_differences", "mesh-delivery-assigner.assigner_read_placement",
|
||||
if want := []string{"mesh-delivery-assigner.assigner_read_asks", "mesh-delivery-assigner.assigner_read_differences", "mesh-delivery-assigner.assigner_read_assignments",
|
||||
"mesh-delivery-assigner.assigner_read_wants", "mesh-delivery-indexer.indexer_read_candidates", "mesh-delivery-indexer.indexer_read_config_candidates",
|
||||
"mesh-delivery-indexer.indexer_read_graph", "mesh-delivery-indexer.indexer_read_heard", "mesh-delivery-indexer.indexer_pending", "mesh-delivery-indexer.indexer_read_modules",
|
||||
"mesh-delivery-indexer.indexer_read_packages", "mesh-delivery-indexer.indexer_read_predefined", "mesh-delivery-indexer.indexer_read_taken",
|
||||
@@ -117,7 +117,7 @@ func TestManifestIsTakenAndReadsOnly(t *testing.T) { // 1134/AC7
|
||||
"seat:node-engine.manifest-reads"}; !reflect.DeepEqual(m.Invokes, want) { // ADR 0618 §3: node_manifest_reads asks the node-engine seat's verb of every node; 1585/T24: view_tiers asks indexer_pending, a verb edge (ADR 0614 §2)
|
||||
t.Errorf("invokes = %v, want %v", m.Invokes, want)
|
||||
}
|
||||
if want := []string{"mesh-delivery-assigner.views.asks", "mesh-delivery-assigner.views.placement", "mesh-delivery-assigner.views.wants",
|
||||
if want := []string{"mesh-delivery-assigner.views.asks", "mesh-delivery-assigner.views.assignments", "mesh-delivery-assigner.views.wants",
|
||||
"mesh-delivery-indexer.views.candidates", "mesh-delivery-indexer.views.modules", "mesh-delivery-indexer.views.taken"}; !reflect.DeepEqual(m.Consumes, want) {
|
||||
t.Errorf("consumes = %v, want %v", m.Consumes, want)
|
||||
}
|
||||
@@ -166,7 +166,7 @@ func TestManifestIsTakenAndReadsOnly(t *testing.T) { // 1134/AC7
|
||||
t.Errorf("the view reads %s, its manifest's reads are %v", view.SignersRead, m.Reads)
|
||||
}
|
||||
followed := map[string]string{view.ModulesBucket: view.IndexerModule + ".views.modules", view.CandidatesBucket: view.IndexerModule + ".views.candidates",
|
||||
view.TakenBucket: view.IndexerModule + ".views.taken", view.PlacementBucket: view.AssignerModule + ".views.placement",
|
||||
view.TakenBucket: view.IndexerModule + ".views.taken", view.AssignmentsBucket: view.AssignerModule + ".views.assignments",
|
||||
view.AssignerWantsBucket: view.AssignerModule + ".views.wants", view.AssignerAsksBucket: view.AssignerModule + ".views.asks"}
|
||||
for bucket, family := range followed {
|
||||
if module, state, _ := strings.Cut(family, ".views."); bucket != module+"_"+state {
|
||||
@@ -339,7 +339,7 @@ func TestNoSharedDirectoryIsClaimed(t *testing.T) { // 1134/AC7
|
||||
}
|
||||
|
||||
// The node-engine never places a module-owned directory below /etc, /usr, /run or /var/run: they are root's
|
||||
// (mesh-host internal/apply/placement_guard.go:80, rootsOnly; novox/hq issue 339).
|
||||
// (mesh-host internal/apply/assignments_guard.go:80, rootsOnly; novox/hq issue 339).
|
||||
func TestNoDirectoryBelowRootsTrees(t *testing.T) { // 1134/AC10
|
||||
m, _ := load(t)
|
||||
for _, r := range m.Resources {
|
||||
|
||||
@@ -43,7 +43,7 @@
|
||||
],
|
||||
"consumes": [
|
||||
"mesh-delivery-assigner.views.asks",
|
||||
"mesh-delivery-assigner.views.placement",
|
||||
"mesh-delivery-assigner.views.assignments",
|
||||
"mesh-delivery-assigner.views.wants",
|
||||
"mesh-delivery-indexer.views.candidates",
|
||||
"mesh-delivery-indexer.views.modules",
|
||||
@@ -52,7 +52,7 @@
|
||||
"invokes": [
|
||||
"mesh-delivery-assigner.assigner_read_asks",
|
||||
"mesh-delivery-assigner.assigner_read_differences",
|
||||
"mesh-delivery-assigner.assigner_read_placement",
|
||||
"mesh-delivery-assigner.assigner_read_assignments",
|
||||
"mesh-delivery-assigner.assigner_read_wants",
|
||||
"mesh-delivery-indexer.indexer_read_candidates",
|
||||
"mesh-delivery-indexer.indexer_read_config_candidates",
|
||||
|
||||
@@ -14,8 +14,8 @@ replace git.novox.be/novox/mesh-delivery/sdk => ../../../sdk
|
||||
require (
|
||||
git.novox.be/novox/mesh-contracts/go/clients/nodeengineclient v0.0.0-00010101000000-000000000000 // indirect
|
||||
git.novox.be/novox/mesh-contracts/go/seats/nodeengine v0.0.0-00010101000000-000000000000 // indirect
|
||||
git.novox.be/novox/mesh-contracts/placement/go/clients/meshmoduleassignerclient v0.0.0-00010101000000-000000000000 // indirect
|
||||
git.novox.be/novox/mesh-contracts/placement/go/seats/meshmoduleassigner v0.0.0-00010101000000-000000000000 // indirect
|
||||
git.novox.be/novox/mesh-contracts/go/clients/meshmoduleassignerclient v0.0.0-00010101000000-000000000000 // indirect
|
||||
git.novox.be/novox/mesh-contracts/go/seats/meshmoduleassigner v0.0.0-00010101000000-000000000000 // indirect
|
||||
git.novox.be/novox/mesh-delivery/contracts/go/clients/containerimageregistryclient v0.0.0-00010101000000-000000000000 // indirect
|
||||
git.novox.be/novox/mesh-delivery/contracts/go/clients/meshcatalogclient v0.0.0-00010101000000-000000000000 // indirect
|
||||
git.novox.be/novox/mesh-delivery/contracts/go/seats/containerimageregistry v0.0.0-00010101000000-000000000000 // indirect
|
||||
|
||||
Reference in New Issue
Block a user