diff --git a/modules/mesh-delivery-assigner/cmd/mesh-delivery-assigner/candidateadded.go b/modules/mesh-delivery-assigner/cmd/mesh-delivery-assigner/candidateadded.go index 5dc20219..1bbfa391 100644 --- a/modules/mesh-delivery-assigner/cmd/mesh-delivery-assigner/candidateadded.go +++ b/modules/mesh-delivery-assigner/cmd/mesh-delivery-assigner/candidateadded.go @@ -9,18 +9,26 @@ import ( // addedOf is the `added` of node's candidate (design 47 G A-316, §379, §421): by module, each module the candidate adds to node // (laid over current) with no want there, the version and parts the want it would write carries, taken from the same code that -// writes a want's (namedBuild, the want's build at the module's trunk fingerprint). A module whose build names none is not listed. +// writes a want's (namedBuild, the want's build at the fingerprint of the branch the want's code takes). A module whose build names none is not listed. func (p *passer) addedOf(node string, laid *mma.Assignments, current map[string]mma.Assignments) map[string]mma.AddedModule { if laid == nil { return nil } - trunk := p.w.trunk() + placed := map[string]string{} + for _, m := range laid.Modules { + placed[m.Module] = m.Branch + } var out map[string]mma.AddedModule for _, module := range plc.ChangeOf(current[node], *laid).Added { if key, err := mwc.WantKey(node, module); err != nil || p.w.has(buckets.Wants(), key) { continue } - fp := trunk[module].Fp2 + // The branch the want's code takes: the one the candidate's placement names, else the module's default (groups, wants). + branch := p.w.trunkName() + if p.ends.following() { + branch = p.ends.branchOf(module, placed[module]) + } + fp := p.w.trunkOf(branch)[module].Fp2 if fp == "" { continue } diff --git a/modules/mesh-delivery-assigner/cmd/mesh-delivery-assigner/candidateadded_test.go b/modules/mesh-delivery-assigner/cmd/mesh-delivery-assigner/candidateadded_test.go index e33950b3..b6a9505f 100644 --- a/modules/mesh-delivery-assigner/cmd/mesh-delivery-assigner/candidateadded_test.go +++ b/modules/mesh-delivery-assigner/cmd/mesh-delivery-assigner/candidateadded_test.go @@ -43,4 +43,17 @@ func TestACandidateThatAddsAModuleCarriesItsParts(t *testing.T) { if got := p.candidateOf("p1", "ace", nil, current); got.Added != nil { t.Errorf("a candidate taking the key away adds %+v", got.Added) } + // A placement on a watched branch is added at that branch's fingerprint, as the want's code takes it, not the trunk's. + w.putModule("feat", "mail", meshcatalog.ModulesByModuleValue{Fp2: "fp-feat"}, graph.Node{}, nil) + feat, _ := json.Marshal(builds.BuildEnded{Module: "mail", Fingerprint: "fp-feat", Made: map[string]string{"program": "sha256:4"}, KeptOn: "g14"}) + if err := w.ends.put(feat); err != nil { + t.Fatal(err) + } + p.ends = newPipelineEnds(newMemEnds(), func() {}, t.Logf) + p.ends.trunk = w.trunkName + p.ends.on.Store(true) + onFeat := &mma.Assignments{Node: "g14", Modules: []mma.PlacedModule{{Module: "mail", Branch: "feat"}}} + if got, want := p.candidateOf("p2", "g14", onFeat, nil).Added, map[string]mma.AddedModule{"mail": {Parts: map[string]string{"mail:program": "sha256:4"}}}; !reflect.DeepEqual(got, want) { + t.Errorf("a placement on branch feat adds %+v, want %+v", got, want) + } }