Test that declarationWith sets modules and builds for a node that reads them (issue 1145); the Approve of a head it did not cover refuses a new module, heads keyed by the repository (issue 1146)
This commit is contained in:
@@ -0,0 +1,91 @@
|
||||
//go:build integration
|
||||
|
||||
package main
|
||||
|
||||
import (
|
||||
"encoding/json"
|
||||
"strings"
|
||||
"testing"
|
||||
"time"
|
||||
|
||||
"github.com/novox/mesh-controller/internal/link"
|
||||
)
|
||||
|
||||
// 1145/AC1 on a store: declarationWith itself sets the module of each resource and the build of each module for a
|
||||
// node recorded as reading them, and for no other. Skips without a store.
|
||||
func TestAComposedDeclarationCarriesModulesAndBuildsOnlyForANodeThatReadsThem(t *testing.T) {
|
||||
open := aMesh(t)
|
||||
ctx := t.Context()
|
||||
inv := open.inventory
|
||||
start := time.Now().Add(-time.Hour)
|
||||
manifest := resticFixture(false)
|
||||
manifest["module"], manifest["version"] = "restic", "1"
|
||||
raw, _ := json.Marshal(manifest)
|
||||
b := link.BuildResult{ID: link.NewBuildID(start), Repository: "novox/mesh-catalog", Path: "modules/restic",
|
||||
On: "anchor", Module: "restic", Commit: "c1", Manifest: raw,
|
||||
Source: &link.SourceOnSeat{Seat: "git", Repository: "novox/mesh-catalog"}}
|
||||
if _, _, err := takeIn(ctx, inv, asTheOperator(t, inv, b)); err != nil {
|
||||
t.Fatal(err)
|
||||
}
|
||||
for _, n := range []string{"anchor", "laptop"} {
|
||||
if _, err := inv.Assign(ctx, n, "restic"); err != nil {
|
||||
t.Fatal(err)
|
||||
}
|
||||
}
|
||||
anchor, err := inv.NodeByName(ctx, "anchor")
|
||||
if err != nil {
|
||||
t.Fatal(err)
|
||||
}
|
||||
if err := inv.RecordReadsModules(ctx, anchor.ID, true); err != nil {
|
||||
t.Fatal(err)
|
||||
}
|
||||
wantBuild, err := inv.BuildOf(ctx, "restic", "c1")
|
||||
if err != nil || wantBuild == "" {
|
||||
t.Fatalf("the build of restic at c1 is %q (%v)", wantBuild, err)
|
||||
}
|
||||
|
||||
declare := func(node string) sendable {
|
||||
t.Helper()
|
||||
plan, settings, err := planFor(ctx, open, node)
|
||||
if err != nil {
|
||||
t.Fatal(err)
|
||||
}
|
||||
gens, err := generators(ctx, open)
|
||||
if err != nil {
|
||||
t.Fatal(err)
|
||||
}
|
||||
d, err := declarationWith(ctx, open, node, plan, settings, gens, Allocating)
|
||||
if err != nil {
|
||||
t.Fatal(err)
|
||||
}
|
||||
return d
|
||||
}
|
||||
reads := bodyKeys(t, declare("anchor"))
|
||||
builds, _ := reads["builds"].(map[string]any)
|
||||
if builds["restic"] != wantBuild {
|
||||
t.Errorf("1145/AC1: anchor reads modules and was sent builds %v, want restic at %s", reads["builds"], wantBuild)
|
||||
}
|
||||
owned := 0
|
||||
for _, r := range reads["resources"].([]any) {
|
||||
r := r.(map[string]any)
|
||||
if strings.HasPrefix(r["id"].(string), "restic.") {
|
||||
owned++
|
||||
if r["module"] != "restic" {
|
||||
t.Errorf("1145/AC1: resource %v carries module %v, want restic", r["id"], r["module"])
|
||||
}
|
||||
}
|
||||
}
|
||||
if owned == 0 {
|
||||
t.Fatal("1145/AC1: no resource of restic was composed")
|
||||
}
|
||||
|
||||
plain := bodyKeys(t, declare("laptop"))
|
||||
if _, there := plain["builds"]; there {
|
||||
t.Errorf("1145/AC1: laptop never said it reads modules and was sent builds %v", plain["builds"])
|
||||
}
|
||||
for _, r := range plain["resources"].([]any) {
|
||||
if _, there := r.(map[string]any)["module"]; there {
|
||||
t.Fatalf("1145/AC1: laptop was sent a module on %v", r)
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -37,6 +37,24 @@ func (m *anEmptyMesh) MergeOf(context.Context, string, string) (inventory.Batche
|
||||
return m.merge, true, nil
|
||||
}
|
||||
|
||||
// aDeliveryMergeOf is the Approved merge of a pull request of novox/mesh-delivery, its heads keyed by that repository,
|
||||
// and the ask and warrant bound to exactly those heads (the digest the Approve left covers them).
|
||||
func aDeliveryMergeOf(t *testing.T, head string, covered map[string]string) anApprovedMerge {
|
||||
t.Helper()
|
||||
a := approvedMerge(t)
|
||||
a.merge.Owner, a.merge.Repo, a.merge.Number, a.merge.HeadSHA = "novox", "mesh-delivery", 7, head
|
||||
a.merge.Heads = covered
|
||||
for n := range a.ask.Options {
|
||||
d, err := asks.ActDigest(mergeAct(a.merge.AskID, a.ask.Options[n].ID, covered))
|
||||
if err != nil {
|
||||
t.Fatal(err)
|
||||
}
|
||||
a.ask.Options[n].Binds = d
|
||||
}
|
||||
a.warrant.AskDigest = a.ask.Digest()
|
||||
return a
|
||||
}
|
||||
|
||||
func TestANewModuleIsRegisteredOnTheOperatorsApproveOfItsMergeAndRefusedOtherwise(t *testing.T) {
|
||||
const commit, head = "c0ffee0123456789", "a1a1a1a1a1a1a1a1a1a1a1a1a1a1a1a1a1a1a1a1"
|
||||
built := inventory.Source{Repository: "novox/mesh-delivery", Seat: "git"}
|
||||
@@ -53,8 +71,12 @@ func TestANewModuleIsRegisteredOnTheOperatorsApproveOfItsMergeAndRefusedOtherwis
|
||||
{what: "the Approve of the merged head, a protected trunk on the forge", request: "merge", accepted: true, ac: "1146/AC1"},
|
||||
{what: "a build asked through a verb", request: "build", ac: "1146/AC2"},
|
||||
{what: "a merge with no warrant", request: "merge", unkept: true, ac: "1146/AC2"},
|
||||
{what: "a warrant of another head", request: "merge", ac: "1146/AC2", change: func(a *anApprovedMerge) {
|
||||
a.merge.Heads = map[string]string{"novox/mesh-host@aaaaaaaaaaaa": "e5e5e5e5e5e5e5e5e5e5e5e5e5e5e5e5e5e5e5e5"}
|
||||
{what: "a merged head the Approve did not cover", request: "merge", ac: "1146/AC2", change: func(a *anApprovedMerge) {
|
||||
*a = aDeliveryMergeOf(t, head, map[string]string{
|
||||
"novox/mesh-delivery@eeeeeeeeeeee": "e5e5e5e5e5e5e5e5e5e5e5e5e5e5e5e5e5e5e5e5"})
|
||||
}},
|
||||
{what: "heads other than the ones the Approve was bound to", request: "merge", ac: "1146/AC2", change: func(a *anApprovedMerge) {
|
||||
a.merge.Heads = map[string]string{"novox/mesh-delivery@eeeeeeeeeeee": "e5e5e5e5e5e5e5e5e5e5e5e5e5e5e5e5e5e5e5e5"}
|
||||
}},
|
||||
{what: "a repository not on the mesh's forge", request: "merge", ac: "1146/AC3",
|
||||
built: &inventory.Source{Repository: "http://elsewhere.example/x/y.git"}},
|
||||
@@ -62,8 +84,7 @@ func TestANewModuleIsRegisteredOnTheOperatorsApproveOfItsMergeAndRefusedOtherwis
|
||||
{what: "an unprotected trunk", request: "merge", ac: "1146/AC3", forge: forgeFacts{ID: 9, Guarded: false, Why: "direct push"}},
|
||||
} {
|
||||
t.Run(c.ac+" "+c.what, func(t *testing.T) {
|
||||
a := approvedMerge(t)
|
||||
a.merge.Owner, a.merge.Repo, a.merge.Number, a.merge.HeadSHA = "novox", "mesh-delivery", 7, head
|
||||
a := aDeliveryMergeOf(t, head, map[string]string{"novox/mesh-delivery@a1a1a1a1a1a1": head})
|
||||
if c.change != nil {
|
||||
c.change(&a)
|
||||
}
|
||||
|
||||
@@ -65,8 +65,8 @@ func TestANewModuleFromANewRepositoryIsRegisteredOnlyOnTheOperatorsApproveOnTheB
|
||||
t.Fatal(err)
|
||||
}
|
||||
|
||||
a := approvedMerge(t)
|
||||
a.merge.Owner, a.merge.Repo, a.merge.Number = "novox", "mesh-delivery", 7
|
||||
a := aDeliveryMergeOf(t, "a1a1a1a1a1a1a1a1a1a1a1a1a1a1a1a1a1a1a1a1",
|
||||
map[string]string{"novox/mesh-delivery@a1a1a1a1a1a1": "a1a1a1a1a1a1a1a1a1a1a1a1a1a1a1a1a1a1a1a1"})
|
||||
if c.answer {
|
||||
record, _ := json.Marshal(map[string]any{"state": "closed", "ask": a.ask, "warrant": a.warrant})
|
||||
if _, err := records.Put(ctx, theDelivery+"."+a.merge.AskID, record); err != nil {
|
||||
|
||||
Reference in New Issue
Block a user