From 8b72bea2f337b1bd7bae6fedfe36862df769dca3 Mon Sep 17 00:00:00 2001 From: Pavan Neerudu Date: Mon, 22 Jan 2024 14:47:53 +0530 Subject: [PATCH] Init commit --- .gitignore | 2 + .pipelines/build.yaml | 19 + Dockerfile | 39 +- Makefile | 84 ++- api/v1beta1/types.go | 4 + cloud/defaults.go | 1 + cloud/scope/cluster.go | 2 +- cloud/scope/scopeinterface.go | 1 + cloud/scope/virtualmachine.go | 2 +- cloud/services/disks/service.go | 2 +- cloud/services/groups/service.go | 2 +- cloud/services/health/health.go | 6 +- cloud/services/keyvaults/service.go | 2 +- cloud/services/loadbalancers/loadbalancers.go | 6 +- cloud/services/loadbalancers/service.go | 2 +- .../networkinterfaces/networkinterfaces.go | 10 +- cloud/services/networkinterfaces/service.go | 2 +- cloud/services/vippools/service.go | 2 +- cloud/services/virtualmachines/service.go | 2 +- .../virtualmachines/virtualmachines.go | 2 +- cloud/services/virtualnetworks/service.go | 2 +- cloud/telemetry/logutils.go | 8 +- cmd/manager/main.go | 3 + config/certmanager/kustomization.yaml | 6 +- ...luster.x-k8s.io_azurestackhciclusters.yaml | 598 ------------------ ...r.x-k8s.io_azurestackhciloadbalancers.yaml | 438 ------------- ...luster.x-k8s.io_azurestackhcimachines.yaml | 438 +------------ ...-k8s.io_azurestackhcimachinetemplates.yaml | 262 +------- ...x-k8s.io_azurestackhcivirtualmachines.yaml | 428 +------------ config/crd/kustomization.yaml | 30 +- config/default/kustomization.yaml | 95 +-- config/default/manager_auth_proxy_patch.yaml | 2 +- config/manager/kustomization.yaml | 2 +- config/rbac/kustomization.yaml | 14 +- config/webhook/kustomization.yaml | 8 +- .../azurestackhcicluster_controller.go | 10 +- ...zurestackhciloadbalancer_virtualmachine.go | 6 +- .../azurestackhcimachine_controller.go | 71 ++- .../azurestackhcimachine_controller_test.go | 245 +++++++ controllers/controllers_suite_test.go | 129 ++++ go.mod | 7 +- go.sum | 4 +- hack/config/kustomization.yaml | 20 +- pkg/auth/auth.go | 14 +- pkg/cloudtest/cloudtest.go | 51 -- pkg/util/util.go | 2 +- templates/flavors/base/kustomization.yaml | 2 +- templates/flavors/default/kustomization.yaml | 8 +- templates/flavors/mgmt/kustomization.yaml | 6 +- test/mocks/externalmocks.go | 5 + test/mocks/k8s/client/client.go | 228 +++++++ 51 files changed, 891 insertions(+), 2443 deletions(-) create mode 100644 controllers/azurestackhcimachine_controller_test.go create mode 100644 controllers/controllers_suite_test.go delete mode 100644 pkg/cloudtest/cloudtest.go create mode 100644 test/mocks/externalmocks.go create mode 100644 test/mocks/k8s/client/client.go diff --git a/.gitignore b/.gitignore index 118c52c..1ff433f 100644 --- a/.gitignore +++ b/.gitignore @@ -42,6 +42,8 @@ kubeconfig # Ignore output manifests config/samples +config/default/manager_image_patch.yaml + manager_image_patch.yaml-e # Bazel diff --git a/.pipelines/build.yaml b/.pipelines/build.yaml index 6d4ae20..142ce5c 100644 --- a/.pipelines/build.yaml +++ b/.pipelines/build.yaml @@ -22,23 +22,42 @@ jobs: branchName: "refs/heads/master" downloadType: "specific" downloadPath: "$(System.DefaultWorkingDirectory)" + - task: InstallSSHKey@0 inputs: knownHostsEntry: "$(KNOWN_HOST)" sshPublicKey: "$(SSH_PUBLIC_KEY)" sshKeySecureFile: "azure-pipelines-ssh-key-new" + - task: DockerInstaller@0 inputs: dockerVersion: "17.09.0-ce" + - task: Docker@2 displayName: Login to ACR inputs: command: login containerRegistry: mocimages-connection + - task: GoTool@0 inputs: version: "1.19.9" + - script: + set -e + make test + workingDirectory: "$(System.DefaultWorkingDirectory)" + displayName: "Run Unit Tests" + + - script: + [[ -z "$(git status -s)" ]] || { + git diff --color | cat; + echo "Source changes detected after running make. Make sure to build both the product and test code locally (and run unit tests) before pushing changes"; + exit 1; + } + workingDirectory: "$(System.DefaultWorkingDirectory)" + displayName: "Check for uncommitted changes" + - script: | set -e set -x diff --git a/Dockerfile b/Dockerfile index 244389c..258ba89 100644 --- a/Dockerfile +++ b/Dockerfile @@ -13,42 +13,11 @@ # See the License for the specific language governing permissions and # limitations under the License. -# Build the manager binary -#FROM golang:1.12.9 as builder -# WORKDIR /workspace - -# Run this with docker build --build_arg $(go env GOPROXY) to override the goproxy -#ARG goproxy=https://proxy.golang.org -#ENV GOPROXY=$goproxy - -#ENV GOPRIVATE="github.com/microsoft" -#RUN go env GOPRIVATE=github.com/microsoft - -# Copy the Go Modules manifests -#COPY go.mod go.mod -#COPY go.sum go.sum -# Cache deps before building and copying source so that we don't need to re-download as much -# and so that source changes don't invalidate our downloaded layer -#RUN go mod download - -# Copy the sources -#COPY ./ ./ -#COPY ./bin/manager ./ - -# Build -#ARG ARCH -#RUN CGO_ENABLED=0 GOOS=linux GOARCH=${ARCH} GO111MODULE=on \ -# go build -a -ldflags '-extldflags "-static"' \ -# -o manager . - - -# NOTE: Approach above is not used while we still have a couple of private git repo's. -# Can be uncommented later. - -# Copy the controller-manager into a thin image -#FROM alpine:3.11 -FROM gcr.io/distroless/static:latest +# Use distroless as minimal base image to package the manager binary +FROM mcr.microsoft.com/cbl-mariner/distroless/debug:2.0 WORKDIR / + COPY bin/manager ./ USER nobody + ENTRYPOINT ["/manager"] \ No newline at end of file diff --git a/Makefile b/Makefile index c7ccf64..9909277 100644 --- a/Makefile +++ b/Makefile @@ -66,8 +66,6 @@ OUTPUT_BASE := --output-base=$(ROOT_DIR) CAPI_VERSION := v1.4.2 # Binaries. -KUBE_APISERVER=$(TOOLS_BIN_DIR)/kube-apiserver -ETCD=$(TOOLS_BIN_DIR)/etcd GO_INSTALL = ./scripts/go_install.sh # Binaries. @@ -87,7 +85,7 @@ ENVSUBST_VER := v2.0.0-20210730161058-179042472c46 ENVSUBST_BIN := envsubst ENVSUBST := $(TOOLS_BIN_DIR)/$(ENVSUBST_BIN)-$(ENVSUBST_VER) -GOLANGCI_LINT_VER := v1.48.0 +GOLANGCI_LINT_VER := v1.54.1 GOLANGCI_LINT_BIN := golangci-lint GOLANGCI_LINT := $(TOOLS_BIN_DIR)/$(GOLANGCI_LINT_BIN)-$(GOLANGCI_LINT_VER) @@ -107,14 +105,28 @@ GO_APIDIFF_VER := v0.6.0 GO_APIDIFF_BIN := go-apidiff GO_APIDIFF := $(TOOLS_BIN_DIR)/$(GO_APIDIFF_BIN) -GINKGO_VER := v2.9.7 +GINKGO_VER := v2.9.2 GINKGO_BIN := ginkgo GINKGO := $(TOOLS_BIN_DIR)/$(GINKGO_BIN)-$(GINKGO_VER) -KUBECTL_VER := v1.25.11 +KUBECTL_VER := v1.26.6 KUBECTL_BIN := kubectl KUBECTL := $(TOOLS_BIN_DIR)/$(KUBECTL_BIN)-$(KUBECTL_VER) +# ENVTEST is used for running controller tests. +SETUP_ENVTEST_VER := 116a1b831fffe7ccc3c8145306c3e1a3b1b14ffa # Note: this matches the commit ID of the dependent controller-runtime module. +SETUP_ENVTEST_BIN := setup-envtest +SETUP_ENVTEST := $(abspath $(TOOLS_BIN_DIR)/$(SETUP_ENVTEST_BIN)-$(SETUP_ENVTEST_VER)) + +# +# Kubebuilder +# +export KUBEBUILDER_ENVTEST_KUBERNETES_VERSION ?= 1.26.0 +export KUBEBUILDER_CONTROLPLANE_START_TIMEOUT ?= 60s +export KUBEBUILDER_CONTROLPLANE_STOP_TIMEOUT ?= 60s + +KUBEBUILDER_ASSETS ?= $(shell $(SETUP_ENVTEST) use --use-env -p path $(KUBEBUILDER_ENVTEST_KUBERNETES_VERSION)) + # Version MAJOR_VER ?= 1 MINOR_VER ?= 1 @@ -153,27 +165,10 @@ help: ## Display this help ## Testing ## -------------------------------------- -test: export TEST_ASSET_KUBECTL = $(ROOT_DIR)/$(KUBECTL) -test: export TEST_ASSET_KUBE_APISERVER = $(ROOT_DIR)/$(KUBE_APISERVER) -test: export TEST_ASSET_ETCD = $(ROOT_DIR)/$(ETCD) - .PHONY: test -test: $(KUBECTL) $(KUBE_APISERVER) $(ETCD) generate lint ## Run tests - go test ./... - - -.PHONY: test-integration -test-integration: ## Run integration tests - go test -v -tags=integration ./test/integration/... - -.PHONY: test-e2e -test-e2e: ## Run e2e tests - PULL_POLICY=IfNotPresent $(MAKE) docker-build - MANAGER_IMAGE=$(CONTROLLER_IMG)-$(ARCH):$(TAG) \ - go test ./test/e2e -v -tags=e2e -ginkgo.v -ginkgo.trace -count=1 -timeout=90m - -$(KUBE_APISERVER) $(ETCD): ## install test asset kube-apiserver, etcd - source ./scripts/fetch_ext_bins.sh && fetch_tools +test: generate lint fmt modules vet $(SETUP_ENVTEST) + KUBEBUILDER_ASSETS="$(KUBEBUILDER_ASSETS)" \ + ginkgo -r -v -cover -coverprofile cover.out ./... ## -------------------------------------- ## Binaries @@ -182,8 +177,9 @@ $(KUBE_APISERVER) $(ETCD): ## install test asset kube-apiserver, etcd .PHONY: binaries binaries: manager ## Builds and installs all binaries -.PHONY: manager -manager: ## Build manager binary. + ## Build manager binary. +.PHONY: manager +manager: generate lint fmt modules vet ## Build manager binary. CGO_ENABLED=0 GOOS=linux go build -a -ldflags '-extldflags "-static"' -o bin/manager cmd/manager/main.go ## -------------------------------------- @@ -203,6 +199,7 @@ $(CLUSTERCTL_BIN): $(CLUSTERCTL) $(CONTROLLER_GEN): ## Build controller-gen from tools folder. GOBIN=$(TOOLS_BIN_DIR) $(GO_INSTALL) sigs.k8s.io/controller-tools/cmd/controller-gen $(CONTROLLER_GEN_BIN) $(CONTROLLER_GEN_VER) + $(CONVERSION_GEN): ## Build conversion-gen. GOBIN=$(TOOLS_BIN_DIR) $(GO_INSTALL) k8s.io/code-generator/cmd/conversion-gen $(CONVERSION_GEN_BIN) $(CONVERSION_GEN_VER) @@ -212,6 +209,16 @@ $(ENVSUBST): ## Build envsubst from tools folder. .PHONY: $(ENVSUBST_BIN) $(ENVSUBST_BIN): $(ENVSUBST) +.PHONY: $(SETUP_ENVTEST_BIN) +$(SETUP_ENVTEST_BIN): $(SETUP_ENVTEST) ## Build a local copy of setup-envtest. + +.PHONY: setup-envtest +setup-envtest: $(SETUP_ENVTEST) ## Set up envtest (download kubebuilder assets) + @echo KUBEBUILDER_ASSETS=$(KUBEBUILDER_ASSETS) + +.PHONY: mockgen +mockgen: $(MOCKGEN) ## Generate mocks using mockgen. + $(GOLANGCI_LINT): ## Build golangci-lint from tools folder. GOBIN=$(TOOLS_BIN_DIR) $(GO_INSTALL) github.com/golangci/golangci-lint/cmd/golangci-lint $(GOLANGCI_LINT_BIN) $(GOLANGCI_LINT_VER) @@ -240,6 +247,10 @@ $(KUBECTL): ## Get kubectl .PHONY: $(KUBECTL_BIN) $(KUBECTL_BIN): $(KUBECTL) +$(SETUP_ENVTEST): # Build setup-envtest. + GOBIN=$(TOOLS_BIN_DIR) $(GO_INSTALL) sigs.k8s.io/controller-runtime/tools/setup-envtest $(SETUP_ENVTEST_BIN) $(SETUP_ENVTEST_VER) + @echo "🛠 setup-envtest installed to $(TOOLS_BIN_DIR)/$(ENVTEST_BIN)" + ## -------------------------------------- ## Linting ## -------------------------------------- @@ -260,6 +271,15 @@ modules: ## Runs go mod to ensure proper vendoring. go mod tidy cd $(TOOLS_DIR); go mod tidy +# Run go fmt against code +.PHONY: fmt +fmt: + go fmt ./... + +# Run go vet against code +vet: + go vet ./... + .PHONY: generate generate: ## Generate code $(MAKE) generate-go @@ -270,19 +290,13 @@ generate: ## Generate code generate-go: $(CONTROLLER_GEN) $(MOCKGEN) $(CONVERSION_GEN) ## Runs Go related generate targets go generate ./... $(CONTROLLER_GEN) \ - paths=./api/... \ + paths=./api/v1beta1 \ object:headerFile=./hack/boilerplate/boilerplate.generatego.txt - - $(CONVERSION_GEN) \ - --input-dirs=./api/v1alpha3 \ - --input-dirs=./api/v1alpha4 \ - --output-file-base=zz_generated.conversion $(OUTPUT_BASE) \ - --go-header-file=./hack/boilerplate/boilerplate.generatego.txt .PHONY: generate-manifests generate-manifests: $(CONTROLLER_GEN) ## Generate manifests e.g. CRD, RBAC etc. $(CONTROLLER_GEN) \ - paths=./api/... \ + paths=./api/v1beta1 \ crd:crdVersions=v1 \ rbac:roleName=manager-role \ output:crd:dir=$(CRD_ROOT) \ diff --git a/api/v1beta1/types.go b/api/v1beta1/types.go index a22fadc..12f2454 100644 --- a/api/v1beta1/types.go +++ b/api/v1beta1/types.go @@ -106,12 +106,14 @@ func (s Subnets) ToMap() map[string]*SubnetSpec { type IPAllocationMethod int32 +// nolint: golint const ( IPAllocationMethod_Invalid IPAllocationMethod = 0 IPAllocationMethod_Dynamic IPAllocationMethod = 1 IPAllocationMethod_Static IPAllocationMethod = 2 ) +// nolint: golint type IpConfigurationSpec struct { Name string `json:"name,omitempty"` // +optional @@ -128,6 +130,8 @@ type IpConfigurationSpec struct { // +optional Gateway string `json:"gateway,omitempty"` } + +// nolint: golint type IpConfigurations []*IpConfigurationSpec type NetworkInterfaceSpec struct { diff --git a/cloud/defaults.go b/cloud/defaults.go index 551da37..905d787 100644 --- a/cloud/defaults.go +++ b/cloud/defaults.go @@ -59,6 +59,7 @@ const ( LatestVersion = "latest" ) +// nolint: golint const ( // Role is used to distinguish api server lb from other lbs. // used by SDN integration diff --git a/cloud/scope/cluster.go b/cloud/scope/cluster.go index 312f41c..286d128 100644 --- a/cloud/scope/cluster.go +++ b/cloud/scope/cluster.go @@ -84,7 +84,7 @@ func NewClusterScope(params ClusterScopeParams) (*ClusterScope, error) { Context: scopeContext, } - authorizer, err := azhciauth.ReconcileAzureStackHCIAccess(*params.Logger, scope.Context, scope.Client, agentFqdn) + authorizer, err := azhciauth.ReconcileAzureStackHCIAccess(scope.Context, *params.Logger, scope.Client, agentFqdn) if err != nil { return nil, errors.Wrap(err, "error creating azurestackhci services. can not authenticate to azurestackhci") } diff --git a/cloud/scope/scopeinterface.go b/cloud/scope/scopeinterface.go index c6c048c..fd09957 100644 --- a/cloud/scope/scopeinterface.go +++ b/cloud/scope/scopeinterface.go @@ -23,6 +23,7 @@ import ( ) // ScopeInterface allows multiple scope types to be used for cloud services +// nolint: golint type ScopeInterface interface { GetResourceGroup() string GetCloudAgentFqdn() string diff --git a/cloud/scope/virtualmachine.go b/cloud/scope/virtualmachine.go index 6ff8456..667862a 100644 --- a/cloud/scope/virtualmachine.go +++ b/cloud/scope/virtualmachine.go @@ -68,7 +68,7 @@ func NewVirtualMachineScope(params VirtualMachineScopeParams) (*VirtualMachineSc params.AzureStackHCIClients.CloudAgentFqdn = agentFqdn scopeContext := diagnostics.NewContextWithCorrelationId(context.Background(), params.AzureStackHCIVirtualMachine.GetAnnotations()[infrav1.AzureCorrelationIDAnnotationKey]) - authorizer, err := azhciauth.ReconcileAzureStackHCIAccess(*params.Logger, scopeContext, params.Client, agentFqdn) + authorizer, err := azhciauth.ReconcileAzureStackHCIAccess(scopeContext, *params.Logger, params.Client, agentFqdn) if err != nil { return nil, errors.Wrap(err, "failed to create azurestackhci session") } diff --git a/cloud/services/disks/service.go b/cloud/services/disks/service.go index f9f82da..592599d 100644 --- a/cloud/services/disks/service.go +++ b/cloud/services/disks/service.go @@ -21,8 +21,8 @@ import ( //"github.com/Azure/go-autorest/autorest" azurestackhci "github.com/microsoft/cluster-api-provider-azurestackhci/cloud" "github.com/microsoft/cluster-api-provider-azurestackhci/cloud/scope" - "github.com/microsoft/moc/pkg/auth" "github.com/microsoft/moc-sdk-for-go/services/storage/virtualharddisk" + "github.com/microsoft/moc/pkg/auth" ) var _ azurestackhci.Service = (*Service)(nil) diff --git a/cloud/services/groups/service.go b/cloud/services/groups/service.go index ee4727d..46f77b3 100644 --- a/cloud/services/groups/service.go +++ b/cloud/services/groups/service.go @@ -20,8 +20,8 @@ package groups import ( azurestackhci "github.com/microsoft/cluster-api-provider-azurestackhci/cloud" "github.com/microsoft/cluster-api-provider-azurestackhci/cloud/scope" - "github.com/microsoft/moc/pkg/auth" "github.com/microsoft/moc-sdk-for-go/services/cloud/group" + "github.com/microsoft/moc/pkg/auth" ) var _ azurestackhci.Service = (*Service)(nil) diff --git a/cloud/services/health/health.go b/cloud/services/health/health.go index 078206c..d6882f5 100644 --- a/cloud/services/health/health.go +++ b/cloud/services/health/health.go @@ -22,13 +22,13 @@ import ( "fmt" ) -func (s *Service) GetMocDeploymentId(ctx context.Context) string { - deploymentId, err := s.Client.GetDeploymentId(ctx) +func (s *Service) GetMocDeploymentID(ctx context.Context) string { + deploymentID, err := s.Client.GetDeploymentId(ctx) if err != nil { s.Scope.GetLogger().Error(err, "Unable to get moc deployment id") return "" } - return deploymentId + return deploymentID } diff --git a/cloud/services/keyvaults/service.go b/cloud/services/keyvaults/service.go index 065142e..283b8bc 100644 --- a/cloud/services/keyvaults/service.go +++ b/cloud/services/keyvaults/service.go @@ -20,8 +20,8 @@ package keyvaults import ( azurestackhci "github.com/microsoft/cluster-api-provider-azurestackhci/cloud" "github.com/microsoft/cluster-api-provider-azurestackhci/cloud/scope" - "github.com/microsoft/moc/pkg/auth" "github.com/microsoft/moc-sdk-for-go/services/security/keyvault" + "github.com/microsoft/moc/pkg/auth" ) var _ azurestackhci.Service = (*Service)(nil) diff --git a/cloud/services/loadbalancers/loadbalancers.go b/cloud/services/loadbalancers/loadbalancers.go index 46396b7..4c8f408 100644 --- a/cloud/services/loadbalancers/loadbalancers.go +++ b/cloud/services/loadbalancers/loadbalancers.go @@ -70,12 +70,12 @@ func (s *Service) Reconcile(ctx context.Context, spec interface{}) error { Name: to.StringPtr(lbSpec.Name), LoadBalancerPropertiesFormat: &network.LoadBalancerPropertiesFormat{ BackendAddressPools: &[]network.BackendAddressPool{ - network.BackendAddressPool{ + { Name: to.StringPtr(lbSpec.BackendPoolName), }, }, FrontendIPConfigurations: &[]network.FrontendIPConfiguration{ - network.FrontendIPConfiguration{ + { FrontendIPConfigurationPropertiesFormat: &network.FrontendIPConfigurationPropertiesFormat{ Subnet: &network.Subnet{ ID: to.StringPtr(lbSpec.VnetName), @@ -84,7 +84,7 @@ func (s *Service) Reconcile(ctx context.Context, spec interface{}) error { }, }, LoadBalancingRules: &[]network.LoadBalancingRule{ - network.LoadBalancingRule{ + { LoadBalancingRulePropertiesFormat: &network.LoadBalancingRulePropertiesFormat{ Protocol: network.TransportProtocolTCP, FrontendPort: to.Int32Ptr(lbSpec.FrontendPort), diff --git a/cloud/services/loadbalancers/service.go b/cloud/services/loadbalancers/service.go index b82db4e..245c52b 100644 --- a/cloud/services/loadbalancers/service.go +++ b/cloud/services/loadbalancers/service.go @@ -20,8 +20,8 @@ package loadbalancers import ( azurestackhci "github.com/microsoft/cluster-api-provider-azurestackhci/cloud" "github.com/microsoft/cluster-api-provider-azurestackhci/cloud/scope" - "github.com/microsoft/moc/pkg/auth" "github.com/microsoft/moc-sdk-for-go/services/network/loadbalancer" + "github.com/microsoft/moc/pkg/auth" ) var _ azurestackhci.Service = (*Service)(nil) diff --git a/cloud/services/networkinterfaces/networkinterfaces.go b/cloud/services/networkinterfaces/networkinterfaces.go index 53e9fc4..700d357 100644 --- a/cloud/services/networkinterfaces/networkinterfaces.go +++ b/cloud/services/networkinterfaces/networkinterfaces.go @@ -104,7 +104,7 @@ func (s *Service) Reconcile(ctx context.Context, spec interface{}) error { logger.Info("Adding ipconfigurations to nic ", "len", len(nicSpec.IPConfigurations), "name", nicSpec.Name) for _, ipconfig := range nicSpec.IPConfigurations { - networkIpConfig := network.InterfaceIPConfiguration{ + networkIPConfig := network.InterfaceIPConfiguration{ Name: &ipconfig.Name, InterfaceIPConfigurationPropertiesFormat: &network.InterfaceIPConfigurationPropertiesFormat{ Primary: &ipconfig.Primary, @@ -115,18 +115,18 @@ func (s *Service) Reconcile(ctx context.Context, spec interface{}) error { } if ipconfig.Primary { - networkIpConfig.LoadBalancerBackendAddressPools = &backendAddressPools + networkIPConfig.LoadBalancerBackendAddressPools = &backendAddressPools } - *networkInterface.IPConfigurations = append(*networkInterface.IPConfigurations, networkIpConfig) + *networkInterface.IPConfigurations = append(*networkInterface.IPConfigurations, networkIPConfig) } } else { - networkIpConfig := network.InterfaceIPConfiguration{ + networkIPConfig := network.InterfaceIPConfiguration{ Name: to.StringPtr("pipConfig"), InterfaceIPConfigurationPropertiesFormat: nicConfig, } - *networkInterface.IPConfigurations = append(*networkInterface.IPConfigurations, networkIpConfig) + *networkInterface.IPConfigurations = append(*networkInterface.IPConfigurations, networkIPConfig) } _, err := s.Client.CreateOrUpdate(ctx, diff --git a/cloud/services/networkinterfaces/service.go b/cloud/services/networkinterfaces/service.go index 445dcb1..b054bac 100644 --- a/cloud/services/networkinterfaces/service.go +++ b/cloud/services/networkinterfaces/service.go @@ -21,8 +21,8 @@ import ( //"github.com/Azure/go-autorest/autorest" azurestackhci "github.com/microsoft/cluster-api-provider-azurestackhci/cloud" "github.com/microsoft/cluster-api-provider-azurestackhci/cloud/scope" - "github.com/microsoft/moc/pkg/auth" "github.com/microsoft/moc-sdk-for-go/services/network/networkinterface" + "github.com/microsoft/moc/pkg/auth" ) var _ azurestackhci.Service = (*Service)(nil) diff --git a/cloud/services/vippools/service.go b/cloud/services/vippools/service.go index e367e7b..b45eef0 100644 --- a/cloud/services/vippools/service.go +++ b/cloud/services/vippools/service.go @@ -20,8 +20,8 @@ package vippools import ( azhci "github.com/microsoft/cluster-api-provider-azurestackhci/cloud" "github.com/microsoft/cluster-api-provider-azurestackhci/cloud/scope" - "github.com/microsoft/moc/pkg/auth" "github.com/microsoft/moc-sdk-for-go/services/network/vippool" + "github.com/microsoft/moc/pkg/auth" ) var _ azhci.Service = (*Service)(nil) diff --git a/cloud/services/virtualmachines/service.go b/cloud/services/virtualmachines/service.go index b4017d1..991624e 100644 --- a/cloud/services/virtualmachines/service.go +++ b/cloud/services/virtualmachines/service.go @@ -20,8 +20,8 @@ package virtualmachines import ( azurestackhci "github.com/microsoft/cluster-api-provider-azurestackhci/cloud" "github.com/microsoft/cluster-api-provider-azurestackhci/cloud/scope" - "github.com/microsoft/moc/pkg/auth" "github.com/microsoft/moc-sdk-for-go/services/compute/virtualmachine" + "github.com/microsoft/moc/pkg/auth" ) var _ azurestackhci.Service = (*Service)(nil) diff --git a/cloud/services/virtualmachines/virtualmachines.go b/cloud/services/virtualmachines/virtualmachines.go index 93cba28..5474930 100644 --- a/cloud/services/virtualmachines/virtualmachines.go +++ b/cloud/services/virtualmachines/virtualmachines.go @@ -326,7 +326,7 @@ func GenerateRandomString(n int) (string, error) { // generateComputerName returns a unique OS computer name which is expected to be valid on any // operating system. To satisfy Windows requirements, we generate a length-restricted name. The -// generated computer name has the following format: +// generated computer name has the following format: func generateComputerName(os infrav1.OSType) (string, error) { computerName := computerNamePrefix diff --git a/cloud/services/virtualnetworks/service.go b/cloud/services/virtualnetworks/service.go index 42b9fd6..5c330da 100644 --- a/cloud/services/virtualnetworks/service.go +++ b/cloud/services/virtualnetworks/service.go @@ -21,8 +21,8 @@ import ( //"github.com/Azure/go-autorest/autorest" azurestackhci "github.com/microsoft/cluster-api-provider-azurestackhci/cloud" "github.com/microsoft/cluster-api-provider-azurestackhci/cloud/scope" - "github.com/microsoft/moc/pkg/auth" "github.com/microsoft/moc-sdk-for-go/services/network/virtualnetwork" + "github.com/microsoft/moc/pkg/auth" ) var _ azurestackhci.Service = (*Service)(nil) diff --git a/cloud/telemetry/logutils.go b/cloud/telemetry/logutils.go index 73cc2fc..a2a9fee 100644 --- a/cloud/telemetry/logutils.go +++ b/cloud/telemetry/logutils.go @@ -122,7 +122,7 @@ func GenerateMocResourceName(nameSegments ...string) string { } type MocInfoLog struct { - MocDeploymentId string `json:"moc_deployment_id"` + MocDeploymentID string `json:"moc_deployment_id"` WssdCloudAgentVersion string `json:"wssd_cloud_agent_version"` MocVersion string `json:"moc_version"` } @@ -131,7 +131,7 @@ var healthService *health.Service var versionsService *versions.Service func WriteMocInfoLog(ctx context.Context, scope scope.ScopeInterface) { - deploymentId := getHealthService(scope).GetMocDeploymentId(ctx) + deploymentID := getHealthService(scope).GetMocDeploymentID(ctx) wssdCloudAgentVersion := "" mocVersion := "" @@ -145,7 +145,7 @@ func WriteMocInfoLog(ctx context.Context, scope scope.ScopeInterface) { } infoLog := MocInfoLog{ - MocDeploymentId: deploymentId, + MocDeploymentID: deploymentID, WssdCloudAgentVersion: wssdCloudAgentVersion, MocVersion: mocVersion, } @@ -158,7 +158,7 @@ func WriteMocInfoLog(ctx context.Context, scope scope.ScopeInterface) { } func getHealthService(scope scope.ScopeInterface) *health.Service { - // if healthService instance is created, directy return instance + // if healthService instance is created, directly return instance if healthService != nil { return healthService } diff --git a/cmd/manager/main.go b/cmd/manager/main.go index 58bafef..16e0899 100644 --- a/cmd/manager/main.go +++ b/cmd/manager/main.go @@ -20,6 +20,8 @@ package main import ( "flag" "net/http" + + //nolint:gosec _ "net/http/pprof" "os" "time" @@ -162,6 +164,7 @@ func main() { if profilerAddress != "" { setupLog.Info("Profiler listening for requests", "profiler-address", profilerAddress) go func() { + //nolint:gosec setupLog.Error(http.ListenAndServe(profilerAddress, nil), "listen and serve error") }() } diff --git a/config/certmanager/kustomization.yaml b/config/certmanager/kustomization.yaml index 34e7e5b..8c1ed45 100644 --- a/config/certmanager/kustomization.yaml +++ b/config/certmanager/kustomization.yaml @@ -1,4 +1,6 @@ resources: - - certificate.yaml +- certificate.yaml configurations: - - kustomizeconfig.yaml +- kustomizeconfig.yaml +apiVersion: kustomize.config.k8s.io/v1beta1 +kind: Kustomization diff --git a/config/crd/bases/infrastructure.cluster.x-k8s.io_azurestackhciclusters.yaml b/config/crd/bases/infrastructure.cluster.x-k8s.io_azurestackhciclusters.yaml index 2d643cc..3e1aadd 100644 --- a/config/crd/bases/infrastructure.cluster.x-k8s.io_azurestackhciclusters.yaml +++ b/config/crd/bases/infrastructure.cluster.x-k8s.io_azurestackhciclusters.yaml @@ -16,604 +16,6 @@ spec: singular: azurestackhcicluster scope: Namespaced versions: - - additionalPrinterColumns: - - description: AzureStackHCICluster status such as Pending/Provisioning/Provisioned/Deleting/Failed - jsonPath: .status.phase - name: Phase - type: string - name: v1alpha3 - schema: - openAPIV3Schema: - description: AzureStackHCICluster is the Schema for the azurestackhciclusters - API - properties: - apiVersion: - description: 'APIVersion defines the versioned schema of this representation - of an object. Servers should convert recognized schemas to the latest - internal value, and may reject unrecognized values. More info: https://git.k8s.io/community/contributors/devel/sig-architecture/api-conventions.md#resources' - type: string - kind: - description: 'Kind is a string value representing the REST resource this - object represents. Servers may infer this from the endpoint the client - submits requests to. Cannot be updated. In CamelCase. More info: https://git.k8s.io/community/contributors/devel/sig-architecture/api-conventions.md#types-kinds' - type: string - metadata: - type: object - spec: - description: AzureStackHCIClusterSpec defines the desired state of AzureStackHCICluster - properties: - azureStackHCILoadBalancer: - description: AzureStackHCILoadBalancer is used to declare the AzureStackHCILoadBalancerSpec - if a LoadBalancer is desired for the AzureStackHCICluster. - properties: - image: - description: 'Image defines information about the image to use - for VM creation. There are three ways to specify an image: by - ID, by publisher, or by Shared Image Gallery. If specifying - an image by ID, only the ID field needs to be set. If specifying - an image by publisher, the Publisher, Offer, SKU, and Version - fields must be set. If specifying an image from a Shared Image - Gallery, the SubscriptionID, ResourceGroup, Gallery, Name, and - Version fields must be set.' - properties: - gallery: - type: string - id: - type: string - name: - type: string - offer: - type: string - osType: - description: OSType describes the OS type of a disk. - type: string - publisher: - type: string - resourceGroup: - type: string - sku: - type: string - subscriptionID: - type: string - version: - type: string - required: - - osType - type: object - replicas: - default: 1 - description: Number of desired loadbalancer machines. Defaults - to 1. This is a pointer to distinguish between explicit zero - and not specified. - format: int32 - type: integer - sshPublicKey: - type: string - vmSize: - type: string - required: - - image - - sshPublicKey - - vmSize - type: object - controlPlaneEndpoint: - description: ControlPlaneEndpoint represents the endpoint used to - communicate with the control plane. - properties: - host: - description: The hostname on which the API server is serving. - type: string - port: - description: The port on which the API server is serving. - format: int32 - type: integer - required: - - host - - port - type: object - location: - type: string - management: - description: Management is true when the cluster is a Management Cluster. - type: boolean - networkSpec: - description: NetworkSpec encapsulates all things related to Azure - network. - properties: - subnets: - description: Subnets is the configuration for the control-plane - subnet and the node subnet. - items: - description: SubnetSpec configures an Azure subnet. - properties: - cidrBlock: - description: CidrBlock is the CIDR block to be used when - the provider creates a managed Vnet. - type: string - id: - description: ID defines a unique identifier to reference - this resource. - type: string - name: - description: Name defines a name for the subnet resource. - type: string - vnetId: - description: VnetID defines the ID of the virtual network - this subnet should be built in. - type: string - required: - - name - - vnetId - type: object - type: array - vnet: - description: Vnet is the configuration for the Azure virtual network. - properties: - cidrBlock: - description: CidrBlock is the CIDR block to be used when the - provider creates a managed virtual network. - type: string - group: - description: Group is the resource group the vnet should use. - type: string - id: - description: ID is the identifier of the virtual network this - provider should use to create resources. - type: string - name: - description: Name defines a name for the virtual network resource. - type: string - required: - - name - type: object - type: object - resourceGroup: - type: string - version: - description: Version indicates the desired Kubernetes version of the - cluster. - type: string - required: - - location - - resourceGroup - - version - type: object - status: - description: AzureStackHCIClusterStatus defines the observed state of - AzureStackHCICluster - properties: - bastion: - description: VM describes an Azure virtual machine. - properties: - availabilityZone: - type: string - bootstrapData: - type: string - id: - type: string - identity: - description: VMIdentity defines the identity of the virtual machine, - if configured. - type: string - image: - description: Storage profile - properties: - gallery: - type: string - id: - type: string - name: - type: string - offer: - type: string - osType: - description: OSType describes the OS type of a disk. - type: string - publisher: - type: string - resourceGroup: - type: string - sku: - type: string - subscriptionID: - type: string - version: - type: string - required: - - osType - type: object - name: - type: string - osDisk: - properties: - diskSizeGB: - format: int32 - type: integer - managedDisk: - properties: - storageAccountType: - type: string - required: - - storageAccountType - type: object - name: - type: string - osType: - description: OSType describes the OS type of a disk. - type: string - source: - type: string - required: - - diskSizeGB - - managedDisk - - name - - osType - - source - type: object - vmSize: - description: Hardware profile - type: string - vmState: - description: State - The provisioning state, which only appears - in the response. - type: string - type: object - conditions: - description: Conditions defines current service state of the AzureStackHCICluster. - items: - description: Condition defines an observation of a Cluster API resource - operational state. - properties: - lastTransitionTime: - description: Last time the condition transitioned from one status - to another. This should be when the underlying condition changed. - If that is not known, then using the time when the API field - changed is acceptable. - format: date-time - type: string - message: - description: A human readable message indicating details about - the transition. This field may be empty. - type: string - reason: - description: The reason for the condition's last transition - in CamelCase. The specific API may choose whether or not this - field is considered a guaranteed API. This field may not be - empty. - type: string - severity: - description: Severity provides an explicit classification of - Reason code, so the users or machines can immediately understand - the current situation and act accordingly. The Severity field - MUST be set only when Status=False. - type: string - status: - description: Status of the condition, one of True, False, Unknown. - type: string - type: - description: Type of condition in CamelCase or in foo.example.com/CamelCase. - Many .condition.type values are consistent across resources - like Available, but because arbitrary conditions can be useful - (see .node.status.conditions), the ability to deconflict is - important. - type: string - required: - - status - - type - type: object - type: array - phase: - description: Phase represents the current phase of cluster actuation. - E.g. Pending, Running, Terminating, Failed etc. - type: string - ready: - description: Ready is true when the provider resource is ready. - type: boolean - type: object - type: object - served: true - storage: false - subresources: - status: {} - - additionalPrinterColumns: - - description: AzureStackHCICluster status such as Pending/Provisioning/Provisioned/Deleting/Failed - jsonPath: .status.phase - name: Phase - type: string - name: v1alpha4 - schema: - openAPIV3Schema: - description: AzureStackHCICluster is the Schema for the azurestackhciclusters - API - properties: - apiVersion: - description: 'APIVersion defines the versioned schema of this representation - of an object. Servers should convert recognized schemas to the latest - internal value, and may reject unrecognized values. More info: https://git.k8s.io/community/contributors/devel/sig-architecture/api-conventions.md#resources' - type: string - kind: - description: 'Kind is a string value representing the REST resource this - object represents. Servers may infer this from the endpoint the client - submits requests to. Cannot be updated. In CamelCase. More info: https://git.k8s.io/community/contributors/devel/sig-architecture/api-conventions.md#types-kinds' - type: string - metadata: - type: object - spec: - description: AzureStackHCIClusterSpec defines the desired state of AzureStackHCICluster - properties: - azureStackHCILoadBalancer: - description: AzureStackHCILoadBalancer is used to declare the AzureStackHCILoadBalancerSpec - if a LoadBalancer is desired for the AzureStackHCICluster. - properties: - image: - description: 'Image defines information about the image to use - for VM creation. There are three ways to specify an image: by - ID, by publisher, or by Shared Image Gallery. If specifying - an image by ID, only the ID field needs to be set. If specifying - an image by publisher, the Publisher, Offer, SKU, and Version - fields must be set. If specifying an image from a Shared Image - Gallery, the SubscriptionID, ResourceGroup, Gallery, Name, and - Version fields must be set.' - properties: - gallery: - type: string - id: - type: string - name: - type: string - offer: - type: string - osType: - description: OSType describes the OS type of a disk. - type: string - publisher: - type: string - resourceGroup: - type: string - sku: - type: string - subscriptionID: - type: string - version: - type: string - required: - - osType - type: object - replicas: - default: 1 - description: Number of desired loadbalancer machines. Defaults - to 1. This is a pointer to distinguish between explicit zero - and not specified. - format: int32 - type: integer - sshPublicKey: - type: string - vmSize: - type: string - required: - - image - - sshPublicKey - - vmSize - type: object - controlPlaneEndpoint: - description: ControlPlaneEndpoint represents the endpoint used to - communicate with the control plane. - properties: - host: - description: The hostname on which the API server is serving. - type: string - port: - description: The port on which the API server is serving. - format: int32 - type: integer - required: - - host - - port - type: object - location: - type: string - management: - description: Management is true when the cluster is a Management Cluster. - type: boolean - networkSpec: - description: NetworkSpec encapsulates all things related to Azure - network. - properties: - subnets: - description: Subnets is the configuration for the control-plane - subnet and the node subnet. - items: - description: SubnetSpec configures an Azure subnet. - properties: - cidrBlock: - description: CidrBlock is the CIDR block to be used when - the provider creates a managed Vnet. - type: string - id: - description: ID defines a unique identifier to reference - this resource. - type: string - name: - description: Name defines a name for the subnet resource. - type: string - vnetId: - description: VnetID defines the ID of the virtual network - this subnet should be built in. - type: string - required: - - name - - vnetId - type: object - type: array - vnet: - description: Vnet is the configuration for the Azure virtual network. - properties: - cidrBlock: - description: CidrBlock is the CIDR block to be used when the - provider creates a managed virtual network. - type: string - group: - description: Group is the resource group the vnet should use. - type: string - id: - description: ID is the identifier of the virtual network this - provider should use to create resources. - type: string - name: - description: Name defines a name for the virtual network resource. - type: string - required: - - name - type: object - type: object - resourceGroup: - type: string - version: - description: Version indicates the desired Kubernetes version of the - cluster. - type: string - required: - - location - - resourceGroup - - version - type: object - status: - description: AzureStackHCIClusterStatus defines the observed state of - AzureStackHCICluster - properties: - bastion: - description: VM describes an Azure virtual machine. - properties: - availabilityZone: - type: string - bootstrapData: - type: string - id: - type: string - identity: - description: VMIdentity defines the identity of the virtual machine, - if configured. - type: string - image: - description: Storage profile - properties: - gallery: - type: string - id: - type: string - name: - type: string - offer: - type: string - osType: - description: OSType describes the OS type of a disk. - type: string - publisher: - type: string - resourceGroup: - type: string - sku: - type: string - subscriptionID: - type: string - version: - type: string - required: - - osType - type: object - name: - type: string - osDisk: - properties: - diskSizeGB: - format: int32 - type: integer - managedDisk: - properties: - storageAccountType: - type: string - required: - - storageAccountType - type: object - name: - type: string - osType: - description: OSType describes the OS type of a disk. - type: string - source: - type: string - required: - - diskSizeGB - - managedDisk - - name - - osType - - source - type: object - vmSize: - description: Hardware profile - type: string - vmState: - description: State - The provisioning state, which only appears - in the response. - type: string - type: object - conditions: - description: Conditions defines current service state of the AzureStackHCICluster. - items: - description: Condition defines an observation of a Cluster API resource - operational state. - properties: - lastTransitionTime: - description: Last time the condition transitioned from one status - to another. This should be when the underlying condition changed. - If that is not known, then using the time when the API field - changed is acceptable. - format: date-time - type: string - message: - description: A human readable message indicating details about - the transition. This field may be empty. - type: string - reason: - description: The reason for the condition's last transition - in CamelCase. The specific API may choose whether or not this - field is considered a guaranteed API. This field may not be - empty. - type: string - severity: - description: Severity provides an explicit classification of - Reason code, so the users or machines can immediately understand - the current situation and act accordingly. The Severity field - MUST be set only when Status=False. - type: string - status: - description: Status of the condition, one of True, False, Unknown. - type: string - type: - description: Type of condition in CamelCase or in foo.example.com/CamelCase. - Many .condition.type values are consistent across resources - like Available, but because arbitrary conditions can be useful - (see .node.status.conditions), the ability to deconflict is - important. - type: string - required: - - status - - type - type: object - type: array - phase: - description: Phase represents the current phase of cluster actuation. - E.g. Pending, Running, Terminating, Failed etc. - type: string - ready: - description: Ready is true when the provider resource is ready. - type: boolean - type: object - type: object - served: true - storage: false - subresources: - status: {} - additionalPrinterColumns: - description: AzureStackHCICluster status such as Pending/Provisioning/Provisioned/Deleting/Failed jsonPath: .status.phase diff --git a/config/crd/bases/infrastructure.cluster.x-k8s.io_azurestackhciloadbalancers.yaml b/config/crd/bases/infrastructure.cluster.x-k8s.io_azurestackhciloadbalancers.yaml index 1a631b5..a8e921d 100644 --- a/config/crd/bases/infrastructure.cluster.x-k8s.io_azurestackhciloadbalancers.yaml +++ b/config/crd/bases/infrastructure.cluster.x-k8s.io_azurestackhciloadbalancers.yaml @@ -16,444 +16,6 @@ spec: singular: azurestackhciloadbalancer scope: Namespaced versions: - - additionalPrinterColumns: - - description: The current phase/status of the loadbalancer - jsonPath: .status.phase - name: Phase - type: string - - description: The frontend VIP address assigned to the loadbalancer - jsonPath: .status.address - name: IP - type: string - - description: The frontend port assigned to the loadbalancer - jsonPath: .status.port - name: Port - type: integer - - description: Total number of desired machine replicas for this loadbalancer - jsonPath: .spec.replicas - name: Replicas - type: integer - - description: Total number of machine replicas created to service this loadbalancer - jsonPath: .status.replicas - name: Created - type: integer - - description: Total number of machine replicas that are actively connected to - the loadbalancer service - jsonPath: .status.readyReplicas - name: Ready - type: integer - - description: Total number of machine replicas that are in a failed or unavailable - state - jsonPath: .status.failedReplicas - name: Unavailable - type: integer - name: v1alpha3 - schema: - openAPIV3Schema: - description: AzureStackHCILoadBalancer is the Schema for the azurestackhciloadbalancers - API - properties: - apiVersion: - description: 'APIVersion defines the versioned schema of this representation - of an object. Servers should convert recognized schemas to the latest - internal value, and may reject unrecognized values. More info: https://git.k8s.io/community/contributors/devel/sig-architecture/api-conventions.md#resources' - type: string - kind: - description: 'Kind is a string value representing the REST resource this - object represents. Servers may infer this from the endpoint the client - submits requests to. Cannot be updated. In CamelCase. More info: https://git.k8s.io/community/contributors/devel/sig-architecture/api-conventions.md#types-kinds' - type: string - metadata: - type: object - spec: - properties: - image: - description: 'Image defines information about the image to use for - VM creation. There are three ways to specify an image: by ID, by - publisher, or by Shared Image Gallery. If specifying an image by - ID, only the ID field needs to be set. If specifying an image by - publisher, the Publisher, Offer, SKU, and Version fields must be - set. If specifying an image from a Shared Image Gallery, the SubscriptionID, - ResourceGroup, Gallery, Name, and Version fields must be set.' - properties: - gallery: - type: string - id: - type: string - name: - type: string - offer: - type: string - osType: - description: OSType describes the OS type of a disk. - type: string - publisher: - type: string - resourceGroup: - type: string - sku: - type: string - subscriptionID: - type: string - version: - type: string - required: - - osType - type: object - replicas: - default: 1 - description: Number of desired loadbalancer machines. Defaults to - 1. This is a pointer to distinguish between explicit zero and not - specified. - format: int32 - type: integer - sshPublicKey: - type: string - vmSize: - type: string - required: - - image - - sshPublicKey - - vmSize - type: object - status: - properties: - address: - description: Address is the IP address of the load balancer. - type: string - conditions: - description: Conditions defines current service state of the AzureStackHCILoadBalancer. - items: - description: Condition defines an observation of a Cluster API resource - operational state. - properties: - lastTransitionTime: - description: Last time the condition transitioned from one status - to another. This should be when the underlying condition changed. - If that is not known, then using the time when the API field - changed is acceptable. - format: date-time - type: string - message: - description: A human readable message indicating details about - the transition. This field may be empty. - type: string - reason: - description: The reason for the condition's last transition - in CamelCase. The specific API may choose whether or not this - field is considered a guaranteed API. This field may not be - empty. - type: string - severity: - description: Severity provides an explicit classification of - Reason code, so the users or machines can immediately understand - the current situation and act accordingly. The Severity field - MUST be set only when Status=False. - type: string - status: - description: Status of the condition, one of True, False, Unknown. - type: string - type: - description: Type of condition in CamelCase or in foo.example.com/CamelCase. - Many .condition.type values are consistent across resources - like Available, but because arbitrary conditions can be useful - (see .node.status.conditions), the ability to deconflict is - important. - type: string - required: - - status - - type - type: object - type: array - errorMessage: - description: "ErrorMessage will be set in the event that there is - a terminal problem reconciling the Machine and will contain a more - verbose string suitable for logging and human consumption. \n This - field should not be set for transitive errors that a controller - faces that are expected to be fixed automatically over time (like - service outages), but instead indicate that something is fundamentally - wrong with the Machine's spec or the configuration of the controller, - and that manual intervention is required. Examples of terminal errors - would be invalid combinations of settings in the spec, values that - are unsupported by the controller, or the responsible controller - itself being critically misconfigured. \n Any transient errors that - occur during the reconciliation of Machines can be added as events - to the Machine object and/or logged in the controller's output." - type: string - errorReason: - description: "ErrorReason will be set in the event that there is a - terminal problem reconciling the Machine and will contain a succinct - value suitable for machine interpretation. \n This field should - not be set for transitive errors that a controller faces that are - expected to be fixed automatically over time (like service outages), - but instead indicate that something is fundamentally wrong with - the Machine's spec or the configuration of the controller, and that - manual intervention is required. Examples of terminal errors would - be invalid combinations of settings in the spec, values that are - unsupported by the controller, or the responsible controller itself - being critically misconfigured. \n Any transient errors that occur - during the reconciliation of Machines can be added as events to - the Machine object and/or logged in the controller's output." - type: string - failedReplicas: - description: Total number of failed replicas for this loadbalancer. - format: int32 - type: integer - phase: - description: Phase represents the current phase of loadbalancer actuation. - E.g. Pending, Running, Terminating, Failed etc. - type: string - port: - description: Port is the port of the azureStackHCIloadbalancers frontend. - format: int32 - type: integer - ready: - type: boolean - readyReplicas: - description: Total number of ready (service connected) replicas for - this loadbalancer - format: int32 - type: integer - replicas: - description: Total number of non-terminated replicas for this loadbalancer - format: int32 - type: integer - selector: - description: 'Selector is the label selector in string format to avoid - introspection by clients, and is used to provide the CRD-based integration - for the scale subresource and additional integrations for things - like kubectl describe.. The string will be in the same format as - the query-param syntax. More info about label selectors: http://kubernetes.io/docs/user-guide/labels#label-selectors' - type: string - type: object - type: object - served: true - storage: false - subresources: - scale: - labelSelectorPath: .status.selector - specReplicasPath: .spec.replicas - statusReplicasPath: .status.replicas - status: {} - - additionalPrinterColumns: - - description: The current phase/status of the loadbalancer - jsonPath: .status.phase - name: Phase - type: string - - description: The frontend VIP address assigned to the loadbalancer - jsonPath: .status.address - name: IP - type: string - - description: The frontend port assigned to the loadbalancer - jsonPath: .status.port - name: Port - type: integer - - description: Total number of desired machine replicas for this loadbalancer - jsonPath: .spec.replicas - name: Replicas - type: integer - - description: Total number of machine replicas created to service this loadbalancer - jsonPath: .status.replicas - name: Created - type: integer - - description: Total number of machine replicas that are actively connected to - the loadbalancer service - jsonPath: .status.readyReplicas - name: Ready - type: integer - - description: Total number of machine replicas that are in a failed or unavailable - state - jsonPath: .status.failedReplicas - name: Unavailable - type: integer - name: v1alpha4 - schema: - openAPIV3Schema: - description: AzureStackHCILoadBalancer is the Schema for the azurestackhciloadbalancers - API - properties: - apiVersion: - description: 'APIVersion defines the versioned schema of this representation - of an object. Servers should convert recognized schemas to the latest - internal value, and may reject unrecognized values. More info: https://git.k8s.io/community/contributors/devel/sig-architecture/api-conventions.md#resources' - type: string - kind: - description: 'Kind is a string value representing the REST resource this - object represents. Servers may infer this from the endpoint the client - submits requests to. Cannot be updated. In CamelCase. More info: https://git.k8s.io/community/contributors/devel/sig-architecture/api-conventions.md#types-kinds' - type: string - metadata: - type: object - spec: - properties: - image: - description: 'Image defines information about the image to use for - VM creation. There are three ways to specify an image: by ID, by - publisher, or by Shared Image Gallery. If specifying an image by - ID, only the ID field needs to be set. If specifying an image by - publisher, the Publisher, Offer, SKU, and Version fields must be - set. If specifying an image from a Shared Image Gallery, the SubscriptionID, - ResourceGroup, Gallery, Name, and Version fields must be set.' - properties: - gallery: - type: string - id: - type: string - name: - type: string - offer: - type: string - osType: - description: OSType describes the OS type of a disk. - type: string - publisher: - type: string - resourceGroup: - type: string - sku: - type: string - subscriptionID: - type: string - version: - type: string - required: - - osType - type: object - replicas: - default: 1 - description: Number of desired loadbalancer machines. Defaults to - 1. This is a pointer to distinguish between explicit zero and not - specified. - format: int32 - type: integer - sshPublicKey: - type: string - vmSize: - type: string - required: - - image - - sshPublicKey - - vmSize - type: object - status: - properties: - address: - description: Address is the IP address of the load balancer. - type: string - conditions: - description: Conditions defines current service state of the AzureStackHCILoadBalancer. - items: - description: Condition defines an observation of a Cluster API resource - operational state. - properties: - lastTransitionTime: - description: Last time the condition transitioned from one status - to another. This should be when the underlying condition changed. - If that is not known, then using the time when the API field - changed is acceptable. - format: date-time - type: string - message: - description: A human readable message indicating details about - the transition. This field may be empty. - type: string - reason: - description: The reason for the condition's last transition - in CamelCase. The specific API may choose whether or not this - field is considered a guaranteed API. This field may not be - empty. - type: string - severity: - description: Severity provides an explicit classification of - Reason code, so the users or machines can immediately understand - the current situation and act accordingly. The Severity field - MUST be set only when Status=False. - type: string - status: - description: Status of the condition, one of True, False, Unknown. - type: string - type: - description: Type of condition in CamelCase or in foo.example.com/CamelCase. - Many .condition.type values are consistent across resources - like Available, but because arbitrary conditions can be useful - (see .node.status.conditions), the ability to deconflict is - important. - type: string - required: - - status - - type - type: object - type: array - errorMessage: - description: "ErrorMessage will be set in the event that there is - a terminal problem reconciling the Machine and will contain a more - verbose string suitable for logging and human consumption. \n This - field should not be set for transitive errors that a controller - faces that are expected to be fixed automatically over time (like - service outages), but instead indicate that something is fundamentally - wrong with the Machine's spec or the configuration of the controller, - and that manual intervention is required. Examples of terminal errors - would be invalid combinations of settings in the spec, values that - are unsupported by the controller, or the responsible controller - itself being critically misconfigured. \n Any transient errors that - occur during the reconciliation of Machines can be added as events - to the Machine object and/or logged in the controller's output." - type: string - errorReason: - description: "ErrorReason will be set in the event that there is a - terminal problem reconciling the Machine and will contain a succinct - value suitable for machine interpretation. \n This field should - not be set for transitive errors that a controller faces that are - expected to be fixed automatically over time (like service outages), - but instead indicate that something is fundamentally wrong with - the Machine's spec or the configuration of the controller, and that - manual intervention is required. Examples of terminal errors would - be invalid combinations of settings in the spec, values that are - unsupported by the controller, or the responsible controller itself - being critically misconfigured. \n Any transient errors that occur - during the reconciliation of Machines can be added as events to - the Machine object and/or logged in the controller's output." - type: string - failedReplicas: - description: Total number of failed replicas for this loadbalancer. - format: int32 - type: integer - phase: - description: Phase represents the current phase of loadbalancer actuation. - E.g. Pending, Running, Terminating, Failed etc. - type: string - port: - description: Port is the port of the azureStackHCIloadbalancers frontend. - format: int32 - type: integer - ready: - type: boolean - readyReplicas: - description: Total number of ready (service connected) replicas for - this loadbalancer - format: int32 - type: integer - replicas: - description: Total number of non-terminated replicas for this loadbalancer - format: int32 - type: integer - selector: - description: 'Selector is the label selector in string format to avoid - introspection by clients, and is used to provide the CRD-based integration - for the scale subresource and additional integrations for things - like kubectl describe.. The string will be in the same format as - the query-param syntax. More info about label selectors: http://kubernetes.io/docs/user-guide/labels#label-selectors' - type: string - type: object - type: object - served: true - storage: false - subresources: - scale: - labelSelectorPath: .status.selector - specReplicasPath: .spec.replicas - statusReplicasPath: .status.replicas - status: {} - additionalPrinterColumns: - description: The current phase/status of the loadbalancer jsonPath: .status.phase diff --git a/config/crd/bases/infrastructure.cluster.x-k8s.io_azurestackhcimachines.yaml b/config/crd/bases/infrastructure.cluster.x-k8s.io_azurestackhcimachines.yaml index 665b937..2f0d033 100644 --- a/config/crd/bases/infrastructure.cluster.x-k8s.io_azurestackhcimachines.yaml +++ b/config/crd/bases/infrastructure.cluster.x-k8s.io_azurestackhcimachines.yaml @@ -16,442 +16,6 @@ spec: singular: azurestackhcimachine scope: Namespaced versions: - - name: v1alpha3 - schema: - openAPIV3Schema: - description: AzureStackHCIMachine is the Schema for the azurestackhcimachines - API - properties: - apiVersion: - description: 'APIVersion defines the versioned schema of this representation - of an object. Servers should convert recognized schemas to the latest - internal value, and may reject unrecognized values. More info: https://git.k8s.io/community/contributors/devel/sig-architecture/api-conventions.md#resources' - type: string - kind: - description: 'Kind is a string value representing the REST resource this - object represents. Servers may infer this from the endpoint the client - submits requests to. Cannot be updated. In CamelCase. More info: https://git.k8s.io/community/contributors/devel/sig-architecture/api-conventions.md#types-kinds' - type: string - metadata: - type: object - spec: - description: AzureStackHCIMachineSpec defines the desired state of AzureStackHCIMachine - properties: - additionalSSHKeys: - items: - type: string - type: array - allocatePublicIP: - description: AllocatePublicIP allows the ability to create dynamic - public ips for machines where this value is true. - type: boolean - availabilityZone: - properties: - enabled: - type: boolean - id: - type: string - type: object - image: - description: 'Image defines information about the image to use for - VM creation. There are three ways to specify an image: by ID, by - publisher, or by Shared Image Gallery. If specifying an image by - ID, only the ID field needs to be set. If specifying an image by - publisher, the Publisher, Offer, SKU, and Version fields must be - set. If specifying an image from a Shared Image Gallery, the SubscriptionID, - ResourceGroup, Gallery, Name, and Version fields must be set.' - properties: - gallery: - type: string - id: - type: string - name: - type: string - offer: - type: string - osType: - description: OSType describes the OS type of a disk. - type: string - publisher: - type: string - resourceGroup: - type: string - sku: - type: string - subscriptionID: - type: string - version: - type: string - required: - - osType - type: object - location: - type: string - osDisk: - properties: - diskSizeGB: - format: int32 - type: integer - managedDisk: - properties: - storageAccountType: - type: string - required: - - storageAccountType - type: object - name: - type: string - osType: - description: OSType describes the OS type of a disk. - type: string - source: - type: string - required: - - diskSizeGB - - managedDisk - - name - - osType - - source - type: object - providerID: - description: ProviderID is the unique identifier as specified by the - cloud provider. - type: string - sshPublicKey: - type: string - vmSize: - type: string - required: - - location - - sshPublicKey - - vmSize - type: object - status: - description: AzureStackHCIMachineStatus defines the observed state of - AzureStackHCIMachine - properties: - addresses: - description: Addresses contains the Azure instance associated addresses. - items: - description: NodeAddress contains information for the node's address. - properties: - address: - description: The node address. - type: string - type: - description: Node address type, one of Hostname, ExternalIP - or InternalIP. - type: string - required: - - address - - type - type: object - type: array - conditions: - description: Conditions defines current service state of the AzureStackHCIMachine. - items: - description: Condition defines an observation of a Cluster API resource - operational state. - properties: - lastTransitionTime: - description: Last time the condition transitioned from one status - to another. This should be when the underlying condition changed. - If that is not known, then using the time when the API field - changed is acceptable. - format: date-time - type: string - message: - description: A human readable message indicating details about - the transition. This field may be empty. - type: string - reason: - description: The reason for the condition's last transition - in CamelCase. The specific API may choose whether or not this - field is considered a guaranteed API. This field may not be - empty. - type: string - severity: - description: Severity provides an explicit classification of - Reason code, so the users or machines can immediately understand - the current situation and act accordingly. The Severity field - MUST be set only when Status=False. - type: string - status: - description: Status of the condition, one of True, False, Unknown. - type: string - type: - description: Type of condition in CamelCase or in foo.example.com/CamelCase. - Many .condition.type values are consistent across resources - like Available, but because arbitrary conditions can be useful - (see .node.status.conditions), the ability to deconflict is - important. - type: string - required: - - status - - type - type: object - type: array - failureMessage: - description: "FailureMessage will be set in the event that there is - a terminal problem reconciling the Machine and will contain a more - verbose string suitable for logging and human consumption. \n This - field should not be set for transitive errors that a controller - faces that are expected to be fixed automatically over time (like - service outages), but instead indicate that something is fundamentally - wrong with the Machine's spec or the configuration of the controller, - and that manual intervention is required. Examples of terminal errors - would be invalid combinations of settings in the spec, values that - are unsupported by the controller, or the responsible controller - itself being critically misconfigured. \n Any transient errors that - occur during the reconciliation of Machines can be added as events - to the Machine object and/or logged in the controller's output." - type: string - failureReason: - description: "FailureReason will be set in the event that there is - a terminal problem reconciling the Machine and will contain a succinct - value suitable for machine interpretation. \n This field should - not be set for transitive errors that a controller faces that are - expected to be fixed automatically over time (like service outages), - but instead indicate that something is fundamentally wrong with - the Machine's spec or the configuration of the controller, and that - manual intervention is required. Examples of terminal errors would - be invalid combinations of settings in the spec, values that are - unsupported by the controller, or the responsible controller itself - being critically misconfigured. \n Any transient errors that occur - during the reconciliation of Machines can be added as events to - the Machine object and/or logged in the controller's output." - type: string - ready: - description: Ready is true when the provider resource is ready. - type: boolean - vmState: - description: VMState is the provisioning state of the Azure virtual - machine. - type: string - type: object - type: object - served: true - storage: false - subresources: - status: {} - - name: v1alpha4 - schema: - openAPIV3Schema: - description: AzureStackHCIMachine is the Schema for the azurestackhcimachines - API - properties: - apiVersion: - description: 'APIVersion defines the versioned schema of this representation - of an object. Servers should convert recognized schemas to the latest - internal value, and may reject unrecognized values. More info: https://git.k8s.io/community/contributors/devel/sig-architecture/api-conventions.md#resources' - type: string - kind: - description: 'Kind is a string value representing the REST resource this - object represents. Servers may infer this from the endpoint the client - submits requests to. Cannot be updated. In CamelCase. More info: https://git.k8s.io/community/contributors/devel/sig-architecture/api-conventions.md#types-kinds' - type: string - metadata: - type: object - spec: - description: AzureStackHCIMachineSpec defines the desired state of AzureStackHCIMachine - properties: - additionalSSHKeys: - items: - type: string - type: array - allocatePublicIP: - description: AllocatePublicIP allows the ability to create dynamic - public ips for machines where this value is true. - type: boolean - availabilityZone: - properties: - enabled: - type: boolean - id: - type: string - type: object - image: - description: 'Image defines information about the image to use for - VM creation. There are three ways to specify an image: by ID, by - publisher, or by Shared Image Gallery. If specifying an image by - ID, only the ID field needs to be set. If specifying an image by - publisher, the Publisher, Offer, SKU, and Version fields must be - set. If specifying an image from a Shared Image Gallery, the SubscriptionID, - ResourceGroup, Gallery, Name, and Version fields must be set.' - properties: - gallery: - type: string - id: - type: string - name: - type: string - offer: - type: string - osType: - description: OSType describes the OS type of a disk. - type: string - publisher: - type: string - resourceGroup: - type: string - sku: - type: string - subscriptionID: - type: string - version: - type: string - required: - - osType - type: object - location: - type: string - osDisk: - properties: - diskSizeGB: - format: int32 - type: integer - managedDisk: - properties: - storageAccountType: - type: string - required: - - storageAccountType - type: object - name: - type: string - osType: - description: OSType describes the OS type of a disk. - type: string - source: - type: string - required: - - diskSizeGB - - managedDisk - - name - - osType - - source - type: object - providerID: - description: ProviderID is the unique identifier as specified by the - cloud provider. - type: string - sshPublicKey: - type: string - vmSize: - type: string - required: - - location - - sshPublicKey - - vmSize - type: object - status: - description: AzureStackHCIMachineStatus defines the observed state of - AzureStackHCIMachine - properties: - addresses: - description: Addresses contains the Azure instance associated addresses. - items: - description: NodeAddress contains information for the node's address. - properties: - address: - description: The node address. - type: string - type: - description: Node address type, one of Hostname, ExternalIP - or InternalIP. - type: string - required: - - address - - type - type: object - type: array - conditions: - description: Conditions defines current service state of the AzureStackHCIMachine. - items: - description: Condition defines an observation of a Cluster API resource - operational state. - properties: - lastTransitionTime: - description: Last time the condition transitioned from one status - to another. This should be when the underlying condition changed. - If that is not known, then using the time when the API field - changed is acceptable. - format: date-time - type: string - message: - description: A human readable message indicating details about - the transition. This field may be empty. - type: string - reason: - description: The reason for the condition's last transition - in CamelCase. The specific API may choose whether or not this - field is considered a guaranteed API. This field may not be - empty. - type: string - severity: - description: Severity provides an explicit classification of - Reason code, so the users or machines can immediately understand - the current situation and act accordingly. The Severity field - MUST be set only when Status=False. - type: string - status: - description: Status of the condition, one of True, False, Unknown. - type: string - type: - description: Type of condition in CamelCase or in foo.example.com/CamelCase. - Many .condition.type values are consistent across resources - like Available, but because arbitrary conditions can be useful - (see .node.status.conditions), the ability to deconflict is - important. - type: string - required: - - status - - type - type: object - type: array - failureMessage: - description: "FailureMessage will be set in the event that there is - a terminal problem reconciling the Machine and will contain a more - verbose string suitable for logging and human consumption. \n This - field should not be set for transitive errors that a controller - faces that are expected to be fixed automatically over time (like - service outages), but instead indicate that something is fundamentally - wrong with the Machine's spec or the configuration of the controller, - and that manual intervention is required. Examples of terminal errors - would be invalid combinations of settings in the spec, values that - are unsupported by the controller, or the responsible controller - itself being critically misconfigured. \n Any transient errors that - occur during the reconciliation of Machines can be added as events - to the Machine object and/or logged in the controller's output." - type: string - failureReason: - description: "FailureReason will be set in the event that there is - a terminal problem reconciling the Machine and will contain a succinct - value suitable for machine interpretation. \n This field should - not be set for transitive errors that a controller faces that are - expected to be fixed automatically over time (like service outages), - but instead indicate that something is fundamentally wrong with - the Machine's spec or the configuration of the controller, and that - manual intervention is required. Examples of terminal errors would - be invalid combinations of settings in the spec, values that are - unsupported by the controller, or the responsible controller itself - being critically misconfigured. \n Any transient errors that occur - during the reconciliation of Machines can be added as events to - the Machine object and/or logged in the controller's output." - type: string - ready: - description: Ready is true when the provider resource is ready. - type: boolean - vmState: - description: VMState is the provisioning state of the Azure virtual - machine. - type: string - type: object - type: object - served: true - storage: false - subresources: - status: {} - name: v1beta1 schema: openAPIV3Schema: @@ -527,7 +91,9 @@ spec: items: properties: ipConfigurations: + description: 'nolint: golint' items: + description: 'nolint: golint' properties: allocation: format: int32 diff --git a/config/crd/bases/infrastructure.cluster.x-k8s.io_azurestackhcimachinetemplates.yaml b/config/crd/bases/infrastructure.cluster.x-k8s.io_azurestackhcimachinetemplates.yaml index 988733d..e0b3746 100644 --- a/config/crd/bases/infrastructure.cluster.x-k8s.io_azurestackhcimachinetemplates.yaml +++ b/config/crd/bases/infrastructure.cluster.x-k8s.io_azurestackhcimachinetemplates.yaml @@ -16,266 +16,6 @@ spec: singular: azurestackhcimachinetemplate scope: Namespaced versions: - - name: v1alpha3 - schema: - openAPIV3Schema: - description: AzureStackHCIMachineTemplate is the Schema for the azurestackhcimachinetemplates - API - properties: - apiVersion: - description: 'APIVersion defines the versioned schema of this representation - of an object. Servers should convert recognized schemas to the latest - internal value, and may reject unrecognized values. More info: https://git.k8s.io/community/contributors/devel/sig-architecture/api-conventions.md#resources' - type: string - kind: - description: 'Kind is a string value representing the REST resource this - object represents. Servers may infer this from the endpoint the client - submits requests to. Cannot be updated. In CamelCase. More info: https://git.k8s.io/community/contributors/devel/sig-architecture/api-conventions.md#types-kinds' - type: string - metadata: - type: object - spec: - description: AzureStackHCIMachineTemplateSpec defines the desired state - of AzureStackHCIMachineTemplate - properties: - template: - description: AzureStackHCIMachineTemplateResource describes the data - needed to create an AzureStackHCIMachine from a template - properties: - spec: - description: Spec is the specification of the desired behavior - of the machine. - properties: - additionalSSHKeys: - items: - type: string - type: array - allocatePublicIP: - description: AllocatePublicIP allows the ability to create - dynamic public ips for machines where this value is true. - type: boolean - availabilityZone: - properties: - enabled: - type: boolean - id: - type: string - type: object - image: - description: 'Image defines information about the image to - use for VM creation. There are three ways to specify an - image: by ID, by publisher, or by Shared Image Gallery. - If specifying an image by ID, only the ID field needs to - be set. If specifying an image by publisher, the Publisher, - Offer, SKU, and Version fields must be set. If specifying - an image from a Shared Image Gallery, the SubscriptionID, - ResourceGroup, Gallery, Name, and Version fields must be - set.' - properties: - gallery: - type: string - id: - type: string - name: - type: string - offer: - type: string - osType: - description: OSType describes the OS type of a disk. - type: string - publisher: - type: string - resourceGroup: - type: string - sku: - type: string - subscriptionID: - type: string - version: - type: string - required: - - osType - type: object - location: - type: string - osDisk: - properties: - diskSizeGB: - format: int32 - type: integer - managedDisk: - properties: - storageAccountType: - type: string - required: - - storageAccountType - type: object - name: - type: string - osType: - description: OSType describes the OS type of a disk. - type: string - source: - type: string - required: - - diskSizeGB - - managedDisk - - name - - osType - - source - type: object - providerID: - description: ProviderID is the unique identifier as specified - by the cloud provider. - type: string - sshPublicKey: - type: string - vmSize: - type: string - required: - - location - - sshPublicKey - - vmSize - type: object - required: - - spec - type: object - required: - - template - type: object - type: object - served: true - storage: false - - name: v1alpha4 - schema: - openAPIV3Schema: - description: AzureStackHCIMachineTemplate is the Schema for the azurestackhcimachinetemplates - API - properties: - apiVersion: - description: 'APIVersion defines the versioned schema of this representation - of an object. Servers should convert recognized schemas to the latest - internal value, and may reject unrecognized values. More info: https://git.k8s.io/community/contributors/devel/sig-architecture/api-conventions.md#resources' - type: string - kind: - description: 'Kind is a string value representing the REST resource this - object represents. Servers may infer this from the endpoint the client - submits requests to. Cannot be updated. In CamelCase. More info: https://git.k8s.io/community/contributors/devel/sig-architecture/api-conventions.md#types-kinds' - type: string - metadata: - type: object - spec: - description: AzureStackHCIMachineTemplateSpec defines the desired state - of AzureStackHCIMachineTemplate - properties: - template: - description: AzureStackHCIMachineTemplateResource describes the data - needed to create an AzureStackHCIMachine from a template - properties: - spec: - description: Spec is the specification of the desired behavior - of the machine. - properties: - additionalSSHKeys: - items: - type: string - type: array - allocatePublicIP: - description: AllocatePublicIP allows the ability to create - dynamic public ips for machines where this value is true. - type: boolean - availabilityZone: - properties: - enabled: - type: boolean - id: - type: string - type: object - image: - description: 'Image defines information about the image to - use for VM creation. There are three ways to specify an - image: by ID, by publisher, or by Shared Image Gallery. - If specifying an image by ID, only the ID field needs to - be set. If specifying an image by publisher, the Publisher, - Offer, SKU, and Version fields must be set. If specifying - an image from a Shared Image Gallery, the SubscriptionID, - ResourceGroup, Gallery, Name, and Version fields must be - set.' - properties: - gallery: - type: string - id: - type: string - name: - type: string - offer: - type: string - osType: - description: OSType describes the OS type of a disk. - type: string - publisher: - type: string - resourceGroup: - type: string - sku: - type: string - subscriptionID: - type: string - version: - type: string - required: - - osType - type: object - location: - type: string - osDisk: - properties: - diskSizeGB: - format: int32 - type: integer - managedDisk: - properties: - storageAccountType: - type: string - required: - - storageAccountType - type: object - name: - type: string - osType: - description: OSType describes the OS type of a disk. - type: string - source: - type: string - required: - - diskSizeGB - - managedDisk - - name - - osType - - source - type: object - providerID: - description: ProviderID is the unique identifier as specified - by the cloud provider. - type: string - sshPublicKey: - type: string - vmSize: - type: string - required: - - location - - sshPublicKey - - vmSize - type: object - required: - - spec - type: object - required: - - template - type: object - type: object - served: true - storage: false - name: v1beta1 schema: openAPIV3Schema: @@ -362,7 +102,9 @@ spec: items: properties: ipConfigurations: + description: 'nolint: golint' items: + description: 'nolint: golint' properties: allocation: format: int32 diff --git a/config/crd/bases/infrastructure.cluster.x-k8s.io_azurestackhcivirtualmachines.yaml b/config/crd/bases/infrastructure.cluster.x-k8s.io_azurestackhcivirtualmachines.yaml index bbe2252..5067678 100644 --- a/config/crd/bases/infrastructure.cluster.x-k8s.io_azurestackhcivirtualmachines.yaml +++ b/config/crd/bases/infrastructure.cluster.x-k8s.io_azurestackhcivirtualmachines.yaml @@ -16,432 +16,6 @@ spec: singular: azurestackhcivirtualmachine scope: Namespaced versions: - - name: v1alpha3 - schema: - openAPIV3Schema: - description: AzureStackHCIVirtualMachine is the Schema for the azurestackhcivirtualmachines - API - properties: - apiVersion: - description: 'APIVersion defines the versioned schema of this representation - of an object. Servers should convert recognized schemas to the latest - internal value, and may reject unrecognized values. More info: https://git.k8s.io/community/contributors/devel/sig-architecture/api-conventions.md#resources' - type: string - kind: - description: 'Kind is a string value representing the REST resource this - object represents. Servers may infer this from the endpoint the client - submits requests to. Cannot be updated. In CamelCase. More info: https://git.k8s.io/community/contributors/devel/sig-architecture/api-conventions.md#types-kinds' - type: string - metadata: - type: object - spec: - description: AzureStackHCIVirtualMachineSpec defines the desired state - of AzureStackHCIVirtualMachine - properties: - additionalSSHKeys: - items: - type: string - type: array - availabilityZone: - properties: - enabled: - type: boolean - id: - type: string - type: object - backendPoolNames: - items: - type: string - type: array - bootstrapData: - type: string - clusterName: - type: string - identity: - description: VMIdentity defines the identity of the virtual machine, - if configured. - type: string - image: - description: 'Image defines information about the image to use for - VM creation. There are three ways to specify an image: by ID, by - publisher, or by Shared Image Gallery. If specifying an image by - ID, only the ID field needs to be set. If specifying an image by - publisher, the Publisher, Offer, SKU, and Version fields must be - set. If specifying an image from a Shared Image Gallery, the SubscriptionID, - ResourceGroup, Gallery, Name, and Version fields must be set.' - properties: - gallery: - type: string - id: - type: string - name: - type: string - offer: - type: string - osType: - description: OSType describes the OS type of a disk. - type: string - publisher: - type: string - resourceGroup: - type: string - sku: - type: string - subscriptionID: - type: string - version: - type: string - required: - - osType - type: object - location: - type: string - osDisk: - properties: - diskSizeGB: - format: int32 - type: integer - managedDisk: - properties: - storageAccountType: - type: string - required: - - storageAccountType - type: object - name: - type: string - osType: - description: OSType describes the OS type of a disk. - type: string - source: - type: string - required: - - diskSizeGB - - managedDisk - - name - - osType - - source - type: object - resourceGroup: - description: come from the cluster scope for machine and lb controller - creation path - type: string - sshPublicKey: - type: string - subnetName: - type: string - vmSize: - type: string - vnetName: - type: string - required: - - clusterName - - image - - location - - resourceGroup - - sshPublicKey - - subnetName - - vmSize - - vnetName - type: object - status: - description: AzureStackHCIVirtualMachineStatus defines the observed state - of AzureStackHCIVirtualMachine - properties: - addresses: - description: Addresses contains the AzureStackHCI instance associated - addresses. - items: - description: NodeAddress contains information for the node's address. - properties: - address: - description: The node address. - type: string - type: - description: Node address type, one of Hostname, ExternalIP - or InternalIP. - type: string - required: - - address - - type - type: object - type: array - conditions: - description: Conditions defines current service state of the AzureStackHCIVirtualMachine. - items: - description: Condition defines an observation of a Cluster API resource - operational state. - properties: - lastTransitionTime: - description: Last time the condition transitioned from one status - to another. This should be when the underlying condition changed. - If that is not known, then using the time when the API field - changed is acceptable. - format: date-time - type: string - message: - description: A human readable message indicating details about - the transition. This field may be empty. - type: string - reason: - description: The reason for the condition's last transition - in CamelCase. The specific API may choose whether or not this - field is considered a guaranteed API. This field may not be - empty. - type: string - severity: - description: Severity provides an explicit classification of - Reason code, so the users or machines can immediately understand - the current situation and act accordingly. The Severity field - MUST be set only when Status=False. - type: string - status: - description: Status of the condition, one of True, False, Unknown. - type: string - type: - description: Type of condition in CamelCase or in foo.example.com/CamelCase. - Many .condition.type values are consistent across resources - like Available, but because arbitrary conditions can be useful - (see .node.status.conditions), the ability to deconflict is - important. - type: string - required: - - status - - type - type: object - type: array - failureMessage: - type: string - failureReason: - description: MachineStatusError defines errors states for Machine - objects. - type: string - ready: - description: Ready is true when the provider resource is ready. - type: boolean - vmState: - description: VMState is the provisioning state of the AzureStackHCI - virtual machine. - type: string - type: object - type: object - served: true - storage: false - subresources: - status: {} - - name: v1alpha4 - schema: - openAPIV3Schema: - description: AzureStackHCIVirtualMachine is the Schema for the azurestackhcivirtualmachines - API - properties: - apiVersion: - description: 'APIVersion defines the versioned schema of this representation - of an object. Servers should convert recognized schemas to the latest - internal value, and may reject unrecognized values. More info: https://git.k8s.io/community/contributors/devel/sig-architecture/api-conventions.md#resources' - type: string - kind: - description: 'Kind is a string value representing the REST resource this - object represents. Servers may infer this from the endpoint the client - submits requests to. Cannot be updated. In CamelCase. More info: https://git.k8s.io/community/contributors/devel/sig-architecture/api-conventions.md#types-kinds' - type: string - metadata: - type: object - spec: - description: AzureStackHCIVirtualMachineSpec defines the desired state - of AzureStackHCIVirtualMachine - properties: - additionalSSHKeys: - items: - type: string - type: array - availabilityZone: - properties: - enabled: - type: boolean - id: - type: string - type: object - backendPoolNames: - items: - type: string - type: array - bootstrapData: - type: string - clusterName: - type: string - identity: - description: VMIdentity defines the identity of the virtual machine, - if configured. - type: string - image: - description: 'Image defines information about the image to use for - VM creation. There are three ways to specify an image: by ID, by - publisher, or by Shared Image Gallery. If specifying an image by - ID, only the ID field needs to be set. If specifying an image by - publisher, the Publisher, Offer, SKU, and Version fields must be - set. If specifying an image from a Shared Image Gallery, the SubscriptionID, - ResourceGroup, Gallery, Name, and Version fields must be set.' - properties: - gallery: - type: string - id: - type: string - name: - type: string - offer: - type: string - osType: - description: OSType describes the OS type of a disk. - type: string - publisher: - type: string - resourceGroup: - type: string - sku: - type: string - subscriptionID: - type: string - version: - type: string - required: - - osType - type: object - location: - type: string - osDisk: - properties: - diskSizeGB: - format: int32 - type: integer - managedDisk: - properties: - storageAccountType: - type: string - required: - - storageAccountType - type: object - name: - type: string - osType: - description: OSType describes the OS type of a disk. - type: string - source: - type: string - required: - - diskSizeGB - - managedDisk - - name - - osType - - source - type: object - resourceGroup: - description: come from the cluster scope for machine and lb controller - creation path - type: string - sshPublicKey: - type: string - subnetName: - type: string - vmSize: - type: string - vnetName: - type: string - required: - - clusterName - - image - - location - - resourceGroup - - sshPublicKey - - subnetName - - vmSize - - vnetName - type: object - status: - description: AzureStackHCIVirtualMachineStatus defines the observed state - of AzureStackHCIVirtualMachine - properties: - addresses: - description: Addresses contains the AzureStackHCI instance associated - addresses. - items: - description: NodeAddress contains information for the node's address. - properties: - address: - description: The node address. - type: string - type: - description: Node address type, one of Hostname, ExternalIP - or InternalIP. - type: string - required: - - address - - type - type: object - type: array - conditions: - description: Conditions defines current service state of the AzureStackHCIVirtualMachine. - items: - description: Condition defines an observation of a Cluster API resource - operational state. - properties: - lastTransitionTime: - description: Last time the condition transitioned from one status - to another. This should be when the underlying condition changed. - If that is not known, then using the time when the API field - changed is acceptable. - format: date-time - type: string - message: - description: A human readable message indicating details about - the transition. This field may be empty. - type: string - reason: - description: The reason for the condition's last transition - in CamelCase. The specific API may choose whether or not this - field is considered a guaranteed API. This field may not be - empty. - type: string - severity: - description: Severity provides an explicit classification of - Reason code, so the users or machines can immediately understand - the current situation and act accordingly. The Severity field - MUST be set only when Status=False. - type: string - status: - description: Status of the condition, one of True, False, Unknown. - type: string - type: - description: Type of condition in CamelCase or in foo.example.com/CamelCase. - Many .condition.type values are consistent across resources - like Available, but because arbitrary conditions can be useful - (see .node.status.conditions), the ability to deconflict is - important. - type: string - required: - - status - - type - type: object - type: array - failureMessage: - type: string - failureReason: - description: MachineStatusError defines errors states for Machine - objects. - type: string - ready: - description: Ready is true when the provider resource is ready. - type: boolean - vmState: - description: VMState is the provisioning state of the AzureStackHCI - virtual machine. - type: string - type: object - type: object - served: true - storage: false - subresources: - status: {} - name: v1beta1 schema: openAPIV3Schema: @@ -526,7 +100,9 @@ spec: items: properties: ipConfigurations: + description: 'nolint: golint' items: + description: 'nolint: golint' properties: allocation: format: int32 diff --git a/config/crd/kustomization.yaml b/config/crd/kustomization.yaml index b462997..5e0c2e1 100644 --- a/config/crd/kustomization.yaml +++ b/config/crd/kustomization.yaml @@ -1,8 +1,6 @@ # This kustomization.yaml is not intended to be run by itself, # since it depends on service name and namespace that are out of this kustomize package. # It should be run by config/ -commonLabels: - cluster.x-k8s.io/v1beta1: v1beta1 resources: - bases/infrastructure.cluster.x-k8s.io_azurestackhcimachines.yaml @@ -12,25 +10,31 @@ resources: - bases/infrastructure.cluster.x-k8s.io_azurestackhciloadbalancers.yaml # +kubebuilder:scaffold:crdkustomizeresource -patchesStrategicMerge: # [WEBHOOK] To enable webhook, uncomment all the sections with [WEBHOOK] prefix. # patches here are for enabling the conversion webhook for each CRD -- patches/webhook_in_azurestackhcimachines.yaml -- patches/webhook_in_azurestackhciclusters.yaml -- patches/webhook_in_azurestackhcimachinetemplates.yaml -- patches/webhook_in_azurestackhcivirtualmachines.yaml -- patches/webhook_in_azurestackhciloadbalancers.yaml # +kubebuilder:scaffold:crdkustomizewebhookpatch # [CERTMANAGER] To enable cert-manager, uncomment all the sections with [CERTMANAGER] prefix. # patches here are for enabling the CA injection for each CRD -- patches/cainjection_in_azurestackhcimachines.yaml -- patches/cainjection_in_azurestackhciclusters.yaml -- patches/cainjection_in_azurestackhcimachinetemplates.yaml -- patches/cainjection_in_azurestackhcivirtualmachines.yaml -- patches/cainjection_in_azurestackhciloadbalancers.yaml # +kubebuilder:scaffold:crdkustomizecainjectionpatch # the following config is for teaching kustomize how to do kustomization for CRDs. configurations: - kustomizeconfig.yaml +apiVersion: kustomize.config.k8s.io/v1beta1 +kind: Kustomization +labels: +- includeSelectors: true + pairs: + cluster.x-k8s.io/v1beta1: v1beta1 +patches: +- path: patches/webhook_in_azurestackhcimachines.yaml +- path: patches/webhook_in_azurestackhciclusters.yaml +- path: patches/webhook_in_azurestackhcimachinetemplates.yaml +- path: patches/webhook_in_azurestackhcivirtualmachines.yaml +- path: patches/webhook_in_azurestackhciloadbalancers.yaml +- path: patches/cainjection_in_azurestackhcimachines.yaml +- path: patches/cainjection_in_azurestackhciclusters.yaml +- path: patches/cainjection_in_azurestackhcimachinetemplates.yaml +- path: patches/cainjection_in_azurestackhcivirtualmachines.yaml +- path: patches/cainjection_in_azurestackhciloadbalancers.yaml diff --git a/config/default/kustomization.yaml b/config/default/kustomization.yaml index 64b1581..bad86cd 100644 --- a/config/default/kustomization.yaml +++ b/config/default/kustomization.yaml @@ -3,56 +3,61 @@ namespace: caph-system namePrefix: caph- # Labels to add to all resources and selectors. -commonLabels: - cluster.x-k8s.io/provider: "infrastructure-azurestackhci" -bases: - - ../crd - - ../certmanager - - ../webhook - - ../rbac - - ../manager resources: - - namespace.yaml - - credentials.yaml +- namespace.yaml +- credentials.yaml +- ../crd +- ../certmanager +- ../webhook +- ../rbac +- ../manager -patchesStrategicMerge: - - manager_credentials_patch.yaml - - manager_volume_patch.yaml - - manager_auth_proxy_patch.yaml - - manager_image_patch.yaml - - manager_pull_policy.yaml - - manager_webhook_patch.yaml - - webhookcainjection_patch.yaml vars: - - name: CERTIFICATE_NAMESPACE # namespace of the certificate CR - objref: - kind: Certificate - group: cert-manager.io - version: v1 - name: serving-cert # this name should match the one in certificate.yaml - fieldref: - fieldpath: metadata.namespace - - name: CERTIFICATE_NAME - objref: - kind: Certificate - group: cert-manager.io - version: v1 - name: serving-cert # this name should match the one in certificate.yaml - - name: SERVICE_NAMESPACE # namespace of the service - objref: - kind: Service - version: v1 - name: webhook-service - fieldref: - fieldpath: metadata.namespace - - name: SERVICE_NAME - objref: - kind: Service - version: v1 - name: webhook-service +- fieldref: + fieldPath: metadata.namespace + name: CERTIFICATE_NAMESPACE + objref: + group: cert-manager.io + kind: Certificate + name: serving-cert + version: v1 +- fieldref: {} + name: CERTIFICATE_NAME + objref: + group: cert-manager.io + kind: Certificate + name: serving-cert + version: v1 +- fieldref: + fieldPath: metadata.namespace + name: SERVICE_NAMESPACE + objref: + kind: Service + name: webhook-service + version: v1 +- fieldref: {} + name: SERVICE_NAME + objref: + kind: Service + name: webhook-service + version: v1 configurations: - - kustomizeconfig.yaml +- kustomizeconfig.yaml +apiVersion: kustomize.config.k8s.io/v1beta1 +kind: Kustomization +labels: +- includeSelectors: true + pairs: + cluster.x-k8s.io/provider: infrastructure-azurestackhci +patches: +- path: manager_credentials_patch.yaml +- path: manager_volume_patch.yaml +- path: manager_auth_proxy_patch.yaml +- path: manager_image_patch.yaml +- path: manager_pull_policy.yaml +- path: manager_webhook_patch.yaml +- path: webhookcainjection_patch.yaml diff --git a/config/default/manager_auth_proxy_patch.yaml b/config/default/manager_auth_proxy_patch.yaml index 04291ea..226f8fb 100644 --- a/config/default/manager_auth_proxy_patch.yaml +++ b/config/default/manager_auth_proxy_patch.yaml @@ -10,7 +10,7 @@ spec: spec: containers: - name: kube-rbac-proxy - image: gcr.io/kubebuilder/kube-rbac-proxy:v0.4.1 + image: ecpacr.azurecr.io/kube-rbac-proxy:v0.12.0 args: - "--secure-listen-address=0.0.0.0:8443" - "--upstream=http://127.0.0.1:8080/" diff --git a/config/manager/kustomization.yaml b/config/manager/kustomization.yaml index 2926b52..99cf0f7 100644 --- a/config/manager/kustomization.yaml +++ b/config/manager/kustomization.yaml @@ -1,4 +1,4 @@ apiVersion: kustomize.config.k8s.io/v1beta1 kind: Kustomization resources: - - manager.yaml +- manager.yaml diff --git a/config/rbac/kustomization.yaml b/config/rbac/kustomization.yaml index 7205f69..ac51278 100644 --- a/config/rbac/kustomization.yaml +++ b/config/rbac/kustomization.yaml @@ -1,10 +1,10 @@ apiVersion: kustomize.config.k8s.io/v1beta1 kind: Kustomization resources: - - role.yaml - - role_binding.yaml - - leader_election_role.yaml - - leader_election_role_binding.yaml - - auth_proxy_service.yaml - - auth_proxy_role.yaml - - auth_proxy_role_binding.yaml +- role.yaml +- role_binding.yaml +- leader_election_role.yaml +- leader_election_role_binding.yaml +- auth_proxy_service.yaml +- auth_proxy_role.yaml +- auth_proxy_role_binding.yaml diff --git a/config/webhook/kustomization.yaml b/config/webhook/kustomization.yaml index fbd74f3..3334392 100644 --- a/config/webhook/kustomization.yaml +++ b/config/webhook/kustomization.yaml @@ -1,6 +1,8 @@ resources: - - manifests.yaml - - service.yaml +- manifests.yaml +- service.yaml configurations: - - kustomizeconfig.yaml \ No newline at end of file +- kustomizeconfig.yaml +apiVersion: kustomize.config.k8s.io/v1beta1 +kind: Kustomization diff --git a/controllers/azurestackhcicluster_controller.go b/controllers/azurestackhcicluster_controller.go index c176c12..5773578 100644 --- a/controllers/azurestackhcicluster_controller.go +++ b/controllers/azurestackhcicluster_controller.go @@ -261,10 +261,10 @@ func (r *AzureStackHCIClusterReconciler) deleteOrphanedMachines(clusterScope *sc } if machine == nil { // update correlation id before deletion - infrav1util.CopyCorrelationId(clusterScope.AzureStackHCICluster, azhciMachine) + infrav1util.CopyCorrelationID(clusterScope.AzureStackHCICluster, azhciMachine) if err := r.Client.Update(clusterScope.Context, azhciMachine); err != nil { if !apierrors.IsNotFound(err) { - return errors.Wrapf(err, "Failed to update AzureStackHCIMachine %s", azhciMachine) + return errors.Wrapf(err, "Failed to update AzureStackHCIMachine %s", azhciMachine.Name) } } clusterScope.Info("Deleting Orphaned Machine", "Name", azhciMachine.Name, "AzureStackHCICluster", clusterScope.AzureStackHCICluster.Name) @@ -279,7 +279,7 @@ func (r *AzureStackHCIClusterReconciler) deleteOrphanedMachines(clusterScope *sc err) if err != nil { if !apierrors.IsNotFound(err) { - return errors.Wrapf(err, "Failed to delete AzureStackHCIMachine %s", azhciMachine) + return errors.Wrapf(err, "Failed to delete AzureStackHCIMachine %s", azhciMachine.Name) } } } @@ -316,7 +316,7 @@ func (r *AzureStackHCIClusterReconciler) reconcileAzureStackHCILoadBalancer(clus azureStackHCILoadBalancer.Spec.SSHPublicKey = clusterScope.AzureStackHCILoadBalancer().SSHPublicKey azureStackHCILoadBalancer.Spec.VMSize = clusterScope.AzureStackHCILoadBalancer().VMSize azureStackHCILoadBalancer.Spec.Replicas = clusterScope.AzureStackHCILoadBalancer().Replicas - infrav1util.CopyCorrelationId(clusterScope.AzureStackHCICluster, azureStackHCILoadBalancer) + infrav1util.CopyCorrelationID(clusterScope.AzureStackHCICluster, azureStackHCILoadBalancer) return nil } @@ -378,7 +378,7 @@ func (r *AzureStackHCIClusterReconciler) reconcileDeleteAzureStackHCILoadBalance } else if azureStackHCILoadBalancer.GetDeletionTimestamp().IsZero() { // If the AzureStackHCILoadBalancer is not already marked for deletion, delete it // Update correlation id before deletion - infrav1util.CopyCorrelationId(clusterScope.AzureStackHCICluster, azureStackHCILoadBalancer) + infrav1util.CopyCorrelationID(clusterScope.AzureStackHCICluster, azureStackHCILoadBalancer) if err := r.Client.Update(clusterScope.Context, azureStackHCILoadBalancer); err != nil { if !apierrors.IsNotFound(err) { conditions.MarkFalse(clusterScope.AzureStackHCICluster, infrav1.NetworkInfrastructureReadyCondition, clusterv1.DeletionFailedReason, clusterv1.ConditionSeverityWarning, err.Error()) diff --git a/controllers/azurestackhciloadbalancer_virtualmachine.go b/controllers/azurestackhciloadbalancer_virtualmachine.go index ba62a57..60cb880 100644 --- a/controllers/azurestackhciloadbalancer_virtualmachine.go +++ b/controllers/azurestackhciloadbalancer_virtualmachine.go @@ -132,7 +132,7 @@ func (r *AzureStackHCILoadBalancerReconciler) reconcileDeleteVirtualMachines(loa for _, vm := range vmList { if vm.GetDeletionTimestamp().IsZero() { // update correlationId before deletion - infrav1util.CopyCorrelationId(loadBalancerScope.AzureStackHCILoadBalancer, vm) + infrav1util.CopyCorrelationID(loadBalancerScope.AzureStackHCILoadBalancer, vm) if err := r.Client.Update(clusterScope.Context, vm); err != nil { if !apierrors.IsNotFound(err) { return errors.Wrapf(err, "failed to update AzureStackHCIVirtualMachine %s", vm.Name) @@ -206,7 +206,7 @@ func (r *AzureStackHCILoadBalancerReconciler) createOrUpdateVirtualMachine(loadB return errors.Wrap(err, "failed to get AzureStackHCILoadBalancer image") } image.DeepCopyInto(&vm.Spec.Image) - infrav1util.CopyCorrelationId(loadBalancerScope.AzureStackHCILoadBalancer, vm) + infrav1util.CopyCorrelationID(loadBalancerScope.AzureStackHCILoadBalancer, vm) return nil } @@ -233,7 +233,7 @@ func (r *AzureStackHCILoadBalancerReconciler) createOrUpdateVirtualMachine(loadB func (r *AzureStackHCILoadBalancerReconciler) deleteVirtualMachine(lbs *scope.LoadBalancerScope, clusterScope *scope.ClusterScope, vm *infrav1.AzureStackHCIVirtualMachine) error { if vm.GetDeletionTimestamp().IsZero() { // update correlationId before deletion - infrav1util.CopyCorrelationId(lbs.AzureStackHCILoadBalancer, vm) + infrav1util.CopyCorrelationID(lbs.AzureStackHCILoadBalancer, vm) if err := r.Client.Update(clusterScope.Context, vm); err != nil { if !apierrors.IsNotFound(err) { return errors.Wrapf(err, "failed to update AzureStackHCIVirtualMachine %s", vm.Name) diff --git a/controllers/azurestackhcimachine_controller.go b/controllers/azurestackhcimachine_controller.go index b0d115d..2c8343d 100644 --- a/controllers/azurestackhcimachine_controller.go +++ b/controllers/azurestackhcimachine_controller.go @@ -326,7 +326,7 @@ func (r *AzureStackHCIMachineReconciler) reconcileVirtualMachineNormal(machineSc machineScope.AzureStackHCIMachine.Spec.NetworkInterfaces.DeepCopyInto(&vm.Spec.NetworkInterfaces) - infrav1util.CopyCorrelationId(machineScope.AzureStackHCIMachine, vm) + infrav1util.CopyCorrelationID(machineScope.AzureStackHCIMachine, vm) return nil } @@ -381,8 +381,9 @@ func (r *AzureStackHCIMachineReconciler) reconcileVirtualMachineNormal(machineSc func (r *AzureStackHCIMachineReconciler) reconcileDelete(machineScope *scope.MachineScope, clusterScope *scope.ClusterScope) (reconcile.Result, error) { machineScope.Info("Handling deleted AzureStackHCIMachine", "MachineName", machineScope.AzureStackHCIMachine.Name) - if err := r.reconcileVirtualMachineDelete(machineScope, clusterScope); err != nil { - return reconcile.Result{}, err + result, err := r.reconcileVirtualMachineDelete(machineScope, clusterScope) + if err != nil || result.RequeueAfter > 0 { + return result, err } controllerutil.RemoveFinalizer(machineScope.AzureStackHCIMachine, infrav1.MachineFinalizer) @@ -390,47 +391,51 @@ func (r *AzureStackHCIMachineReconciler) reconcileDelete(machineScope *scope.Mac return reconcile.Result{}, nil } -func (r *AzureStackHCIMachineReconciler) reconcileVirtualMachineDelete(machineScope *scope.MachineScope, clusterScope *scope.ClusterScope) error { - // use Get to find VM +func (r *AzureStackHCIMachineReconciler) reconcileVirtualMachineDelete(machineScope *scope.MachineScope, clusterScope *scope.ClusterScope) (reconcile.Result, error) { + // Use Get to find the VM vm := &infrav1.AzureStackHCIVirtualMachine{} vmName := apitypes.NamespacedName{ Namespace: clusterScope.Namespace(), Name: machineScope.Name(), } - // Use Delete to delete it if err := r.Client.Get(clusterScope.Context, vmName, vm); err != nil { - // if the VM resource is not found, it was already deleted - // otherwise return the error + // If the error is other than NotFound, return with error if !apierrors.IsNotFound(err) { - return errors.Wrapf(err, "failed to get AzureStackHCIVirtualMachine %s", vmName) - } - } else if vm.GetDeletionTimestamp().IsZero() { - // this means the VM resource was found and has not been deleted - infrav1util.CopyCorrelationId(machineScope.AzureStackHCIMachine, vm) - if err := r.Client.Update(clusterScope.Context, vm); err != nil { - if !apierrors.IsNotFound(err) { - return errors.Wrapf(err, "failed to update AzureStackHCIVirtualMachine %s", vmName) - } - } - // is this a synchronous call? - err := r.Client.Delete(clusterScope.Context, vm) - telemetry.RecordHybridAKSCRDChange( - clusterScope.GetLogger(), - clusterScope.GetCustomResourceTypeWithName(), - fmt.Sprintf("%s/%s/%s", vm.TypeMeta.Kind, vm.ObjectMeta.Namespace, vm.ObjectMeta.Name), - telemetry.Delete, - telemetry.CRD, - nil, - err) - if err != nil { - if !apierrors.IsNotFound(err) { - return errors.Wrapf(err, "failed to delete AzureStackHCIVirtualMachine %s", vmName) - } + return reconcile.Result{}, errors.Wrapf(err, "failed to get AzureStackHCIVirtualMachine %s", vmName) } + // If the VM resource is not found, no need to reconcile again + return reconcile.Result{}, nil } - return nil + // If the VM resource exists and has a deletion timestamp, it means a deletion has been requested. + // In this case, requeue the request after a delay to check again later if the deletion has been completed. + if !vm.DeletionTimestamp.IsZero() { + return reconcile.Result{RequeueAfter: 15 * time.Second}, nil + } + + // If the VM resource exists and does not have a deletion timestamp, proceed with the deletion process. + infrav1util.CopyCorrelationID(machineScope.AzureStackHCIMachine, vm) + if err := r.Client.Update(clusterScope.Context, vm); err != nil { + return reconcile.Result{}, errors.Wrapf(err, "failed to update AzureStackHCIVirtualMachine %s", vmName) + } + + // Delete the VM resource + err := r.Client.Delete(clusterScope.Context, vm) + telemetry.RecordHybridAKSCRDChange( + clusterScope.GetLogger(), + clusterScope.GetCustomResourceTypeWithName(), + fmt.Sprintf("%s/%s/%s", vm.TypeMeta.Kind, vm.ObjectMeta.Namespace, vm.ObjectMeta.Name), + telemetry.Delete, + telemetry.CRD, + nil, + err) + if err != nil && !apierrors.IsNotFound(err) { + return reconcile.Result{}, errors.Wrapf(err, "failed to delete AzureStackHCIVirtualMachine %s", vmName) + } + + // Requeue the reconciliation after a delay to check if the deletion has been completed + return reconcile.Result{RequeueAfter: 15 * time.Second}, nil } // validateUpdate checks that no immutable fields have been updated and diff --git a/controllers/azurestackhcimachine_controller_test.go b/controllers/azurestackhcimachine_controller_test.go new file mode 100644 index 0000000..3f562f5 --- /dev/null +++ b/controllers/azurestackhcimachine_controller_test.go @@ -0,0 +1,245 @@ +package controllers + +import ( + "context" + "time" + + infrav1 "github.com/microsoft/cluster-api-provider-azurestackhci/api/v1beta1" + "github.com/microsoft/cluster-api-provider-azurestackhci/cloud/scope" + mock8sclient "github.com/microsoft/cluster-api-provider-azurestackhci/test/mocks/k8s/client" + . "github.com/onsi/ginkgo/v2" + . "github.com/onsi/gomega" + "github.com/pkg/errors" + metav1 "k8s.io/apimachinery/pkg/apis/meta/v1" + apitypes "k8s.io/apimachinery/pkg/types" + clusterv1 "sigs.k8s.io/cluster-api/api/v1beta1" + ctrl "sigs.k8s.io/controller-runtime" + "sigs.k8s.io/controller-runtime/pkg/log" +) + +var _ = Describe("AzureStackHCIMachine Controller", func() { + + // Define utility constants for object names and testing timeouts/durations and intervals. + const ( + AzureStackHCIMachineName = "test-cluster-control-plane-0" + AzureStackHCIClusterName = "test-cluster" + MachineNamespace = "default" + ClusterNamespace = "default" + ) + + var ( + cluster *clusterv1.Cluster + machine *clusterv1.Machine + azureStackHCICluster *infrav1.AzureStackHCICluster + azureStackHCIMachine *infrav1.AzureStackHCIMachine + clusterScope *scope.ClusterScope + machineScope *scope.MachineScope + ) + + ctx := context.Background() + + Context("Unit tests for reconcileVirtualMachineCreate", func() { + + It("should return no requeue and no error when AzureStackHCIVirtualMachine is not found", func() { + logger := log.FromContext(ctx) + + // Create a test cluster resource + cluster = &clusterv1.Cluster{ + ObjectMeta: metav1.ObjectMeta{ + Name: AzureStackHCIClusterName, + Namespace: ClusterNamespace, + }, + } + + // Create a test AzureStackHCICluster resource + azureStackHCICluster = &infrav1.AzureStackHCICluster{ + ObjectMeta: metav1.ObjectMeta{ + Name: AzureStackHCIClusterName, + Namespace: ClusterNamespace, + }, + } + + // Create a test machine resource + machine = &clusterv1.Machine{ + ObjectMeta: metav1.ObjectMeta{ + Name: AzureStackHCIMachineName, + Namespace: MachineNamespace, + }, + } + + // Create a test AzureStackHCIMachine resource + azureStackHCIMachine = &infrav1.AzureStackHCIMachine{ + ObjectMeta: metav1.ObjectMeta{ + Name: AzureStackHCIMachineName, + Namespace: MachineNamespace, + }, + } + + // Create a new scope for the cluster(creating this way to skip some of the logic in the scope constructor) + clusterScope = &scope.ClusterScope{ + Logger: logger, + Cluster: cluster, + AzureStackHCICluster: azureStackHCICluster, + Context: ctx, + } + + // Create a new scope for the machine + machineScope = &scope.MachineScope{ + Logger: logger, + Cluster: cluster, + Machine: machine, + AzureStackHCICluster: azureStackHCICluster, + AzureStackHCIMachine: azureStackHCIMachine, + } + + reconcileResult, reconcileErr := azureStackHCIMachineReconciler.reconcileVirtualMachineDelete(machineScope, clusterScope) + Expect(reconcileResult).To(Equal(ctrl.Result{})) + Expect(reconcileErr).ToNot(HaveOccurred()) + }) + + It("should return no requeue and error if there is error in getting the AzureStackHCIVirtualMachine resource", func() { + // Create mocks client + mockClient := mock8sclient.NewMockClient(mockctrl) + + vmName := apitypes.NamespacedName{ + Namespace: clusterScope.Namespace(), + Name: machineScope.Name(), + } + + // When it asks for the AzureStackHCIVirtualMachine, return some error + mockClient.EXPECT().Get(ctx, vmName, &infrav1.AzureStackHCIVirtualMachine{}).Return(errors.New("test error")) + azureStackHCIMachineReconciler.Client = mockClient + + reconcileResult, reconcileErr := azureStackHCIMachineReconciler.reconcileVirtualMachineDelete(machineScope, clusterScope) + Expect(reconcileResult).To(Equal(ctrl.Result{})) + Expect(reconcileErr).To(HaveOccurred()) + Expect(reconcileErr.Error()).To(ContainSubstring("test error")) + }) + + It("should return requeue and no error if AzureStackHCIVirtualMachine is found and deletion timestamp is not zero", func() { + // Create mocks client + mockClient := mock8sclient.NewMockClient(mockctrl) + + vmName := apitypes.NamespacedName{ + Namespace: clusterScope.Namespace(), + Name: machineScope.Name(), + } + + // Set the deletion timestamp to nil + azureStackHCIVirtualMachine := &infrav1.AzureStackHCIVirtualMachine{ + ObjectMeta: metav1.ObjectMeta{ + Name: machineScope.Name(), + Namespace: machineScope.Namespace(), + DeletionTimestamp: &metav1.Time{Time: time.Now()}, + }, + } + + // When it asks for the AzureStackHCIVirtualMachine, return the test resource + mockClient.EXPECT().Get(ctx, vmName, &infrav1.AzureStackHCIVirtualMachine{}).Return(nil).SetArg(2, *azureStackHCIVirtualMachine) + azureStackHCIMachineReconciler.Client = mockClient + + reconcileResult, reconcileErr := azureStackHCIMachineReconciler.reconcileVirtualMachineDelete(machineScope, clusterScope) + Expect(reconcileResult).To(Equal(ctrl.Result{RequeueAfter: 15 * time.Second})) + Expect(reconcileErr).ToNot(HaveOccurred()) + }) + + It("should return no requeue and error if AzureStackHCIVirtualMachine is found, deletion timestamp is zero and update returns error", func() { + // Create mocks client + mockClient := mock8sclient.NewMockClient(mockctrl) + + vmName := apitypes.NamespacedName{ + Namespace: clusterScope.Namespace(), + Name: machineScope.Name(), + } + + // Set the deletion timestamp to nil + azureStackHCIVirtualMachine := &infrav1.AzureStackHCIVirtualMachine{ + ObjectMeta: metav1.ObjectMeta{ + Name: machineScope.Name(), + Namespace: machineScope.Namespace(), + DeletionTimestamp: nil, + }, + } + + // When it asks for the AzureStackHCIVirtualMachine, return the test resource + mockClient.EXPECT().Get(ctx, vmName, &infrav1.AzureStackHCIVirtualMachine{}).Return(nil).SetArg(2, *azureStackHCIVirtualMachine) + + // When it asks to update the AzureStackHCIVirtualMachine, return some error + mockClient.EXPECT().Update(ctx, azureStackHCIVirtualMachine).Return(errors.New("test error")) + azureStackHCIMachineReconciler.Client = mockClient + + reconcileResult, reconcileErr := azureStackHCIMachineReconciler.reconcileVirtualMachineDelete(machineScope, clusterScope) + Expect(reconcileResult).To(Equal(ctrl.Result{})) + Expect(reconcileErr).To(HaveOccurred()) + Expect(reconcileErr.Error()).To(ContainSubstring("test error")) + }) + + It("should return no requeue and error if AzureStackHCIVirtualMachine is found, deletion timestamp is zero, update returns no error and delete returns error", func() { + // Create mocks client + mockClient := mock8sclient.NewMockClient(mockctrl) + + vmName := apitypes.NamespacedName{ + Namespace: clusterScope.Namespace(), + Name: machineScope.Name(), + } + + // Set the deletion timestamp to nil + azureStackHCIVirtualMachine := &infrav1.AzureStackHCIVirtualMachine{ + ObjectMeta: metav1.ObjectMeta{ + Name: machineScope.Name(), + Namespace: machineScope.Namespace(), + DeletionTimestamp: nil, + }, + } + + // When it asks for the AzureStackHCIVirtualMachine, return the test resource + mockClient.EXPECT().Get(ctx, vmName, &infrav1.AzureStackHCIVirtualMachine{}).Return(nil).SetArg(2, *azureStackHCIVirtualMachine) + + // When it asks to update the AzureStackHCIVirtualMachine, return no error + mockClient.EXPECT().Update(ctx, azureStackHCIVirtualMachine).Return(nil) + + // When it asks to delete the AzureStackHCIVirtualMachine, return some error + mockClient.EXPECT().Delete(ctx, azureStackHCIVirtualMachine).Return(errors.New("test error")) + azureStackHCIMachineReconciler.Client = mockClient + + reconcileResult, reconcileErr := azureStackHCIMachineReconciler.reconcileVirtualMachineDelete(machineScope, clusterScope) + Expect(reconcileResult).To(Equal(ctrl.Result{})) + Expect(reconcileErr).To(HaveOccurred()) + Expect(reconcileErr.Error()).To(ContainSubstring("test error")) + }) + + It("should return requeue and no error if AzureStackHCIVirtualMachine is found, deletion timestamp is zero, update returns no error and delete returns no error", func() { + // Create mocks client + mockClient := mock8sclient.NewMockClient(mockctrl) + + vmName := apitypes.NamespacedName{ + Namespace: clusterScope.Namespace(), + Name: machineScope.Name(), + } + + // Set the deletion timestamp to nil + azureStackHCIVirtualMachine := &infrav1.AzureStackHCIVirtualMachine{ + ObjectMeta: metav1.ObjectMeta{ + Name: machineScope.Name(), + Namespace: machineScope.Namespace(), + DeletionTimestamp: nil, + }, + } + + // When it asks for the AzureStackHCIVirtualMachine, return the test resource + mockClient.EXPECT().Get(ctx, vmName, &infrav1.AzureStackHCIVirtualMachine{}).Return(nil).SetArg(2, *azureStackHCIVirtualMachine) + + // When it asks to update the AzureStackHCIVirtualMachine, return no error + mockClient.EXPECT().Update(ctx, azureStackHCIVirtualMachine).Return(nil) + + // When it asks to delete the AzureStackHCIVirtualMachine, return no error + mockClient.EXPECT().Delete(ctx, azureStackHCIVirtualMachine).Return(nil) + azureStackHCIMachineReconciler.Client = mockClient + + reconcileResult, reconcileErr := azureStackHCIMachineReconciler.reconcileVirtualMachineDelete(machineScope, clusterScope) + Expect(reconcileResult).To(Equal(ctrl.Result{RequeueAfter: 15 * time.Second})) + Expect(reconcileErr).ToNot(HaveOccurred()) + }) + + }) +}) diff --git a/controllers/controllers_suite_test.go b/controllers/controllers_suite_test.go new file mode 100644 index 0000000..cae2a0a --- /dev/null +++ b/controllers/controllers_suite_test.go @@ -0,0 +1,129 @@ +package controllers + +import ( + "io/ioutil" + "net/http" + "os" + "path/filepath" + "testing" + "time" + + infrav1 "github.com/microsoft/cluster-api-provider-azurestackhci/api/v1beta1" + . "github.com/onsi/ginkgo/v2" + . "github.com/onsi/gomega" + "github.com/onsi/gomega/gexec" + "k8s.io/client-go/kubernetes/scheme" + "k8s.io/client-go/tools/record" + clusterv1 "sigs.k8s.io/cluster-api/api/v1beta1" + ctrl "sigs.k8s.io/controller-runtime" + "sigs.k8s.io/controller-runtime/pkg/client" + "sigs.k8s.io/controller-runtime/pkg/controller" + "sigs.k8s.io/controller-runtime/pkg/envtest" + logf "sigs.k8s.io/controller-runtime/pkg/log" + "sigs.k8s.io/controller-runtime/pkg/log/zap" + + "github.com/golang/mock/gomock" +) + +var ( + testEnv *envtest.Environment + k8sClient client.Client + fakeRecorder *record.FakeRecorder + mockctrl *gomock.Controller + + azureStackHCIMachineReconciler AzureStackHCIMachineReconciler +) + +func TestClusterApiProviderAzureStackHCIControllerSuite(t *testing.T) { + RegisterFailHandler(Fail) + RunSpecs(t, "ClusterApiProviderAzureStackHCIController Suite") +} + +var _ = BeforeSuite(func() { + logf.SetLogger(zap.New(zap.WriteTo(GinkgoWriter), zap.UseDevMode(true))) + + // Download the Machine CRD + resp, err := http.Get("https://raw.githubusercontent.com/kubernetes-sigs/cluster-api/master/config/crd/bases/cluster.x-k8s.io_machines.yaml") + Expect(err).NotTo(HaveOccurred()) + defer resp.Body.Close() + + // Write the CRD to a temporary file + tmpfile, err := ioutil.TempFile("", "machine.crd.*.yaml") + Expect(err).NotTo(HaveOccurred()) + defer os.Remove(tmpfile.Name()) // clean up + + b, err := ioutil.ReadAll(resp.Body) + Expect(err).NotTo(HaveOccurred()) + + _, err = tmpfile.Write(b) + Expect(err).NotTo(HaveOccurred()) + err = tmpfile.Close() + Expect(err).NotTo(HaveOccurred()) + + // Add the path to the temporary file to the CRDDirectoryPaths + testEnv = &envtest.Environment{ + CRDDirectoryPaths: []string{filepath.Join("..", "config", "crd", "bases"), tmpfile.Name()}, + ErrorIfCRDPathMissing: true, + } + + By("bootstrapping test environment") + cfg, err := testEnv.Start() + if err != nil { + logf.Log.Error(err, "unable to start test environment") + os.Exit(1) + } + + err = infrav1.AddToScheme(scheme.Scheme) + Expect(err).NotTo(HaveOccurred()) + + err = clusterv1.AddToScheme(scheme.Scheme) + Expect(err).NotTo(HaveOccurred()) + + // +kubebuilder:scaffold:scheme + + k8sClient, err = client.New(cfg, client.Options{Scheme: scheme.Scheme}) + Expect(err).NotTo(HaveOccurred()) + Expect(k8sClient).NotTo(BeNil()) + + k8sManager, err := ctrl.NewManager(cfg, ctrl.Options{ + Scheme: scheme.Scheme, + }) + Expect(err).ToNot(HaveOccurred()) + + fakeRecorder = record.NewFakeRecorder(100) + + err = (&AzureStackHCIClusterReconciler{ + Client: k8sClient, + Log: ctrl.Log.WithName("controllers").WithName("AzureStackHCICluster"), + Recorder: fakeRecorder, + }).SetupWithManager(k8sManager, controller.Options{}) + Expect(err).ToNot(HaveOccurred()) + + azureStackHCIMachineReconciler = AzureStackHCIMachineReconciler{ + Client: k8sClient, + Log: ctrl.Log.WithName("controllers").WithName("AzureStackHCIMachine"), + Recorder: fakeRecorder, + } + err = azureStackHCIMachineReconciler.SetupWithManager(k8sManager, controller.Options{}) + Expect(err).ToNot(HaveOccurred()) + + // Start the manager/controller + go func() { + defer GinkgoRecover() + err = k8sManager.Start(ctrl.SetupSignalHandler()) + gexec.KillAndWait(4 * time.Second) + + err := testEnv.Stop() + Expect(err).ToNot(HaveOccurred()) + }() +}) + +var _ = BeforeEach(func() { + mockctrl = gomock.NewController(GinkgoT()) +}) + +var _ = AfterEach(func() { + GinkgoRecover() + + mockctrl.Finish() +}) diff --git a/go.mod b/go.mod index 139cb27..09c9ad2 100644 --- a/go.mod +++ b/go.mod @@ -6,8 +6,11 @@ require ( github.com/Azure/go-autorest/autorest/to v0.4.0 github.com/blang/semver v3.5.1+incompatible github.com/go-logr/logr v1.2.3 + github.com/golang/mock v1.6.0 github.com/microsoft/moc v0.11.0-alpha.37 github.com/microsoft/moc-sdk-for-go v0.11.1-alpha.14 + github.com/onsi/ginkgo/v2 v2.9.2 + github.com/onsi/gomega v1.27.5 github.com/pkg/errors v0.9.1 github.com/spf13/pflag v1.0.5 golang.org/x/crypto v0.17.0 @@ -39,6 +42,7 @@ require ( github.com/go-openapi/jsonpointer v0.19.5 // indirect github.com/go-openapi/jsonreference v0.20.0 // indirect github.com/go-openapi/swag v0.22.3 // indirect + github.com/go-task/slim-sprig v0.0.0-20230315185526-52ccab3ef572 // indirect github.com/gobuffalo/flect v1.0.2 // indirect github.com/gogo/protobuf v1.3.2 // indirect github.com/golang-jwt/jwt/v4 v4.5.0 // indirect @@ -47,6 +51,7 @@ require ( github.com/google/gnostic v0.6.9 // indirect github.com/google/go-cmp v0.5.9 // indirect github.com/google/gofuzz v1.2.0 // indirect + github.com/google/pprof v0.0.0-20210720184732-4bb14d4b1be1 // indirect github.com/google/uuid v1.3.1 // indirect github.com/hashicorp/hcl v1.0.0 // indirect github.com/hectane/go-acl v0.0.0-20190604041725-da78bae5fc95 // indirect @@ -61,7 +66,6 @@ require ( github.com/modern-go/concurrent v0.0.0-20180306012644-bacd9c7ef1dd // indirect github.com/modern-go/reflect2 v1.0.2 // indirect github.com/munnerz/goautoneg v0.0.0-20191010083416-a7dc8b61c822 // indirect - github.com/onsi/gomega v1.27.5 // indirect github.com/pelletier/go-toml/v2 v2.1.0 // indirect github.com/prometheus/client_golang v1.14.0 // indirect github.com/prometheus/client_model v0.4.0 // indirect @@ -84,6 +88,7 @@ require ( golang.org/x/term v0.15.0 // indirect golang.org/x/text v0.14.0 // indirect golang.org/x/time v0.3.0 // indirect + golang.org/x/tools v0.13.0 // indirect gomodules.xyz/jsonpatch/v2 v2.2.0 // indirect google.golang.org/appengine v1.6.7 // indirect google.golang.org/genproto/googleapis/api v0.0.0-20231127180814-3a041ad873d4 // indirect diff --git a/go.sum b/go.sum index 15212af..1c42df9 100644 --- a/go.sum +++ b/go.sum @@ -925,6 +925,7 @@ github.com/go-pdf/fpdf v0.6.0/go.mod h1:HzcnA+A23uwogo0tp9yU+l3V+KXhiESpt1PMayhO github.com/go-stack/stack v1.8.0/go.mod h1:v0f6uXyyMGvRgIKkXu+yp6POWl0qKG85gN/melR3HDY= github.com/go-task/slim-sprig v0.0.0-20210107165309-348f09dbbbc0/go.mod h1:fyg7847qk6SyHyPtNmDHnmrv/HOrqktSC+C9fM+CJOE= github.com/go-task/slim-sprig v0.0.0-20230315185526-52ccab3ef572 h1:tfuBGBXKqDEevZMzYi5KSi8KkcZtzBcTgAUUtapy0OI= +github.com/go-task/slim-sprig v0.0.0-20230315185526-52ccab3ef572/go.mod h1:9Pwr4B2jHnOSGXyyzV8ROjYa2ojvAY6HCGYYfMoC3Ls= github.com/gobuffalo/flect v1.0.2 h1:eqjPGSo2WmjgY2XlpGwo2NXgL3RucAKo4k4qQMNA5sA= github.com/gobuffalo/flect v1.0.2/go.mod h1:A5msMlrHtLqh9umBSnvabjsMrCcCpAyzglnDvkbYKHs= github.com/goccy/go-json v0.9.11/go.mod h1:6MelG93GURQebXPDq3khkgXZkazVtN9CRI+MGFi0w8I= @@ -1210,9 +1211,9 @@ github.com/nxadm/tail v1.4.8/go.mod h1:+ncqLTQzXmGhMZNUePPaPqPvBxHAIsmXswZKocGu+ github.com/onsi/ginkgo v1.6.0/go.mod h1:lLunBs/Ym6LB5Z9jYTR76FiuTmxDTDusOGeTQH+WWjE= github.com/onsi/ginkgo v1.12.1/go.mod h1:zj2OWP4+oCPe1qIXoGWkgMRwljMUYCdkwsT2108oapk= github.com/onsi/ginkgo v1.16.2/go.mod h1:CObGmKUOKaSC0RjmoAK7tKyn4Azo5P2IWuoMnvwxz1E= -github.com/onsi/ginkgo v1.16.4 h1:29JGrr5oVBm5ulCWet69zQkzWipVXIol6ygQUe/EzNc= github.com/onsi/ginkgo v1.16.4/go.mod h1:dX+/inL/fNMqNlz0e9LfyB9TswhZpCVdJM/Z6Vvnwo0= github.com/onsi/ginkgo/v2 v2.9.2 h1:BA2GMJOtfGAfagzYtrAlufIP0lq6QERkFmHLMLPwFSU= +github.com/onsi/ginkgo/v2 v2.9.2/go.mod h1:WHcJJG2dIlcCqVfBAwUCrJxSPFb6v4azBwgxeMeDuts= github.com/onsi/gomega v1.7.1/go.mod h1:XdKZgCCFLUoM/7CFJVPcG8C1xQ1AJ0vpAezJrB7JYyY= github.com/onsi/gomega v1.10.1/go.mod h1:iN09h71vgCQne3DLsj+A5owkum+a2tYe+TOCB1ybHNo= github.com/onsi/gomega v1.13.0/go.mod h1:lRk9szgn8TxENtWd0Tp4c3wjlRfMTMH27I+3Je41yGY= @@ -1426,6 +1427,7 @@ golang.org/x/mod v0.7.0/go.mod h1:iBbtSCu2XBx23ZKBPSOrRkjjQPZFPuis4dIYUhu/chs= golang.org/x/mod v0.8.0/go.mod h1:iBbtSCu2XBx23ZKBPSOrRkjjQPZFPuis4dIYUhu/chs= golang.org/x/mod v0.9.0/go.mod h1:iBbtSCu2XBx23ZKBPSOrRkjjQPZFPuis4dIYUhu/chs= golang.org/x/mod v0.10.0/go.mod h1:iBbtSCu2XBx23ZKBPSOrRkjjQPZFPuis4dIYUhu/chs= +golang.org/x/mod v0.12.0 h1:rmsUpXtvNzj340zd98LZ4KntptpfRHwpFOHG188oHXc= golang.org/x/mod v0.12.0/go.mod h1:iBbtSCu2XBx23ZKBPSOrRkjjQPZFPuis4dIYUhu/chs= golang.org/x/net v0.17.0 h1:pVaXccu2ozPjCXewfr1S7xza/zcXTity9cCdXQYSjIM= golang.org/x/net v0.17.0/go.mod h1:NxSsAGuq816PNPmqtQdLE42eU2Fs7NoRIZrHJAlaCOE= diff --git a/hack/config/kustomization.yaml b/hack/config/kustomization.yaml index c195b1c..1d0f803 100644 --- a/hack/config/kustomization.yaml +++ b/hack/config/kustomization.yaml @@ -1,10 +1,12 @@ -bases: - - ../../config -patchesJson6902: - - target: - group: apps - version: v1 - kind: Deployment - name: controller-manager - path: manager_image_patch.yaml +apiVersion: kustomize.config.k8s.io/v1beta1 +kind: Kustomization +resources: +- ../../config +patches: +- path: manager_image_patch.yaml + target: + group: apps + kind: Deployment + name: controller-manager + version: v1 diff --git a/pkg/auth/auth.go b/pkg/auth/auth.go index dfdc59f..b037897 100644 --- a/pkg/auth/auth.go +++ b/pkg/auth/auth.go @@ -65,10 +65,10 @@ func GetAuthorizerFromKubernetesCluster(ctx context.Context, cloudFqdn string) ( return nil, errors.Wrap(err, "failed to create a client") } - return ReconcileAzureStackHCIAccess(logger, ctx, c, cloudFqdn) + return ReconcileAzureStackHCIAccess(ctx, logger, c, cloudFqdn) } -func ReconcileAzureStackHCIAccess(logger logr.Logger, ctx context.Context, cli client.Client, cloudFqdn string) (auth.Authorizer, error) { +func ReconcileAzureStackHCIAccess(ctx context.Context, logger logr.Logger, cli client.Client, cloudFqdn string) (auth.Authorizer, error) { wssdconfigpath := os.Getenv("WSSD_CONFIG_PATH") if wssdconfigpath == "" { @@ -78,9 +78,9 @@ func ReconcileAzureStackHCIAccess(logger logr.Logger, ctx context.Context, cli c if strings.ToLower(os.Getenv("WSSD_DEBUG_MODE")) != "on" { _, err := os.Stat(wssdconfigpath) if err != nil { - return login(logger, ctx, cli, cloudFqdn) + return login(ctx, logger, cli, cloudFqdn) } - go UpdateLoginConfig(logger, ctx, cli) + go UpdateLoginConfig(ctx, logger, cli) } authorizer, err := auth.NewAuthorizerFromEnvironment(cloudFqdn) if err != nil { @@ -89,12 +89,12 @@ func ReconcileAzureStackHCIAccess(logger logr.Logger, ctx context.Context, cli c return nil, errors.Wrap(err, "error: new authorizer failed") } // Login if certificate expired - return login(logger, ctx, cli, cloudFqdn) + return login(ctx, logger, cli, cloudFqdn) } return authorizer, nil } -func UpdateLoginConfig(logger logr.Logger, ctx context.Context, cli client.Client) { +func UpdateLoginConfig(ctx context.Context, logger logr.Logger, cli client.Client) { secret, err := GetSecret(ctx, cli, AzHCIAccessCreds) if err != nil { logger.Error(err, "error: failed to create wssd session, missing login credentials secret") @@ -119,7 +119,7 @@ func UpdateLoginConfig(logger logr.Logger, ctx context.Context, cli client.Clien } -func login(logger logr.Logger, ctx context.Context, cli client.Client, cloudFqdn string) (auth.Authorizer, error) { +func login(ctx context.Context, logger logr.Logger, cli client.Client, cloudFqdn string) (auth.Authorizer, error) { wssdconfigpath := os.Getenv("WSSD_CONFIG_PATH") if wssdconfigpath == "" { return nil, errors.New("ReconcileAzureStackHCIAccess: Environment variable WSSD_CONFIG_PATH is not set") diff --git a/pkg/cloudtest/cloudtest.go b/pkg/cloudtest/cloudtest.go deleted file mode 100644 index ec90591..0000000 --- a/pkg/cloudtest/cloudtest.go +++ /dev/null @@ -1,51 +0,0 @@ -/* -Copyright 2020 The Kubernetes Authors. -Portions Copyright © Microsoft Corporation. - -Licensed under the Apache License, Version 2.0 (the "License"); -you may not use this file except in compliance with the License. -You may obtain a copy of the License at - - http://www.apache.org/licenses/LICENSE-2.0 - -Unless required by applicable law or agreed to in writing, software -distributed under the License is distributed on an "AS IS" BASIS, -WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. -See the License for the specific language governing permissions and -limitations under the License. -*/ - -package cloudtest - -import ( - "encoding/json" - "testing" - - "github.com/go-logr/logr" - "k8s.io/apimachinery/pkg/runtime" -) - -// RuntimeRawExtension takes anything and turns it into a *runtime.RawExtension. -// This is helpful for creating clusterv1.Cluster/Machine objects that need -// a specific AzureClusterProviderSpec or Status. -func RuntimeRawExtension(t *testing.T, p interface{}) *runtime.RawExtension { - t.Helper() - out, err := json.Marshal(p) - if err != nil { - t.Fatal(err) - } - return &runtime.RawExtension{ - Raw: out, - } -} - -// Log implements logr.Logger for testing. Do not use if you actually want to -// test log messages. -type Log struct{} - -func (l *Log) Error(err error, msg string, keysAndValues ...interface{}) {} -func (l *Log) V(level int) logr.InfoLogger { return l } -func (l *Log) WithValues(keysAndValues ...interface{}) logr.Logger { return l } -func (l *Log) WithName(name string) logr.Logger { return l } -func (l *Log) Info(msg string, keysAndValues ...interface{}) {} -func (l *Log) Enabled() bool { return false } diff --git a/pkg/util/util.go b/pkg/util/util.go index 12563a2..5206a94 100644 --- a/pkg/util/util.go +++ b/pkg/util/util.go @@ -58,7 +58,7 @@ func GetReconcileID(ctx context.Context) types.UID { return reconcileID } -func CopyCorrelationId(source, target client.Object) { +func CopyCorrelationID(source, target client.Object) { sourceAnnotations := source.GetAnnotations() if len(sourceAnnotations) == 0 { return diff --git a/templates/flavors/base/kustomization.yaml b/templates/flavors/base/kustomization.yaml index f732f57..d4200bf 100644 --- a/templates/flavors/base/kustomization.yaml +++ b/templates/flavors/base/kustomization.yaml @@ -3,4 +3,4 @@ apiVersion: kustomize.config.k8s.io/v1beta1 kind: Kustomization namespace: default resources: - - cluster-template.yaml \ No newline at end of file +- cluster-template.yaml diff --git a/templates/flavors/default/kustomization.yaml b/templates/flavors/default/kustomization.yaml index 94dea73..9eb53c5 100644 --- a/templates/flavors/default/kustomization.yaml +++ b/templates/flavors/default/kustomization.yaml @@ -1,4 +1,6 @@ resources: - - ../base -patchesStrategicMerge: - - patches/default.yaml \ No newline at end of file +- ../base +apiVersion: kustomize.config.k8s.io/v1beta1 +kind: Kustomization +patches: +- path: patches/default.yaml diff --git a/templates/flavors/mgmt/kustomization.yaml b/templates/flavors/mgmt/kustomization.yaml index b2a2842..eef95b0 100644 --- a/templates/flavors/mgmt/kustomization.yaml +++ b/templates/flavors/mgmt/kustomization.yaml @@ -1,3 +1,5 @@ resources: - - ../base - - mgmt-machine.yaml \ No newline at end of file +- ../base +- mgmt-machine.yaml +apiVersion: kustomize.config.k8s.io/v1beta1 +kind: Kustomization diff --git a/test/mocks/externalmocks.go b/test/mocks/externalmocks.go new file mode 100644 index 0000000..c3552d1 --- /dev/null +++ b/test/mocks/externalmocks.go @@ -0,0 +1,5 @@ +package test + +// controller-runtime k8s client + +//go:generate mockgen -destination=k8s/client/client.go sigs.k8s.io/controller-runtime/pkg/client Client diff --git a/test/mocks/k8s/client/client.go b/test/mocks/k8s/client/client.go new file mode 100644 index 0000000..837b9d8 --- /dev/null +++ b/test/mocks/k8s/client/client.go @@ -0,0 +1,228 @@ +// Code generated by MockGen. DO NOT EDIT. +// Source: sigs.k8s.io/controller-runtime/pkg/client (interfaces: Client) + +// Package mock_client is a generated GoMock package. +package mock_client + +import ( + context "context" + reflect "reflect" + + gomock "github.com/golang/mock/gomock" + meta "k8s.io/apimachinery/pkg/api/meta" + runtime "k8s.io/apimachinery/pkg/runtime" + types "k8s.io/apimachinery/pkg/types" + client "sigs.k8s.io/controller-runtime/pkg/client" +) + +// MockClient is a mock of Client interface. +type MockClient struct { + ctrl *gomock.Controller + recorder *MockClientMockRecorder +} + +// MockClientMockRecorder is the mock recorder for MockClient. +type MockClientMockRecorder struct { + mock *MockClient +} + +// NewMockClient creates a new mock instance. +func NewMockClient(ctrl *gomock.Controller) *MockClient { + mock := &MockClient{ctrl: ctrl} + mock.recorder = &MockClientMockRecorder{mock} + return mock +} + +// EXPECT returns an object that allows the caller to indicate expected use. +func (m *MockClient) EXPECT() *MockClientMockRecorder { + return m.recorder +} + +// Create mocks base method. +func (m *MockClient) Create(arg0 context.Context, arg1 client.Object, arg2 ...client.CreateOption) error { + m.ctrl.T.Helper() + varargs := []interface{}{arg0, arg1} + for _, a := range arg2 { + varargs = append(varargs, a) + } + ret := m.ctrl.Call(m, "Create", varargs...) + ret0, _ := ret[0].(error) + return ret0 +} + +// Create indicates an expected call of Create. +func (mr *MockClientMockRecorder) Create(arg0, arg1 interface{}, arg2 ...interface{}) *gomock.Call { + mr.mock.ctrl.T.Helper() + varargs := append([]interface{}{arg0, arg1}, arg2...) + return mr.mock.ctrl.RecordCallWithMethodType(mr.mock, "Create", reflect.TypeOf((*MockClient)(nil).Create), varargs...) +} + +// Delete mocks base method. +func (m *MockClient) Delete(arg0 context.Context, arg1 client.Object, arg2 ...client.DeleteOption) error { + m.ctrl.T.Helper() + varargs := []interface{}{arg0, arg1} + for _, a := range arg2 { + varargs = append(varargs, a) + } + ret := m.ctrl.Call(m, "Delete", varargs...) + ret0, _ := ret[0].(error) + return ret0 +} + +// Delete indicates an expected call of Delete. +func (mr *MockClientMockRecorder) Delete(arg0, arg1 interface{}, arg2 ...interface{}) *gomock.Call { + mr.mock.ctrl.T.Helper() + varargs := append([]interface{}{arg0, arg1}, arg2...) + return mr.mock.ctrl.RecordCallWithMethodType(mr.mock, "Delete", reflect.TypeOf((*MockClient)(nil).Delete), varargs...) +} + +// DeleteAllOf mocks base method. +func (m *MockClient) DeleteAllOf(arg0 context.Context, arg1 client.Object, arg2 ...client.DeleteAllOfOption) error { + m.ctrl.T.Helper() + varargs := []interface{}{arg0, arg1} + for _, a := range arg2 { + varargs = append(varargs, a) + } + ret := m.ctrl.Call(m, "DeleteAllOf", varargs...) + ret0, _ := ret[0].(error) + return ret0 +} + +// DeleteAllOf indicates an expected call of DeleteAllOf. +func (mr *MockClientMockRecorder) DeleteAllOf(arg0, arg1 interface{}, arg2 ...interface{}) *gomock.Call { + mr.mock.ctrl.T.Helper() + varargs := append([]interface{}{arg0, arg1}, arg2...) + return mr.mock.ctrl.RecordCallWithMethodType(mr.mock, "DeleteAllOf", reflect.TypeOf((*MockClient)(nil).DeleteAllOf), varargs...) +} + +// Get mocks base method. +func (m *MockClient) Get(arg0 context.Context, arg1 types.NamespacedName, arg2 client.Object, arg3 ...client.GetOption) error { + m.ctrl.T.Helper() + varargs := []interface{}{arg0, arg1, arg2} + for _, a := range arg3 { + varargs = append(varargs, a) + } + ret := m.ctrl.Call(m, "Get", varargs...) + ret0, _ := ret[0].(error) + return ret0 +} + +// Get indicates an expected call of Get. +func (mr *MockClientMockRecorder) Get(arg0, arg1, arg2 interface{}, arg3 ...interface{}) *gomock.Call { + mr.mock.ctrl.T.Helper() + varargs := append([]interface{}{arg0, arg1, arg2}, arg3...) + return mr.mock.ctrl.RecordCallWithMethodType(mr.mock, "Get", reflect.TypeOf((*MockClient)(nil).Get), varargs...) +} + +// List mocks base method. +func (m *MockClient) List(arg0 context.Context, arg1 client.ObjectList, arg2 ...client.ListOption) error { + m.ctrl.T.Helper() + varargs := []interface{}{arg0, arg1} + for _, a := range arg2 { + varargs = append(varargs, a) + } + ret := m.ctrl.Call(m, "List", varargs...) + ret0, _ := ret[0].(error) + return ret0 +} + +// List indicates an expected call of List. +func (mr *MockClientMockRecorder) List(arg0, arg1 interface{}, arg2 ...interface{}) *gomock.Call { + mr.mock.ctrl.T.Helper() + varargs := append([]interface{}{arg0, arg1}, arg2...) + return mr.mock.ctrl.RecordCallWithMethodType(mr.mock, "List", reflect.TypeOf((*MockClient)(nil).List), varargs...) +} + +// Patch mocks base method. +func (m *MockClient) Patch(arg0 context.Context, arg1 client.Object, arg2 client.Patch, arg3 ...client.PatchOption) error { + m.ctrl.T.Helper() + varargs := []interface{}{arg0, arg1, arg2} + for _, a := range arg3 { + varargs = append(varargs, a) + } + ret := m.ctrl.Call(m, "Patch", varargs...) + ret0, _ := ret[0].(error) + return ret0 +} + +// Patch indicates an expected call of Patch. +func (mr *MockClientMockRecorder) Patch(arg0, arg1, arg2 interface{}, arg3 ...interface{}) *gomock.Call { + mr.mock.ctrl.T.Helper() + varargs := append([]interface{}{arg0, arg1, arg2}, arg3...) + return mr.mock.ctrl.RecordCallWithMethodType(mr.mock, "Patch", reflect.TypeOf((*MockClient)(nil).Patch), varargs...) +} + +// RESTMapper mocks base method. +func (m *MockClient) RESTMapper() meta.RESTMapper { + m.ctrl.T.Helper() + ret := m.ctrl.Call(m, "RESTMapper") + ret0, _ := ret[0].(meta.RESTMapper) + return ret0 +} + +// RESTMapper indicates an expected call of RESTMapper. +func (mr *MockClientMockRecorder) RESTMapper() *gomock.Call { + mr.mock.ctrl.T.Helper() + return mr.mock.ctrl.RecordCallWithMethodType(mr.mock, "RESTMapper", reflect.TypeOf((*MockClient)(nil).RESTMapper)) +} + +// Scheme mocks base method. +func (m *MockClient) Scheme() *runtime.Scheme { + m.ctrl.T.Helper() + ret := m.ctrl.Call(m, "Scheme") + ret0, _ := ret[0].(*runtime.Scheme) + return ret0 +} + +// Scheme indicates an expected call of Scheme. +func (mr *MockClientMockRecorder) Scheme() *gomock.Call { + mr.mock.ctrl.T.Helper() + return mr.mock.ctrl.RecordCallWithMethodType(mr.mock, "Scheme", reflect.TypeOf((*MockClient)(nil).Scheme)) +} + +// Status mocks base method. +func (m *MockClient) Status() client.SubResourceWriter { + m.ctrl.T.Helper() + ret := m.ctrl.Call(m, "Status") + ret0, _ := ret[0].(client.SubResourceWriter) + return ret0 +} + +// Status indicates an expected call of Status. +func (mr *MockClientMockRecorder) Status() *gomock.Call { + mr.mock.ctrl.T.Helper() + return mr.mock.ctrl.RecordCallWithMethodType(mr.mock, "Status", reflect.TypeOf((*MockClient)(nil).Status)) +} + +// SubResource mocks base method. +func (m *MockClient) SubResource(arg0 string) client.SubResourceClient { + m.ctrl.T.Helper() + ret := m.ctrl.Call(m, "SubResource", arg0) + ret0, _ := ret[0].(client.SubResourceClient) + return ret0 +} + +// SubResource indicates an expected call of SubResource. +func (mr *MockClientMockRecorder) SubResource(arg0 interface{}) *gomock.Call { + mr.mock.ctrl.T.Helper() + return mr.mock.ctrl.RecordCallWithMethodType(mr.mock, "SubResource", reflect.TypeOf((*MockClient)(nil).SubResource), arg0) +} + +// Update mocks base method. +func (m *MockClient) Update(arg0 context.Context, arg1 client.Object, arg2 ...client.UpdateOption) error { + m.ctrl.T.Helper() + varargs := []interface{}{arg0, arg1} + for _, a := range arg2 { + varargs = append(varargs, a) + } + ret := m.ctrl.Call(m, "Update", varargs...) + ret0, _ := ret[0].(error) + return ret0 +} + +// Update indicates an expected call of Update. +func (mr *MockClientMockRecorder) Update(arg0, arg1 interface{}, arg2 ...interface{}) *gomock.Call { + mr.mock.ctrl.T.Helper() + varargs := append([]interface{}{arg0, arg1}, arg2...) + return mr.mock.ctrl.RecordCallWithMethodType(mr.mock, "Update", reflect.TypeOf((*MockClient)(nil).Update), varargs...) +}