forked from kubernetes-retired/hierarchical-namespaces
-
Notifications
You must be signed in to change notification settings - Fork 4
Expand file tree
/
Copy pathMakefile
More file actions
372 lines (314 loc) · 14.2 KB
/
Copy pathMakefile
File metadata and controls
372 lines (314 loc) · 14.2 KB
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
256
257
258
259
260
261
262
263
264
265
266
267
268
269
270
271
272
273
274
275
276
277
278
279
280
281
282
283
284
285
286
287
288
289
290
291
292
293
294
295
296
297
298
299
300
301
302
303
304
305
306
307
308
309
310
311
312
313
314
315
316
317
318
319
320
321
322
323
324
325
326
327
328
329
330
331
332
333
334
335
336
337
338
339
340
341
342
343
344
345
346
347
348
349
350
351
352
353
354
355
356
357
358
359
360
361
362
363
364
365
366
367
368
369
370
371
372
# Adding .PHONY to hold command shortcuts.
.PHONY: release
# If CONFIG is `kind`, various defaults will be optimized for deploying locally to Kind
CONFIG ?= default
# Set the Kind name (by default, it's "kind"). If you set this explicitly,
# CONFIG is automatically set to "kind" as well, overriding any existing
# setting.
ifeq ($(CONFIG),kind)
KIND ?= "kind"
else
KIND ?= ""
endif
ifneq ($(KIND),"")
CONFIG = kind
endif
# The image name is the *base* name - excluding the registry and the tag.
HNC_IMG_NAME ?= hnc-manager
# By default, the image tag is "latest" but you should override this when
# creating a release in the form vX.Y.Z (e.g. v0.5.1).
#
# If you're using Kind, the tag is 'kind-local' since K8s always attempts to
# re-pull an image the 'latest' tag, and this doesn't work when we're testing
# locally (we rely on the docker-push target, below, to push the image into
# Kind).
ifneq ($(CONFIG),kind)
HNC_IMG_TAG ?= latest
else
HNC_IMG_TAG ?= kind-local
endif
# HNC_IMG is the full image name. It can't be overridden in its entirety since
# parts of the Makefile and Cloud Build target make certain assumptions about
# its components.
#
# Note that if you're using Kind, this image will never actually be pushed to
# the registry.
HNC_IMG = ${HNC_IMG_NAME}:${HNC_IMG_TAG}
# Determine the OS Name, linux/darwin
OS_NAME := $(shell go env GOOS)
# `make` must be called from the HNC root, or all kinds of things will break
# (starting with this).
CURDIR = $(shell pwd)
GOBIN ?= ${CURDIR}/bin
KUSTOMIZE_VERSION ?= v5.3.0
KUSTOMIZE ?= ${GOBIN}/kustomize
CONTROLLER_GEN_VERSION ?= v0.20.0
CONTROLLER_GEN ?= ${GOBIN}/controller-gen
STATICCHECK_VERSION ?= 2023.1
STATICCHECK ?= ${GOBIN}/staticcheck
# This really could be left blank, and setup-envtest would just download the
# latest. But we may as well make it hermetic-ish by always downloading the
# same version. I doubt the version matters much (or at all).
ENVTEST_K8S_VERSION ?= 1.35.0
SETUP_ENVTEST_VERSION ?= release-0.23
SETUP_ENVTEST ?= ${GOBIN}/setup-envtest
# Get check sum value of krew archive. Note that this value is only expanded
# when the var is used.
HNC_KREW_TAR_SHA256=$(shell sha256sum bin/kubectl-hns.tar.gz | cut -d " " -f 1)
all: test docker-build
###################### LOCAL ARTIFACTS #########################
# Run tests
test: build test-only
test-only: build-setup-envtest
KUBEBUILDER_ASSETS="$(shell ${SETUP_ENVTEST} use ${ENVTEST_K8S_VERSION} --bin-dir ${CURDIR}/bin -p path)" \
go test $(shell go list ./... | grep -v '/test/e2e') -coverprofile cover.out
# Builds all binaries (manager and kubectl) and manifests
build: generate fmt vet staticcheck manifests
go build -o bin/manager ./cmd/manager/main.go
GOOS=linux GOARCH=amd64 go build \
-o bin/kubectl/kubectl-hns_linux_amd64 \
-ldflags="-X sigs.k8s.io/hierarchical-namespaces/internal/version.Version=${HNC_IMG_TAG}" \
./cmd/kubectl/main.go
GOOS=darwin GOARCH=amd64 go build \
-o bin/kubectl/kubectl-hns_darwin_amd64 \
-ldflags="-X sigs.k8s.io/hierarchical-namespaces/internal/version.Version=${HNC_IMG_TAG}" \
./cmd/kubectl/main.go
GOOS=darwin GOARCH=arm64 go build \
-o bin/kubectl/kubectl-hns_darwin_arm64 \
-ldflags="-X sigs.k8s.io/hierarchical-namespaces/internal/version.Version=${HNC_IMG_TAG}" \
./cmd/kubectl/main.go
GOOS=linux GOARCH=arm64 go build \
-o bin/kubectl/kubectl-hns_linux_arm64 \
-ldflags="-X sigs.k8s.io/hierarchical-namespaces/internal/version.Version=${HNC_IMG_TAG}" \
./cmd/kubectl/main.go
GOOS=linux GOARCH=arm go build \
-o bin/kubectl/kubectl-hns_linux_arm \
-ldflags="-X sigs.k8s.io/hierarchical-namespaces/internal/version.Version=${HNC_IMG_TAG}" \
./cmd/kubectl/main.go
GOOS=windows GOARCH=amd64 go build \
-o bin/kubectl/kubectl-hns_windows_amd64.exe \
-ldflags="-X sigs.k8s.io/hierarchical-namespaces/internal/version.Version=${HNC_IMG_TAG}" \
./cmd/kubectl/main.go
# Clean all binaries (manager and kubectl)
clean: krew-uninstall
-rm -rf bin/*
-rm -rf manifests/*
# Installs the Linux kubectl plugin to $GOPATH/bin, assume that this is in your PATH already.
kubectl: build
cp bin/kubectl/kubectl-hns_$(OS_NAME)_amd64 $(GOBIN)/kubectl-hns
# Run against the configured Kubernetes cluster in ~/.kube/config
run: build
go run ./cmd/manager/main.go --novalidation
# Generate manifests e.g. CRD, RBAC etc. This can both update the generated
# files in /config (which should be checked into Git) as well as the kustomized
# files in /manifest (which are not checked into Git).
#
# We build the full manifest last so that the kustomization.yaml file is still
# there in case you want to rerun it manually.
manifests: build-controller-gen build-kustomize
@echo "Building manifests with image ${HNC_IMG}"
@# See the comment above about the 'paths' arguments
$(CONTROLLER_GEN) crd rbac:roleName=manager-role webhook paths="./..." output:crd:artifacts:config=config/crd/bases
./hack/crd_patches/singleton-enum-patch.sh
-rm -rf manifests/
mkdir manifests
@echo "Building CRD-only manifest"
cd manifests && \
touch kustomization.yaml && \
${KUSTOMIZE} edit add resource ../config/crd
${KUSTOMIZE} build manifests/ -o manifests/crds.yaml
@cd manifests && \
for variant in default-cc default-cm nowebhooks-cc ha-webhooks-cc hrq ; do \
echo "Building $${variant} manifest"; \
rm kustomization.yaml; \
touch kustomization.yaml && \
${KUSTOMIZE} edit add resource ../config/variants/$${variant} && \
${KUSTOMIZE} edit set image controller=${HNC_IMG}; \
${KUSTOMIZE} build . -o ./$${variant}.yaml; \
done
@echo "Creating alias and summary manifests"
@cp manifests/default-cc.yaml manifests/default.yaml
@cat manifests/nowebhooks-cc.yaml > manifests/ha.yaml
@echo "---" >> manifests/ha.yaml
@cat manifests/ha-webhooks-cc.yaml >> manifests/ha.yaml
# Run go fmt against code
fmt:
@echo "Go version (for logging posterity):"
@go version
gofmt -l -w ./
# check-fmt: Checks gofmt/go fmt has been ran. gofmt -l lists files whose formatting differs from gofmt's, so it fails if there are unformatted go code.
check-fmt:
@if [ $(shell gofmt -l ./ | wc -l ) != 0 ]; then \
echo "Error: there are unformatted go code, please run 'make fmt' before committing" && exit 1; \
fi
# Run go vet against code
vet:
go vet ./...
# Run staticcheck against code
staticcheck: # build-staticcheck
@echo TODO: Skip running staticheck. We need to migrate it to golangci-lint.
# $(STATICCHECK) ./...
build-staticcheck:
GOBIN=$(GOBIN) go install honnef.co/go/tools/cmd/staticcheck@$(STATICCHECK_VERSION)
# Generate code
generate: build-controller-gen
$(CONTROLLER_GEN) object:headerFile=./hack/boilerplate.go.txt paths=./api/...
check-generate: generate
@if [ $(shell git status --untracked-files=no --porcelain | wc -l ) != 0 ]; then \
echo "Error: generated files are out of sync, please run 'make generate' before committing" && git diff && exit 1; \
fi
build-controller-gen:
GOBIN=$(GOBIN) go install sigs.k8s.io/controller-tools/cmd/controller-gen@$(CONTROLLER_GEN_VERSION)
build-setup-envtest:
GOBIN=$(GOBIN) go install sigs.k8s.io/controller-runtime/tools/setup-envtest@$(SETUP_ENVTEST_VERSION)
build-kustomize:
GOBIN=$(GOBIN) go install sigs.k8s.io/kustomize/kustomize/v5@$(KUSTOMIZE_VERSION)
###################### DEPLOYABLE ARTIFACTS AND ACTIONS #########################
# Deploy controller in the configured Kubernetes cluster in ~/.kube/config.
#
# We only delete the deployment if it exists before applying the manifest, because
# a) deleting the CRDs will cause all the existing CRs to be wiped away;
# b) if we don't delete the deployment, a new image won't be pulled unless the
# tag changes, which it frequently won't since we use the "latest" tag during
# development.
deploy: docker-push kubectl manifests
-kubectl -n hnc-system delete deployment --all
kubectl apply -f manifests/default.yaml
deploy-watch:
kubectl logs -n hnc-system --follow deployment/hnc-controller-manager manager
deploy-ha: docker-push kubectl manifests
-kubectl -n hnc-system delete deployment --all
kubectl apply -f manifests/ha.yaml
deploy-watch-ha:
kubectl logs -n hnc-system --follow deployment/hnc-controller-manager-ha manager
deploy-hrq: docker-push kubectl manifests
-kubectl -n hnc-system delete deployment --all
kubectl apply -f manifests/hrq.yaml
# No need to delete the HA configuration here - everything "extra" that it
# installs is in hnc-system, which gets deleted by the default manifest.
undeploy: manifests
@echo "********************************************************************************"
@echo "********************************************************************************"
@echo "********************************************************************************"
@echo "********************************************************************************"
@echo "This will FULLY delete HNC, including all CRDs. You have 5s to turn back"
@echo "********************************************************************************"
@echo "********************************************************************************"
@echo "********************************************************************************"
@echo "********************************************************************************"
@sleep 5
@echo "Deleting all CRDs to ensure all finalizers are removed"
-kubectl delete -f manifests/crds.yaml
@echo "Deleting the rest of HNC"
-kubectl delete -f manifests/default.yaml
@echo Please ignore any \'not found\' errors, these are expected.
# Push the docker image
docker-push: docker-build
@echo "Pushing ${HNC_IMG}"
ifeq ($(CONFIG),kind)
kind load docker-image ${HNC_IMG} --name ${KIND}
else
docker push ${HNC_IMG}
endif
# Build the docker image
docker-build: generate fmt vet staticcheck
@echo "Warning: this does not run tests. Run 'make test' to ensure tests are passing."
docker build . -t ${HNC_IMG}
buildx-setup:
## This script needs to be run to start the emulator for multiarch builds
# This driver translates the instruction set to different platforms
docker run --rm --privileged linuxkit/binfmt:v0.8
docker buildx create --use --name=qemu
docker buildx inspect --bootstrap
# Build and push multi-arch image
docker-push-multi: buildx-setup generate fmt vet staticcheck
@echo "Warning: this does not run tests. Run 'make test' to ensure tests are passing."
docker buildx build \
--platform linux/arm64,linux/amd64,linux/arm/v7 --tag ${HNC_IMG} .
###################### KIND ACTIONS #########################
# Creates a local kind cluster, destroying the old one if necessary.
kind-reboot:
@echo "Warning: the 'kind' command must be in your path for this to work"
-kind delete cluster
kind create cluster --name ${KIND}
# Creates a local kind cluster, destroying the old one if necessary. It's not
# *necessary* to call this wih CONFIG=kind but it's not a bad idea either so
# the correct manifests get created.
kind-reset: kind-reboot
@echo "If this didn't work, ensure you ran 'source devenv' to point kubectl at kind'"
# Convenience target to deploy specifically for kind
kind-deploy:
CONFIG=kind $(MAKE) deploy
###################### E2E TEST #########################
# This test will run on the current cluster the user deployed (either kind or a
# kubernetes cluster).
#
# Note the `-timeout 0` that's passed to the `go test` command - by default, a
# Go test suite has a 10m timeout, and the flag disables that timeout (as of
# July 2020, these tests take ~15m and that number is expected to grow).
#
# To focus on specific tests, use the HNC_FOCUS var as follows:
#
# HNC_FOCUS=772 make test-e2e # only runs the test for issue 772
# HNC_FOCUS=Quickstart make test-e2e # Runs all tests in the "Quickstart" Describe block
.PHONY: test-e2e
test-e2e: warn-hnc-repair
./hack/local-run-e2e.sh
# This batch test will run e2e tests N times on the current cluster the user
# deployed (either kind or a kubernetes cluster), e.g. "make test-e2e-batch N=10"
.PHONY: test-e2e-batch
test-e2e-batch: warn-hnc-repair
number=1 ; while [[ $$number -le $N ]] ; do \
echo $$number ; \
((number = number + 1)) ; \
./hack/local-run-e2e.sh
done
PHONY: test-pfnet-e2e-parallel
test-pfnet-e2e-parallel:
./hack/local-run-e2e.sh --pfnet
# This will *only* run a small number of tests (specifically, the quickstarts). You can run this when you're fairly confident that
# everything will work, but be sure to watch for the postsubmits and periodic tests to ensure they pass too.
.PHONY: test-smoke
test-smoke:
go clean --testcache
go test -v -timeout 0 ./test/e2e/... -args --ginkgo.focus "Quickstart"
warn-hnc-repair:
@echo "************************************************************"
ifndef HNC_REPAIR
@echo "HNC_REPAIR IS NOT SET. CRITICAL TESTS WILL BE SKIPPED."
@echo
@echo "If HNC is installed via an operator (e.g. GKE Hierarchy"
@echo "Controller), this is probably what you want to do. Otherwise,"
@echo "consider setting HNC_REPAIR to run the full set of tests."
else
@echo "HNC_REPAIR IS SET; ENSURE YOU HAVE PERMISSION TO MODIFY HNC"
@echo "CONFIGS."
@echo
@echo "If HNC is installed via an operator (e.g. GKE Hierarchy"
@echo "Controller), these tests will fail and your cluster could"
@echo "be left in a bad state."
endif
@echo
@echo "You have 3s to hit Ctrl-C to cancel..."
@echo "************************************************************"
@echo
@sleep 3
# Generate the Krew manifest and put it in manifests/. Note that 'manifests' must exist because
# krew-build calls krew-tar calls build calls manifests.
HNC_RELEASE_REPO_OWNER ?= pfnet
krew-build: krew-tar
cp hack/krew-kubectl-hns.yaml manifests/krew-kubectl-hns.yaml
sed -i 's/HNC_KREW_TAR_SHA256/${HNC_KREW_TAR_SHA256}/' manifests/krew-kubectl-hns.yaml
sed -i 's/HNC_IMG_TAG/${HNC_IMG_TAG}/' manifests/krew-kubectl-hns.yaml
sed -i 's/HNC_RELEASE_REPO_OWNER/${HNC_RELEASE_REPO_OWNER}/' manifests/krew-kubectl-hns.yaml
# This needs to be separate from krew-build so that the HNC_KREW_TAR_SHA256 env
# var can be evaluated before the recipe starts running.
krew-tar: build
cp LICENSE bin/kubectl
tar -zcvf bin/kubectl-hns.tar.gz bin/kubectl
# Install kubectl plugin locally using krew.
krew-install: krew-build
kubectl krew install --manifest=manifests/krew-kubectl-hns.yaml --archive=bin/kubectl-hns.tar.gz
# Uninstall kubectl plugin locally using krew.
krew-uninstall:
-kubectl krew uninstall hns