Skip to content

Commit df70856

Browse files
authored
Merge pull request #181 from pohanhuangtw/test/add-e2e-framework
feat: add e2e test for sbombastic
2 parents 5410b9f + 0efd4b0 commit df70856

10 files changed

Lines changed: 240 additions & 10 deletions

File tree

.dockerignore

Lines changed: 6 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,6 @@
1+
bin/
2+
coverage/
3+
docs/
4+
examples/
5+
helm/
6+
test/

.github/workflows/e2e.yml

Lines changed: 15 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,15 @@
1+
name: E2E test
2+
3+
on:
4+
pull_request:
5+
6+
jobs:
7+
test:
8+
name: Run E2E tests
9+
runs-on: ubuntu-latest
10+
steps:
11+
- uses: actions/checkout@11bd71901bbe5b1630ceea73d27597364c9af683 # v4.2.2
12+
- uses: actions/setup-go@0aaccfd150d50ccaeb58ebd88d36e91967a5f35b # v5.4.0
13+
with:
14+
go-version: "1.24.1"
15+
- run: make test-e2e

Makefile

Lines changed: 43 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -5,8 +5,14 @@ ENVTEST_K8S_VERSION := 1.31.0
55
CONTROLLER_GEN ?= go run sigs.k8s.io/controller-tools/cmd/controller-gen@$(CONTROLLER_TOOLS_VERSION)
66
ENVTEST ?= go run sigs.k8s.io/controller-runtime/tools/setup-envtest@$(ENVTEST_VERSION)
77

8+
GO_MOD_SRCS := go.mod go.sum
9+
810
ENVTEST_DIR ?= $(shell pwd)/.envtest
911

12+
REGISTRY ?= ghcr.io
13+
REPO ?= rancher-sandbox/sbombastic
14+
TAG ?= latest
15+
1016
.PHONY: all
1117
all: controller storage worker
1218

@@ -18,6 +24,10 @@ test: vet ## Run tests.
1824
helm-unittest:
1925
helm unittest helm/ --file "tests/**/*_test.yaml"
2026

27+
.PHONY: test-e2e
28+
test-e2e: controller-image storage-image worker-image
29+
go test ./test/e2e/ -v
30+
2131
.PHONY: fmt
2232
fmt:
2333
go fmt ./...
@@ -34,18 +44,45 @@ lint-fix: golangci-lint ## Run golangci-lint linter and perform fixes
3444
vet:
3545
go vet ./...
3646

37-
.PHONY: controller
38-
controller: vet
47+
CONTROLLER_SRC_DIRS := cmd/controller api internal/controller
48+
CONTROLLER_GO_SRCS := $(shell find $(CONTROLLER_SRC_DIRS) -type f -name '*.go')
49+
CONTROLLER_SRCS := $(GO_MOD_SRCS) $(CONTROLLER_GO_SRCS)
50+
.PHONY: controller
51+
controller: $(CONTROLLER_SRCS) vet
3952
CGO_ENABLED=0 GOOS=linux GOARCH=amd64 go build -o ./bin/controller ./cmd/controller
4053

41-
.PHONY: storage
42-
storage: vet
43-
CGO_ENABLED=0 GOOS=linux GOARCH=amd64 go build -o ./bin/storage ./cmd/storage
54+
.PHONY: controller-image
55+
controller-image:
56+
docker build -f ./Dockerfile.controller \
57+
-t "$(REGISTRY)/$(REPO)/controller:$(TAG)" .
58+
@echo "Built $(REGISTRY)/$(REPO)/controller:$(TAG)"
4459

60+
STORAGE_SRC_DIRS := cmd/storage api internal/apiserver internal/storage pkg
61+
STORAGE_GO_SRCS := $(shell find $(STORAGE_SRC_DIRS) -type f -name '*.go')
62+
STORAGE_SRCS := $(GO_MOD_SRCS) $(STORAGE_GO_SRCS)
63+
.PHONY: storage
64+
storage: $(STORAGE_SRCS) vet
65+
CGO_ENABLED=0 GOOS=linux GOARCH=amd64 go build -o ./bin/storage ./cmd/storage
66+
67+
.PHONY: storage-image
68+
storage-image:
69+
docker build -f ./Dockerfile.storage \
70+
-t "$(REGISTRY)/$(REPO)/storage:$(TAG)" .
71+
@echo "Built $(REGISTRY)/$(REPO)/storage:$(TAG)"
72+
73+
WORKER_SRC_DIRS := cmd/worker api internal/messaging internal/handlers
74+
WORKER_GO_SRCS := $(shell find $(WORKER_SRC_DIRS) -type f -name '*.go')
75+
WORKER_SRCS := $(GO_MOD_SRCS) $(WORKER_GO_SRCS)
4576
.PHONY: worker
46-
worker: vet
77+
worker: $(WORKER_SRCS) vet
4778
CGO_ENABLED=0 GOOS=linux GOARCH=amd64 go build -o ./bin/worker ./cmd/worker
4879

80+
.PHONY: worker-image
81+
worker-image:
82+
docker build -f ./Dockerfile.worker \
83+
-t "$(REGISTRY)/$(REPO)/worker:$(TAG)" .
84+
@echo "Built $(REGISTRY)/$(REPO)/worker:$(TAG)"
85+
4986
.PHONY: generate
5087
generate: generate-controller generate-storage generate-mocks
5188

Tiltfile

Lines changed: 1 addition & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -1,7 +1,7 @@
11
tilt_settings_file = "./tilt-settings.yaml"
22
settings = read_yaml(tilt_settings_file)
33

4-
# Setup a development registry so we can push images to it
4+
# Setup a development registry so we can push images to it
55
# and use them to test the scanner.
66
k8s_yaml('./hack/registry.yaml')
77

@@ -75,7 +75,6 @@ local_resource(
7575
"go.sum",
7676
"cmd/storage",
7777
"api",
78-
"internal/admission",
7978
"internal/apiserver",
8079
"internal/storage",
8180
"pkg"

go.mod

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -29,6 +29,7 @@ require (
2929
k8s.io/utils v0.0.0-20241104100929-3ea5e8cea738
3030
modernc.org/sqlite v1.37.0
3131
sigs.k8s.io/controller-runtime v0.20.4
32+
sigs.k8s.io/e2e-framework v0.6.0
3233
sigs.k8s.io/structured-merge-diff/v4 v4.7.0
3334
)
3435

@@ -358,6 +359,7 @@ require (
358359
github.com/twitchtv/twirp v8.1.3+incompatible // indirect
359360
github.com/ulikunitz/xz v0.5.12 // indirect
360361
github.com/vbatts/tar-split v0.11.6 // indirect
362+
github.com/vladimirvivien/gexe v0.4.1 // indirect
361363
github.com/vmihailenco/msgpack/v5 v5.4.1 // indirect
362364
github.com/vmihailenco/tagparser/v2 v2.0.0 // indirect
363365
github.com/x448/float16 v0.8.4 // indirect

go.sum

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1925,6 +1925,8 @@ github.com/ulikunitz/xz v0.5.12/go.mod h1:nbz6k7qbPmH4IRqmfOplQw/tblSgqTqBwxkY0o
19251925
github.com/urfave/cli/v2 v2.3.0/go.mod h1:LJmUH05zAU44vOAcrfzZQKsZbVcdbOG8rtL3/XcUArI=
19261926
github.com/vbatts/tar-split v0.11.6 h1:4SjTW5+PU11n6fZenf2IPoV8/tz3AaYHMWjf23envGs=
19271927
github.com/vbatts/tar-split v0.11.6/go.mod h1:dqKNtesIOr2j2Qv3W/cHjnvk9I8+G7oAkFDFN6TCBEI=
1928+
github.com/vladimirvivien/gexe v0.4.1 h1:W9gWkp8vSPjDoXDu04Yp4KljpVMaSt8IQuHswLDd5LY=
1929+
github.com/vladimirvivien/gexe v0.4.1/go.mod h1:3gjgTqE2c0VyHnU5UOIwk7gyNzZDGulPb/DJPgcw64E=
19281930
github.com/vmihailenco/msgpack/v4 v4.3.12/go.mod h1:gborTTJjAo/GWTqqRjrLCn9pgNN+NXzzngzBKDPIqw4=
19291931
github.com/vmihailenco/msgpack/v5 v5.4.1 h1:cQriyiUvjTwOHg8QZaPihLWeRAAVoCpE00IUPn0Bjt8=
19301932
github.com/vmihailenco/msgpack/v5 v5.4.1/go.mod h1:GaZTsDaehaPpQVyxrf5mtQlH+pc21PIudVV/E3rRQok=
@@ -2905,6 +2907,8 @@ sigs.k8s.io/apiserver-network-proxy/konnectivity-client v0.31.2 h1:jpcvIRr3GLoUo
29052907
sigs.k8s.io/apiserver-network-proxy/konnectivity-client v0.31.2/go.mod h1:Ve9uj1L+deCXFrPOk1LpFXqTg7LCFzFso6PA48q/XZw=
29062908
sigs.k8s.io/controller-runtime v0.20.4 h1:X3c+Odnxz+iPTRobG4tp092+CvBU9UK0t/bRf+n0DGU=
29072909
sigs.k8s.io/controller-runtime v0.20.4/go.mod h1:xg2XB0K5ShQzAgsoujxuKN4LNXR2LfwwHsPj7Iaw+XY=
2910+
sigs.k8s.io/e2e-framework v0.6.0 h1:p7hFzHnLKO7eNsWGI2AbC1Mo2IYxidg49BiT4njxkrM=
2911+
sigs.k8s.io/e2e-framework v0.6.0/go.mod h1:IREnCHnKgRCioLRmNi0hxSJ1kJ+aAdjEKK/gokcZu4k=
29082912
sigs.k8s.io/json v0.0.0-20241010143419-9aa6b5e7a4b3 h1:/Rv+M11QRah1itp8VhT6HoVx1Ray9eB4DBr+K+/sCJ8=
29092913
sigs.k8s.io/json v0.0.0-20241010143419-9aa6b5e7a4b3/go.mod h1:18nIHnGi6636UCz6m8i4DhaJ65T6EruyzmoQqI2BVDo=
29102914
sigs.k8s.io/kustomize/api v0.19.0 h1:F+2HB2mU1MSiR9Hp1NEgoU2q9ItNOaBJl0I4Dlus5SQ=

helm/templates/storage/deployment.yaml

Lines changed: 6 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -22,15 +22,20 @@ spec:
2222
containers:
2323
- name: storage
2424
image: {{ .Values.storage.image.repository }}:{{ .Values.storage.image.tag }}
25-
{{- if .Values.storage.logLevel }}
2625
args:
26+
- --cert-dir=/certs
27+
{{- if .Values.storage.logLevel }}
2728
- -log-level={{ .Values.storage.logLevel }}
2829
{{- end }}
2930
imagePullPolicy: {{ .Values.storage.image.pullPolicy }}
3031
volumeMounts:
3132
- name: sqlite-pvc
3233
mountPath: /data/sqlite/
34+
- name: cert-volume
35+
mountPath: /certs
3336
volumes:
3437
- name: sqlite-pvc
3538
persistentVolumeClaim:
3639
claimName: {{ if .Values.persistence.storageData.existingClaim }}{{ .Values.persistence.storageData.existingClaim }}{{- else }}{{ template "sbombastic.fullname" . }}-storage-data{{- end }}
40+
- name: cert-volume
41+
emptyDir: {}

helm/values.yaml

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -8,7 +8,7 @@ controller:
88
tag: v0.1.0-alpha1
99
pullPolicy: IfNotPresent
1010
replicas: 3
11-
logLevel: "info"
11+
logLevel: "info"
1212

1313
storage:
1414
image:

test/e2e/e2e_suite_test.go

Lines changed: 121 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,121 @@
1+
package e2e
2+
3+
import (
4+
"context"
5+
"testing"
6+
7+
"github.com/stretchr/testify/assert"
8+
"github.com/stretchr/testify/require"
9+
metav1 "k8s.io/apimachinery/pkg/apis/meta/v1"
10+
"sigs.k8s.io/e2e-framework/klient/wait"
11+
"sigs.k8s.io/e2e-framework/klient/wait/conditions"
12+
"sigs.k8s.io/e2e-framework/pkg/envconf"
13+
"sigs.k8s.io/e2e-framework/pkg/features"
14+
"sigs.k8s.io/e2e-framework/third_party/helm"
15+
16+
storagev1alpha1 "github.com/rancher/sbombastic/api/storage/v1alpha1"
17+
v1alpha1 "github.com/rancher/sbombastic/api/v1alpha1"
18+
)
19+
20+
func EqualReference(img storagev1alpha1.ImageMetadata, registryURI, registryRepository, tag string) bool {
21+
return img.RegistryURI == registryURI &&
22+
img.Repository == registryRepository &&
23+
img.Tag == tag
24+
}
25+
26+
func TestRegistryCreation(t *testing.T) {
27+
releaseName := "sbombastic"
28+
registryName := "test-registry"
29+
registryURI := "ghcr.io"
30+
registryRepository := "rancher-sandbox/sbombastic/test-assets/golang"
31+
32+
crName := "dfe56d8371e7df15a3dde25c33a78b84b79766de2ab5a5897032019c878b5932"
33+
34+
f := features.New("Start Registry CR Creation test").
35+
Setup(func(ctx context.Context, t *testing.T, cfg *envconf.Config) context.Context {
36+
manager := helm.New(cfg.KubeconfigFile())
37+
err := manager.RunInstall(helm.WithName(releaseName),
38+
helm.WithNamespace(cfg.Namespace()),
39+
helm.WithChart("../../helm"),
40+
helm.WithWait(),
41+
helm.WithArgs("--set", "controller.image.tag=latest",
42+
"--set", "storage.image.tag=latest",
43+
"--set", "worker.image.tag=latest"),
44+
helm.WithTimeout("3m"))
45+
46+
require.NoError(t, err, "sbombastic helm chart is not installed correctly")
47+
48+
err = storagev1alpha1.AddToScheme(cfg.Client().Resources(cfg.Namespace()).GetScheme())
49+
require.NoError(t, err)
50+
51+
err = v1alpha1.AddToScheme(cfg.Client().Resources(cfg.Namespace()).GetScheme())
52+
require.NoError(t, err)
53+
54+
return ctx
55+
}).
56+
Assess("Create Registry CR", func(ctx context.Context, t *testing.T, cfg *envconf.Config) context.Context {
57+
registry := &v1alpha1.Registry{
58+
ObjectMeta: metav1.ObjectMeta{
59+
Name: registryName,
60+
Namespace: cfg.Namespace(),
61+
},
62+
Spec: v1alpha1.RegistrySpec{
63+
URI: registryURI,
64+
Repositories: []string{registryRepository},
65+
},
66+
}
67+
err := cfg.Client().Resources().Create(ctx, registry)
68+
require.NoError(t, err)
69+
return ctx
70+
}).
71+
Assess("Verify the Image is created", func(ctx context.Context, t *testing.T, cfg *envconf.Config) context.Context {
72+
images := storagev1alpha1.ImageList{
73+
Items: []storagev1alpha1.Image{
74+
{ObjectMeta: metav1.ObjectMeta{Name: crName, Namespace: cfg.Namespace()}},
75+
},
76+
}
77+
78+
err := wait.For(conditions.New(cfg.Client().Resources()).ResourcesFound(&images))
79+
if err != nil {
80+
t.Error(err)
81+
}
82+
return ctx
83+
}).
84+
Assess("Verify the SPDX SBOM is created", func(ctx context.Context, t *testing.T, cfg *envconf.Config) context.Context {
85+
sboms := storagev1alpha1.SBOMList{
86+
Items: []storagev1alpha1.SBOM{
87+
{ObjectMeta: metav1.ObjectMeta{Name: crName, Namespace: cfg.Namespace()}},
88+
},
89+
}
90+
91+
err := wait.For(conditions.New(cfg.Client().Resources()).ResourcesFound(&sboms))
92+
if err != nil {
93+
t.Error(err)
94+
}
95+
return ctx
96+
}).
97+
Assess("Verify the VulnerabilityReport is created", func(ctx context.Context, t *testing.T, cfg *envconf.Config) context.Context {
98+
vulnReports := storagev1alpha1.VulnerabilityReportList{
99+
Items: []storagev1alpha1.VulnerabilityReport{
100+
{ObjectMeta: metav1.ObjectMeta{Name: crName, Namespace: cfg.Namespace()}},
101+
},
102+
}
103+
104+
err := wait.For(conditions.New(cfg.Client().Resources()).ResourcesFound(&vulnReports))
105+
if err != nil {
106+
t.Error(err)
107+
}
108+
return ctx
109+
}).
110+
Teardown(func(ctx context.Context, t *testing.T, cfg *envconf.Config) context.Context {
111+
manager := helm.New(cfg.KubeconfigFile())
112+
err := manager.RunUninstall(
113+
helm.WithName(releaseName),
114+
helm.WithNamespace(cfg.Namespace()),
115+
)
116+
assert.NoError(t, err, "sbombastic helm chart is not deleted correctly")
117+
return ctx
118+
})
119+
120+
testenv.Test(t, f.Feature())
121+
}

test/e2e/main_test.go

Lines changed: 41 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,41 @@
1+
package e2e
2+
3+
import (
4+
"os"
5+
"testing"
6+
7+
"sigs.k8s.io/e2e-framework/pkg/env"
8+
"sigs.k8s.io/e2e-framework/pkg/envconf"
9+
"sigs.k8s.io/e2e-framework/pkg/envfuncs"
10+
"sigs.k8s.io/e2e-framework/support/kind"
11+
)
12+
13+
var (
14+
testenv env.Environment
15+
kindClusterName string
16+
namespace string
17+
workerImage = "ghcr.io/rancher-sandbox/sbombastic/worker:latest"
18+
controllerImage = "ghcr.io/rancher-sandbox/sbombastic/controller:latest"
19+
storageImage = "ghcr.io/rancher-sandbox/sbombastic/storage:latest"
20+
)
21+
22+
func TestMain(m *testing.M) {
23+
cfg, _ := envconf.NewFromFlags()
24+
testenv = env.NewWithConfig(cfg)
25+
namespace = envconf.RandomName("sbombastic-e2e-ns", 32)
26+
kindClusterName = envconf.RandomName("sbombastic-e2e-cluster", 32)
27+
28+
testenv.Setup(
29+
envfuncs.CreateCluster(kind.NewProvider(), kindClusterName),
30+
envfuncs.CreateNamespace(namespace),
31+
envfuncs.LoadImageToCluster(kindClusterName, workerImage, "--verbose", "--mode", "direct"),
32+
envfuncs.LoadImageToCluster(kindClusterName, controllerImage, "--verbose", "--mode", "direct"),
33+
envfuncs.LoadImageToCluster(kindClusterName, storageImage, "--verbose", "--mode", "direct"),
34+
)
35+
36+
testenv.Finish(
37+
envfuncs.DestroyCluster(kindClusterName),
38+
)
39+
40+
os.Exit(testenv.Run(m))
41+
}

0 commit comments

Comments
 (0)