diff --git a/Makefile b/Makefile index 2ab199f5..4db8840a 100644 --- a/Makefile +++ b/Makefile @@ -67,6 +67,7 @@ test: manifests generate fmt vet setup-envtest ## Run tests. # CertManager is installed by default; skip with: # - CERT_MANAGER_INSTALL_SKIP=true KIND_CLUSTER ?= multigres-operator-test-e2e +KIND_CLUSTER_DEV ?= multigres-operator-dev .PHONY: setup-test-e2e setup-test-e2e: ## Set up a Kind cluster for e2e tests if it does not exist @@ -91,6 +92,38 @@ test-e2e: setup-test-e2e manifests generate fmt vet ## Run the e2e tests. Expect cleanup-test-e2e: ## Tear down the Kind cluster used for e2e tests @$(KIND) delete cluster --name $(KIND_CLUSTER) +## TODO: This is only temporary, we should have more streamlined setup. +.PHONY: deploy-kind +deploy-kind: docker-build kustomize ## Build, load image to kind, install CRDs, and deploy operator to kind cluster + @echo "Setting up kind cluster '$(KIND_CLUSTER_DEV)'..." + @command -v $(KIND) >/dev/null 2>&1 || { \ + echo "Kind is not installed. Please install Kind manually."; \ + exit 1; \ + } + @case "$$($(KIND) get clusters)" in \ + *"$(KIND_CLUSTER_DEV)"*) \ + echo "Kind cluster '$(KIND_CLUSTER_DEV)' already exists." ;; \ + *) \ + echo "Creating Kind cluster '$(KIND_CLUSTER_DEV)'..."; \ + $(KIND) create cluster --name $(KIND_CLUSTER_DEV) ;; \ + esac + @echo "Loading image $(IMG) into kind cluster..." + $(KIND) load docker-image $(IMG) --name $(KIND_CLUSTER_DEV) + @echo "Installing CRDs..." + $(KUBECTL) --context kind-$(KIND_CLUSTER_DEV) apply -k config/crd + @echo "Deploying operator..." + cd config/deploy && $(KUSTOMIZE) edit set image controller=$(IMG) + $(KUBECTL) --context kind-$(KIND_CLUSTER_DEV) apply -k config/deploy + @echo "Deployment complete! Use 'kubectl --context kind-$(KIND_CLUSTER_DEV) get pods -n multigres-operator' to check status" + +.PHONY: undeploy-kind +undeploy-kind: ## Undeploy operator from kind cluster + $(KUBECTL) --context kind-$(KIND_CLUSTER_DEV) delete --ignore-not-found=true -k config/deploy + +.PHONY: cleanup-kind +cleanup-kind: ## Delete the kind cluster used for development + @$(KIND) delete cluster --name $(KIND_CLUSTER_DEV) + .PHONY: lint lint: golangci-lint ## Run golangci-lint linter $(GOLANGCI_LINT) run diff --git a/config/deploy/clusterrole.yaml b/config/deploy/clusterrole.yaml new file mode 100644 index 00000000..43996051 --- /dev/null +++ b/config/deploy/clusterrole.yaml @@ -0,0 +1,24 @@ +apiVersion: rbac.authorization.k8s.io/v1 +kind: ClusterRole +metadata: + name: multigres-operator +rules: + # MultiGres CRDs + - apiGroups: ["multigres.com"] + resources: ["*"] + verbs: ["*"] + # Core resources + - apiGroups: [""] + resources: ["pods", "services", "configmaps", "secrets", "persistentvolumeclaims"] + verbs: ["*"] + - apiGroups: ["apps"] + resources: ["deployments", "statefulsets"] + verbs: ["*"] + # Events for status updates + - apiGroups: [""] + resources: ["events"] + verbs: ["create", "patch"] + # Leases for leader election + - apiGroups: ["coordination.k8s.io"] + resources: ["leases"] + verbs: ["*"] diff --git a/config/deploy/clusterrolebinding.yaml b/config/deploy/clusterrolebinding.yaml new file mode 100644 index 00000000..9336ccd2 --- /dev/null +++ b/config/deploy/clusterrolebinding.yaml @@ -0,0 +1,12 @@ +apiVersion: rbac.authorization.k8s.io/v1 +kind: ClusterRoleBinding +metadata: + name: multigres-operator +roleRef: + apiGroup: rbac.authorization.k8s.io + kind: ClusterRole + name: multigres-operator +subjects: + - kind: ServiceAccount + name: multigres-operator + namespace: multigres-operator diff --git a/config/deploy/deployment.yaml b/config/deploy/deployment.yaml new file mode 100644 index 00000000..f3579ee4 --- /dev/null +++ b/config/deploy/deployment.yaml @@ -0,0 +1,61 @@ +apiVersion: apps/v1 +kind: Deployment +metadata: + name: multigres-operator + namespace: multigres-operator + labels: + app: multigres-operator +spec: + replicas: 1 + selector: + matchLabels: + app: multigres-operator + template: + metadata: + labels: + app: multigres-operator + spec: + serviceAccountName: multigres-operator + containers: + - name: manager + image: controller:latest + imagePullPolicy: IfNotPresent + command: + - /manager + args: + - --leader-elect + - --health-probe-bind-address=:8081 + ports: + - name: health + containerPort: 8081 + protocol: TCP + livenessProbe: + httpGet: + path: /healthz + port: 8081 + initialDelaySeconds: 15 + periodSeconds: 20 + readinessProbe: + httpGet: + path: /readyz + port: 8081 + initialDelaySeconds: 5 + periodSeconds: 10 + resources: + limits: + cpu: 500m + memory: 256Mi + requests: + cpu: 100m + memory: 128Mi + securityContext: + allowPrivilegeEscalation: false + capabilities: + drop: + - ALL + readOnlyRootFilesystem: true + runAsNonRoot: true + securityContext: + runAsNonRoot: true + seccompProfile: + type: RuntimeDefault diff --git a/config/deploy/kustomization.yaml b/config/deploy/kustomization.yaml new file mode 100644 index 00000000..24de158c --- /dev/null +++ b/config/deploy/kustomization.yaml @@ -0,0 +1,14 @@ +apiVersion: kustomize.config.k8s.io/v1beta1 +kind: Kustomization + +resources: +- namespace.yaml +- serviceaccount.yaml +- clusterrole.yaml +- clusterrolebinding.yaml +- deployment.yaml + +images: +- name: controller + newName: controller + newTag: latest diff --git a/config/deploy/namespace.yaml b/config/deploy/namespace.yaml new file mode 100644 index 00000000..18ac27f2 --- /dev/null +++ b/config/deploy/namespace.yaml @@ -0,0 +1,4 @@ +apiVersion: v1 +kind: Namespace +metadata: + name: multigres-operator diff --git a/config/deploy/serviceaccount.yaml b/config/deploy/serviceaccount.yaml new file mode 100644 index 00000000..239f4052 --- /dev/null +++ b/config/deploy/serviceaccount.yaml @@ -0,0 +1,5 @@ +apiVersion: v1 +kind: ServiceAccount +metadata: + name: multigres-operator + namespace: multigres-operator diff --git a/config/rbac/kustomization.yaml b/config/rbac/kustomization.yaml index 7f61e08a..0e9f46ed 100644 --- a/config/rbac/kustomization.yaml +++ b/config/rbac/kustomization.yaml @@ -22,7 +22,7 @@ resources: # default, aiding admins in cluster management. Those roles are # not used by the kubebuilder itself. You can comment the following lines # if you do not want those helpers be installed with your Project. -- guestbook_admin_role.yaml -- guestbook_editor_role.yaml -- guestbook_viewer_role.yaml +# - guestbook_admin_role.yaml +# - guestbook_editor_role.yaml +# - guestbook_viewer_role.yaml diff --git a/config/samples/etcd-minimal.yaml b/config/samples/etcd-minimal.yaml new file mode 100644 index 00000000..49e7ae39 --- /dev/null +++ b/config/samples/etcd-minimal.yaml @@ -0,0 +1,7 @@ +apiVersion: multigres.com/v1alpha1 +kind: Etcd +metadata: + name: etcd-sample + namespace: default +spec: + cellName: cell-1 diff --git a/devshell.nix b/devshell.nix index fbaec1b5..5ddf1b1e 100644 --- a/devshell.nix +++ b/devshell.nix @@ -8,6 +8,7 @@ pkgs.mkShell { docker-buildx kubectl kind + kustomize golangci-lint # For some script use cases