126 lines
3.4 KiB
Go
126 lines
3.4 KiB
Go
package config
|
|
|
|
import (
|
|
"os"
|
|
"path/filepath"
|
|
"testing"
|
|
)
|
|
|
|
// writeConfig writes a temp config file and returns its path.
|
|
func writeConfig(t *testing.T, content string) string {
|
|
t.Helper()
|
|
name := filepath.Join(t.TempDir(), "config.yaml")
|
|
if err := os.WriteFile(name, []byte(content), 0644); err != nil {
|
|
t.Fatal(err)
|
|
}
|
|
return name
|
|
}
|
|
|
|
// TestInitExample verifies the shipped example configuration is valid.
|
|
func TestInitExample(t *testing.T) {
|
|
if err := Init("../config.example.yaml"); err != nil {
|
|
t.Fatal(err)
|
|
}
|
|
if _, ok := C.Load().Domain("mirror.example.com:443"); !ok {
|
|
t.Error("online domain not resolvable with a port")
|
|
}
|
|
if C.Load().OnlineDomain().Domain != "mirror.example.com" {
|
|
t.Errorf("online domain = %q", C.Load().OnlineDomain().Domain)
|
|
}
|
|
mount, ok := C.Load().MountFor("/almalinux/9/BaseOS/x86_64/os")
|
|
if !ok || mount.Path != "/almalinux" {
|
|
t.Errorf("mount = %+v, %v", mount, ok)
|
|
}
|
|
}
|
|
|
|
// TestStatePathDefault verifies an unset state path lands next to the
|
|
// config file.
|
|
func TestStatePathDefault(t *testing.T) {
|
|
path := writeConfig(t, `
|
|
domains:
|
|
- {domain: m.test, role: online, root: /tmp/online}
|
|
mounts:
|
|
- {path: /, upstream: "https://example.com"}
|
|
`)
|
|
if err := Init(path); err != nil {
|
|
t.Fatal(err)
|
|
}
|
|
want := filepath.Join(filepath.Dir(path), "state.yaml")
|
|
if C.Load().StatePath != want {
|
|
t.Errorf("StatePath = %q, want %q", C.Load().StatePath, want)
|
|
}
|
|
}
|
|
|
|
// TestMountLongestPrefix verifies the most specific mount wins.
|
|
func TestMountLongestPrefix(t *testing.T) {
|
|
path := writeConfig(t, `
|
|
state_path: /tmp/state.yaml
|
|
domains:
|
|
- {domain: m.test, role: online, root: /tmp/online}
|
|
mounts:
|
|
- {path: /, upstream: "https://fallback.example.com"}
|
|
- {path: /centos, upstream: "https://centos.example.com"}
|
|
- {path: /centos/vault, upstream: "https://vault.example.com"}
|
|
`)
|
|
if err := Init(path); err != nil {
|
|
t.Fatal(err)
|
|
}
|
|
cases := map[string]string{
|
|
"/centos/vault/7/os": "https://vault.example.com",
|
|
"/centos/8/BaseOS": "https://centos.example.com",
|
|
"/debian/dists/testy": "https://fallback.example.com",
|
|
}
|
|
for reqPath, want := range cases {
|
|
mount, ok := C.Load().MountFor(reqPath)
|
|
if !ok || mount.Upstream != want {
|
|
t.Errorf("MountFor(%q) = %q, want %q", reqPath, mount.Upstream, want)
|
|
}
|
|
}
|
|
}
|
|
|
|
// TestInitRejections verifies invalid configurations fail with clear
|
|
// errors.
|
|
func TestInitRejections(t *testing.T) {
|
|
cases := map[string]string{
|
|
"two online domains": `
|
|
state_path: /tmp/state.yaml
|
|
domains:
|
|
- {domain: a.test, role: online, root: /tmp/a}
|
|
- {domain: b.test, role: online, root: /tmp/b}
|
|
mounts:
|
|
- {path: /, upstream: "https://example.com"}
|
|
`,
|
|
"no online domain": `
|
|
state_path: /tmp/state.yaml
|
|
domains:
|
|
- {domain: a.test, role: offline, root: /tmp/a}
|
|
mounts:
|
|
- {path: /, upstream: "https://example.com"}
|
|
`,
|
|
"repo outside mount": `
|
|
state_path: /tmp/state.yaml
|
|
domains:
|
|
- {domain: a.test, role: online, root: /tmp/a}
|
|
mounts:
|
|
- path: /centos
|
|
upstream: "https://example.com"
|
|
repos:
|
|
- {path: /debian/dists/x, type: deb}
|
|
`,
|
|
"bad repo type": `
|
|
state_path: /tmp/state.yaml
|
|
domains:
|
|
- {domain: a.test, role: online, root: /tmp/a}
|
|
mounts:
|
|
- path: /centos
|
|
upstream: "https://example.com"
|
|
repos:
|
|
- {path: /centos/7/os, type: gentoo}
|
|
`,
|
|
}
|
|
for name, content := range cases {
|
|
if err := Init(writeConfig(t, content)); err == nil {
|
|
t.Errorf("%s: configuration unexpectedly accepted", name)
|
|
}
|
|
}
|
|
}
|