92 lines
3.8 KiB
Go
92 lines
3.8 KiB
Go
package bundle
|
|
|
|
import (
|
|
"archive/zip"
|
|
"bytes"
|
|
"encoding/json"
|
|
"os"
|
|
"path/filepath"
|
|
"strings"
|
|
"testing"
|
|
)
|
|
|
|
const examples = "../../../contract/examples/bundles"
|
|
|
|
func TestReadExamples(t *testing.T) {
|
|
entries, err := os.ReadDir(examples)
|
|
if err != nil {
|
|
t.Fatal(err)
|
|
}
|
|
for _, e := range entries {
|
|
if _, err := Read(filepath.Join(examples, e.Name())); err != nil {
|
|
t.Errorf("%s: %v", e.Name(), err)
|
|
}
|
|
}
|
|
}
|
|
|
|
func zipWith(t *testing.T, instructions map[string]any, files map[string]string) []byte {
|
|
t.Helper()
|
|
var buffer bytes.Buffer
|
|
z := zip.NewWriter(&buffer)
|
|
raw, _ := json.Marshal(instructions)
|
|
files[InstructionsFile] = string(raw)
|
|
for name, content := range files {
|
|
w, _ := z.Create(name)
|
|
w.Write([]byte(content))
|
|
}
|
|
z.Close()
|
|
return buffer.Bytes()
|
|
}
|
|
|
|
func instructions(ops ...map[string]any) map[string]any {
|
|
return map[string]any{"format": 1, "generated": "2026-10-18T12:00:00Z", "tools": []string{"claude"},
|
|
"packages": []any{}, "operations": ops, "hints": []any{}}
|
|
}
|
|
|
|
func install(pkg, version, path, source, sha string) map[string]any {
|
|
return map[string]any{"op": "install", "package": pkg, "version": version, "checksum": sha, "runtime": "python",
|
|
"entry": "x", "files": []any{map[string]any{"path": path, "source": source, "sha256": sha}}}
|
|
}
|
|
|
|
func TestInvalidBundles(t *testing.T) {
|
|
content := "x"
|
|
sha := Sha256([]byte(content))
|
|
tests := []struct {
|
|
name string
|
|
zip []byte
|
|
message string
|
|
}{
|
|
{"Pfad nach draußen", zipWith(t, instructions(map[string]any{"op": "file", "package": "pub-x",
|
|
"path": "../x", "source": "files/x", "sha256": sha}), map[string]string{"files/x": content}), "Segment"},
|
|
{"absoluter Pfad", zipWith(t, instructions(map[string]any{"op": "remove", "package": "pub-x",
|
|
"path": "/etc/passwd"}), map[string]string{}), "relative"},
|
|
{"Windows-Pfad", zipWith(t, instructions(map[string]any{"op": "remove", "package": "pub-x",
|
|
"path": `C:\x`}), map[string]string{}), "relative"},
|
|
{"falsche Prüfsumme", zipWith(t, instructions(map[string]any{"op": "file", "package": "pub-x",
|
|
"path": "x", "source": "files/x", "sha256": Sha256([]byte("y"))}), map[string]string{"files/x": content}), "Prüfsumme"},
|
|
{"Quelle fehlt", zipWith(t, instructions(map[string]any{"op": "file", "package": "pub-x",
|
|
"path": "x", "source": "files/x", "sha256": sha}), map[string]string{}), "fehlt"},
|
|
{"Quelle außerhalb files/", zipWith(t, instructions(map[string]any{"op": "file", "package": "pub-x",
|
|
"path": "x", "source": "x", "sha256": sha}), map[string]string{"x": content}), "files/"},
|
|
{"unbekannte Operation", zipWith(t, instructions(map[string]any{"op": "ausfuehren"}), map[string]string{}), "unbekannte"},
|
|
{"lokaler Server: Paket als Pfad", zipWith(t, instructions(install("../x", "1.0.0", "x", "local/../x/1.0.0/x", sha)),
|
|
map[string]string{}), "ungültiges Paket"},
|
|
{"lokaler Server: Version als Pfad", zipWith(t, instructions(install("pub-x", "..", "x", "local/pub-x/../x", sha)),
|
|
map[string]string{}), "ungültiges Paket"},
|
|
{"lokaler Server: Datei nach draußen", zipWith(t, instructions(install("pub-x", "1.0.0", "../x", "local/pub-x/1.0.0/../x", sha)),
|
|
map[string]string{}), "Segment"},
|
|
{"lokaler Server: Quelle passt nicht", zipWith(t, instructions(install("pub-x", "1.0.0", "x", "local/pub-y/1.0.0/x", sha)),
|
|
map[string]string{"local/pub-y/1.0.0/x": content}), "passt nicht"},
|
|
{"lokaler Server: falsche Prüfsumme", zipWith(t, instructions(install("pub-x", "1.0.0", "x", "local/pub-x/1.0.0/x", Sha256([]byte("y")))),
|
|
map[string]string{"local/pub-x/1.0.0/x": content}), "Prüfsumme"},
|
|
{"neues Format", zipWith(t, map[string]any{"format": 2}, map[string]string{}), "Format"},
|
|
}
|
|
for _, tt := range tests {
|
|
t.Run(tt.name, func(t *testing.T) {
|
|
_, err := FromZip(tt.zip)
|
|
if err == nil || !strings.Contains(err.Error(), tt.message) {
|
|
t.Errorf("Fehler %v, erwartet %q", err, tt.message)
|
|
}
|
|
})
|
|
}
|
|
}
|