Skip to content

Commit

Permalink
feat: add support for "v2-archives" in "v1" format (canonical#181)
Browse files Browse the repository at this point in the history
"v2-archives" is used for backwards compatibility with Chisel <= 1.0.0
since it will be ignored. In new versions, it will be parsed with the new
fields that break said compatibility, e.g. "pro" archives.

Co-authored-by: Rafid Bin Mostofa <[email protected]>
  • Loading branch information
2 people authored and cjdcordeiro committed Dec 16, 2024
1 parent f77e94b commit 82bb84f
Show file tree
Hide file tree
Showing 4 changed files with 152 additions and 7 deletions.
109 changes: 108 additions & 1 deletion internal/setup/setup_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -1933,6 +1933,93 @@ var setupTests = []setupTest{{
`,
},
relerror: `chisel.yaml: more than one default archive: bar, foo`,
}, {
summary: "Additional v2-archives are merged with regular archives",
input: map[string]string{
"chisel.yaml": `
format: v1
archives:
ubuntu:
version: 20.04
components: [main]
suites: [focal]
priority: 10
public-keys: [test-key]
v2-archives:
fips:
version: 20.04
components: [main]
suites: [focal]
pro: fips
priority: 20
public-keys: [test-key]
public-keys:
test-key:
id: ` + testKey.ID + `
armor: |` + "\n" + testutil.PrefixEachLine(testKey.PubKeyArmor, "\t\t\t\t\t\t") + `
`,
"slices/mydir/mypkg.yaml": `
package: mypkg
`,
},
release: &setup.Release{
Archives: map[string]*setup.Archive{
"ubuntu": {
Name: "ubuntu",
Version: "20.04",
Suites: []string{"focal"},
Components: []string{"main"},
Priority: 10,
PubKeys: []*packet.PublicKey{testKey.PubKey},
},
"fips": {
Name: "fips",
Version: "20.04",
Suites: []string{"focal"},
Components: []string{"main"},
Pro: "fips",
Priority: 20,
PubKeys: []*packet.PublicKey{testKey.PubKey},
},
},
Packages: map[string]*setup.Package{
"mypkg": {
Name: "mypkg",
Path: "slices/mydir/mypkg.yaml",
Slices: map[string]*setup.Slice{},
},
},
},
}, {
summary: "Cannot define same archive name in archives and v2-archives",
input: map[string]string{
"chisel.yaml": `
format: v1
archives:
ubuntu:
version: 20.04
components: [main]
suites: [focal]
priority: 10
public-keys: [test-key]
v2-archives:
ubuntu:
version: 20.04
components: [main]
suites: [focal]
priority: 20
pro: fips
public-keys: [test-key]
public-keys:
test-key:
id: ` + testKey.ID + `
armor: |` + "\n" + testutil.PrefixEachLine(testKey.PubKeyArmor, "\t\t\t\t\t\t") + `
`,
"slices/mydir/mypkg.yaml": `
package: mypkg
`,
},
relerror: `chisel.yaml: archive "ubuntu" defined twice`,
}}

var defaultChiselYaml = `
Expand All @@ -1950,7 +2037,27 @@ var defaultChiselYaml = `
`

func (s *S) TestParseRelease(c *C) {
for _, test := range setupTests {
// Run tests for "archives" field in "v1" format.
runParseReleaseTests(c, setupTests)

// Run tests for "v2-archives" field in "v1" format.
v2ArchiveTests := make([]setupTest, 0, len(setupTests))
for _, t := range setupTests {
m := make(map[string]string)
for k, v := range t.input {
if !strings.Contains(v, "v2-archives:") {
v = strings.Replace(v, "archives:", "v2-archives:", -1)
}
m[k] = v
}
t.input = m
v2ArchiveTests = append(v2ArchiveTests, t)
}
runParseReleaseTests(c, v2ArchiveTests)
}

func runParseReleaseTests(c *C, tests []setupTest) {
for _, test := range tests {
c.Logf("Summary: %s", test.summary)

if _, ok := test.input["chisel.yaml"]; !ok {
Expand Down
26 changes: 22 additions & 4 deletions internal/setup/yaml.go
Original file line number Diff line number Diff line change
Expand Up @@ -25,6 +25,12 @@ type yamlRelease struct {
Format string `yaml:"format"`
Archives map[string]yamlArchive `yaml:"archives"`
PubKeys map[string]yamlPubKey `yaml:"public-keys"`
// "v2-archives" is used for backwards compatibility with Chisel <= 1.0.0
// since it will be ignored. In new versions, it will be parsed with the new
// fields that break said compatibility, e.g. "pro" archives.
//
// Note: "archives" and "v2-archives" are merged together while parsing.
V2Archives map[string]yamlArchive `yaml:"v2-archives"`
}

const (
Expand Down Expand Up @@ -161,7 +167,7 @@ func parseRelease(baseDir, filePath string, data []byte) (*Release, error) {
if yamlVar.Format != "v1" {
return nil, fmt.Errorf("%s: unknown format %q", fileName, yamlVar.Format)
}
if len(yamlVar.Archives) == 0 {
if len(yamlVar.Archives)+len(yamlVar.V2Archives) == 0 {
return nil, fmt.Errorf("%s: no archives defined", fileName)
}

Expand All @@ -178,12 +184,24 @@ func parseRelease(baseDir, filePath string, data []byte) (*Release, error) {
pubKeys[keyName] = key
}

// Merge all archive definitions.
yamlArchives := make(map[string]yamlArchive, len(yamlVar.Archives)+len(yamlVar.V2Archives))
for archiveName, details := range yamlVar.Archives {
yamlArchives[archiveName] = details
}
for archiveName, details := range yamlVar.V2Archives {
if _, ok := yamlArchives[archiveName]; ok {
return nil, fmt.Errorf("%s: archive %q defined twice", fileName, archiveName)
}
yamlArchives[archiveName] = details
}

// For compatibility if there is a default archive set and priorities are
// not being used, we will revert back to the default archive behaviour.
hasPriority := false
var defaultArchive string
var archiveNoPriority string
for archiveName, details := range yamlVar.Archives {
for archiveName, details := range yamlArchives {
if details.Version == "" {
return nil, fmt.Errorf("%s: archive %q missing version field", fileName, archiveName)
}
Expand Down Expand Up @@ -243,15 +261,15 @@ func parseRelease(baseDir, filePath string, data []byte) (*Release, error) {
}
}
if (hasPriority && archiveNoPriority != "") ||
(!hasPriority && defaultArchive == "" && len(yamlVar.Archives) > 1) {
(!hasPriority && defaultArchive == "" && len(yamlArchives) > 1) {
return nil, fmt.Errorf("%s: archive %q is missing the priority setting", fileName, archiveNoPriority)
}
if defaultArchive != "" && !hasPriority {
// For compatibility with the default archive behaviour we will set
// negative priorities to all but the default one, which means all
// others will be ignored unless pinned.
var archiveNames []string
for archiveName := range yamlVar.Archives {
for archiveName := range yamlArchives {
archiveNames = append(archiveNames, archiveName)
}
// Make it deterministic.
Expand Down
22 changes: 21 additions & 1 deletion internal/slicer/slicer_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -1495,7 +1495,27 @@ var defaultChiselYaml = `
`

func (s *S) TestRun(c *C) {
for _, test := range slicerTests {
// Run tests for "archives" field in "v1" format.
runSlicerTests(c, slicerTests)

// Run tests for "v2-archives" field in "v1" format.
v2ArchiveTests := make([]slicerTest, 0, len(slicerTests))
for _, t := range slicerTests {
m := make(map[string]string)
for k, v := range t.release {
if !strings.Contains(v, "v2-archives:") {
v = strings.Replace(v, "archives:", "v2-archives:", -1)
}
m[k] = v
}
t.release = m
v2ArchiveTests = append(v2ArchiveTests, t)
}
runSlicerTests(c, v2ArchiveTests)
}

func runSlicerTests(c *C, tests []slicerTest) {
for _, test := range tests {
for _, testSlices := range testutil.Permutations(test.slices) {
c.Logf("Summary: %s", test.summary)

Expand Down
2 changes: 1 addition & 1 deletion tests/pro-archives/chisel-releases/chisel.yaml
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
format: v1

archives:
v2-archives:
ubuntu:
version: 24.04
pro: esm-infra
Expand Down

0 comments on commit 82bb84f

Please sign in to comment.