From 2919cb5a92c0043634c8924e3840333b1bc77d39 Mon Sep 17 00:00:00 2001 From: Nico Braun Date: Sun, 14 Apr 2024 22:18:55 +0200 Subject: [PATCH] test: add starlark decoder tests Signed-off-by: Nico Braun --- krm/filter.go | 4 +- plugin/builtin/starlark/decoder.lines@v1.star | 3 +- plugin/decoder_test.go | 94 +++++++++++++++++++ plugin/testdata/distribution.json | 19 ++++ plugin/testdata/dockerhub.json | 25 +++++ plugin/testdata/harbor.json | 21 +++++ plugin/testdata/lines.txt | 1 + 7 files changed, 164 insertions(+), 3 deletions(-) create mode 100644 plugin/decoder_test.go create mode 100644 plugin/testdata/distribution.json create mode 100644 plugin/testdata/dockerhub.json create mode 100644 plugin/testdata/harbor.json create mode 100644 plugin/testdata/lines.txt diff --git a/krm/filter.go b/krm/filter.go index 57cab19..32b0eec 100644 --- a/krm/filter.go +++ b/krm/filter.go @@ -18,7 +18,7 @@ func DefaultNodeHandler(_, currentRef, nextRef string, opts Options) (string, er return currentRef, err } - newRef, _, err := parseImageRefWithDigest(nextRef) + newRef, _, err := ParseImageRefWithDigest(nextRef) if err != nil { return currentRef, err } @@ -104,7 +104,7 @@ func (i *ImageRefUpdateFilter) Filter(nodes []*yaml.RNode) ([]*yaml.RNode, error return nodes, err } -func parseImageRefWithDigest(s string) (name.Reference, string, error) { +func ParseImageRefWithDigest(s string) (name.Reference, string, error) { rawRef, digest, _ := strings.Cut(s, "@") // NOTE: not checking ok here, to allow the user to use refs without digest // it is up to them to decide if that is acceptable or not. diff --git a/plugin/builtin/starlark/decoder.lines@v1.star b/plugin/builtin/starlark/decoder.lines@v1.star index c085397..d0dbb88 100644 --- a/plugin/builtin/starlark/decoder.lines@v1.star +++ b/plugin/builtin/starlark/decoder.lines@v1.star @@ -1,2 +1,3 @@ def main(input): - return input.split("\n") + return [x for x in input.split("\n") if x != ""] + diff --git a/plugin/decoder_test.go b/plugin/decoder_test.go new file mode 100644 index 0000000..df9e62e --- /dev/null +++ b/plugin/decoder_test.go @@ -0,0 +1,94 @@ +package plugin + +import ( + "os" + "testing" + + "github.com/bluebrown/kobold/krm" + "github.com/bluebrown/kobold/plugin/builtin" +) + +func TestDecoder(t *testing.T) { + testCases := []struct { + name string + decoder string + giveFile string + wantName string + wantTag string + wantDigest string + }{ + { + name: "lines", + decoder: "decoder.lines@v1", + giveFile: "testdata/lines.txt", + wantName: "index.docker.io/bluebrown/busybox", + wantTag: "v1.1", + wantDigest: "sha256:3b3128d9df6bbbcc92e2358e596c9fbd722a437a62bafbc51607970e9e3b8869", + }, + { + name: "distribution", + decoder: "decoder.distribution@v1", + giveFile: "testdata/distribution.json", + wantName: "test.azurecr.io/busybox", + wantTag: "v1", + wantDigest: "sha256:xxxxd5c8786bb9e621a45ece0dbxxxx1cdc624ad20da9fe62e9d25490f33xxxx", + }, + { + name: "dockerhub", + decoder: "decoder.dockerhub@v1", + giveFile: "testdata/dockerhub.json", + wantName: "index.docker.io/svendowideit/testhook", + wantTag: "stable", + }, + { + name: "harbor", + decoder: "decoder.harbor@v1", + giveFile: "testdata/harbor.json", + wantName: "ghcr.io/bluebrown/busybox", + wantTag: "v1.4", + wantDigest: "sha256:3b3128d9df6bbbcc92e2358e596c9fbd722a437a62bafbc51607970e9e3b8869", + }, + } + for _, tc := range testCases { + t.Run(tc.name, func(t *testing.T) { + + dec := NewDecoderRunner() + + sb, err := builtin.StarlarkScripts.ReadFile("starlark/" + tc.decoder + ".star") + if err != nil { + t.Fatal(err) + } + + fb, err := os.ReadFile(tc.giveFile) + if err != nil { + t.Fatal(err) + } + + refs, err := dec.Decode(tc.decoder, sb, fb) + if err != nil { + t.Fatal(err) + } + + if len(refs) != 1 { + t.Errorf("ref mismatch, got %v, want %v", len(refs), 1) + } + + tag, digest, err := krm.ParseImageRefWithDigest(refs[0]) + if err != nil { + t.Fatalf("failed to parse image ref: %v", err) + } + + if tag.Context().String() != tc.wantName { + t.Errorf("got %v, want %v", tag.Context().String(), tc.wantName) + } + + if tag.Identifier() != tc.wantTag { + t.Errorf("got %v, want %v", tag.Identifier(), tc.wantTag) + } + + if digest != tc.wantDigest { + t.Errorf("got %v, want %v", digest, tc.wantDigest) + } + }) + } +} diff --git a/plugin/testdata/distribution.json b/plugin/testdata/distribution.json new file mode 100644 index 0000000..afb9ed5 --- /dev/null +++ b/plugin/testdata/distribution.json @@ -0,0 +1,19 @@ +{ + "action": "push", + "id": "9a5f8995-dbab-4c2b-b06c-0c29c23e759e", + "request": { + "host": "test.azurecr.io", + "id": "ae93b7e8-7e96-4e21-8487-917d74224d92", + "method": "PUT", + "useragent": "docker/24.0.6 go/go1.20.7 git-commit/1a79695 kernel/5.10.0-25-amd64 os/linux arch/amd64 UpstreamClient(Docker-Client/24.0.6 \\(linux\\))" + }, + "target": { + "digest": "sha256:xxxxd5c8786bb9e621a45ece0dbxxxx1cdc624ad20da9fe62e9d25490f33xxxx", + "length": 524, + "mediaType": "application/vnd.docker.distribution.manifest.v2+json", + "repository": "busybox", + "size": 524, + "tag": "v1" + }, + "timestamp": "2023-10-11T14:45:59.730519823Z" +} diff --git a/plugin/testdata/dockerhub.json b/plugin/testdata/dockerhub.json new file mode 100644 index 0000000..f4f2afb --- /dev/null +++ b/plugin/testdata/dockerhub.json @@ -0,0 +1,25 @@ +{ + "callback_url": "https://registry.hub.docker.com/u/svendowideit/testhook/hook/2141b5bi5i5b02bec211i4eeih0242eg11000a/", + "push_data": { + "pushed_at": 1417566161, + "pusher": "trustedbuilder", + "tag": "stable" + }, + "repository": { + "comment_count": 0, + "date_created": 1417494799, + "description": "", + "dockerfile": "#\n# BUILD\u0009\u0009docker build -t svendowideit/apt-cacher .\n# RUN\u0009\u0009docker run -d -p 3142:3142 -name apt-cacher-run apt-cacher\n#\n# and then you can run containers with:\n# \u0009\u0009docker run -t -i -rm -e http_proxy http://192.168.1.2:3142/ debian bash\n#\nFROM\u0009\u0009ubuntu\n\n\nVOLUME\u0009\u0009[/var/cache/apt-cacher-ng]\nRUN\u0009\u0009apt-get update ; apt-get install -yq apt-cacher-ng\n\nEXPOSE \u0009\u00093142\nCMD\u0009\u0009chmod 777 /var/cache/apt-cacher-ng ; /etc/init.d/apt-cacher-ng start ; tail -f /var/log/apt-cacher-ng/*\n", + "full_description": "Docker Hub based automated build from a GitHub repo", + "is_official": false, + "is_private": true, + "is_trusted": true, + "name": "testhook", + "namespace": "svendowideit", + "owner": "svendowideit", + "repo_name": "svendowideit/testhook", + "repo_url": "https://registry.hub.docker.com/u/svendowideit/testhook/", + "star_count": 0, + "status": "Active" + } +} diff --git a/plugin/testdata/harbor.json b/plugin/testdata/harbor.json new file mode 100644 index 0000000..f237112 --- /dev/null +++ b/plugin/testdata/harbor.json @@ -0,0 +1,21 @@ +{ + "type": "PUSH_ARTIFACT", + "occur_at": 1680501893, + "operator": "harbor-jobservice", + "event_data": { + "resources": [ + { + "digest": "sha256:954b378c375d852eb3c63ab88978f640b4348b01c1b3456a024a81536dafbbf4", + "tag": "sha256:954b378c375d852eb3c63ab88978f640b4348b01c1b3456a024a81536dafbbf4", + "resource_url": "localhost/harbor/alpine@sha256:954b378c375d852eb3c63ab88978f640b4348b01c1b3456a024a81536dafbbf4" + } + ], + "repository": { + "date_created": 1680501893, + "name": "alpine", + "namespace": "harbor", + "repo_full_name": "harbor/alpine", + "repo_type": "private" + } + } +} diff --git a/plugin/testdata/lines.txt b/plugin/testdata/lines.txt new file mode 100644 index 0000000..558880a --- /dev/null +++ b/plugin/testdata/lines.txt @@ -0,0 +1 @@ +docker.io/bluebrown/busybox:v1.1@sha256:3b3128d9df6bbbcc92e2358e596c9fbd722a437a62bafbc51607970e9e3b8869