From 7c1c509750b7a68e0a30106db49eb94c8d091525 Mon Sep 17 00:00:00 2001 From: Benjamin Blattberg Date: Thu, 3 Oct 2024 14:50:53 -0500 Subject: [PATCH] Create optional backups flag (#103) Make backups optional for create As of PGO v5.7, backups can now be disabled or enabled at any point in the postgrescluster's lifecycle. We don't want to bring that functionality entire over into the CLI, but we do want to start by allowing users to create a cluster without backups. Since this is a not recommended for production, we require confirmation. This should not block later changes that may allow users to disable/enable backups after creation. Issue: [PGO-1530] --- Makefile | 3 ++- .../reference/pgo_create_postgrescluster.md | 5 ++++ internal/cmd/create.go | 27 +++++++++++++++++++ .../00--create_cluster.yaml | 5 ++++ .../e2e/create-without-backups/00-errors.yaml | 20 ++++++++++++++ .../01--create_cluster.yaml | 5 ++++ .../e2e/create-without-backups/01-assert.yaml | 20 ++++++++++++++ .../e2e/create-without-backups/02-errors.yaml | 4 +++ 8 files changed, 88 insertions(+), 1 deletion(-) create mode 100644 testing/kuttl/e2e/create-without-backups/00--create_cluster.yaml create mode 100644 testing/kuttl/e2e/create-without-backups/00-errors.yaml create mode 100644 testing/kuttl/e2e/create-without-backups/01--create_cluster.yaml create mode 100644 testing/kuttl/e2e/create-without-backups/01-assert.yaml create mode 100644 testing/kuttl/e2e/create-without-backups/02-errors.yaml diff --git a/Makefile b/Makefile index 42c42d69..0604eb8b 100644 --- a/Makefile +++ b/Makefile @@ -34,6 +34,7 @@ help: ## Display this help .PHONY: all all: check build +bin/kubectl-pgo-%: ## Build the binary bin/kubectl-pgo-%: go.* $(shell ls -1 cmd/**/*.go internal/**/*.go) GOOS=$(word 1,$(subst -, ,$*)) GOARCH=$(word 2,$(subst -, ,$*)) $(GO_BUILD) -o $@ ./cmd/kubectl-pgo @@ -43,7 +44,7 @@ build: bin/kubectl-pgo-$(subst $(eval) ,-,$(shell $(GO) env GOOS GOARCH)) ln -fs $(notdir $<) ./bin/kubectl-pgo .PHONY: check -check: +check: ## Run tests $(GO_TEST) -cover ./... # Expects operator to be running diff --git a/docs/content/reference/pgo_create_postgrescluster.md b/docs/content/reference/pgo_create_postgrescluster.md index 4c0a55ec..f877c78d 100644 --- a/docs/content/reference/pgo_create_postgrescluster.md +++ b/docs/content/reference/pgo_create_postgrescluster.md @@ -26,6 +26,10 @@ pgo create postgrescluster CLUSTER_NAME [flags] # Create a postgrescluster with Postgres 15 pgo create postgrescluster hippo --pg-major-version 15 +# Create a postgrescluster with backups disabled (only available in CPK v5.7+) +# Requires confirmation +pgo create postgrescluster hippo --disable-backups + ``` ### Example output ``` @@ -35,6 +39,7 @@ postgresclusters/hippo created ### Options ``` + --disable-backups Disable backups -h, --help help for postgrescluster --pg-major-version int Set the Postgres major version ``` diff --git a/internal/cmd/create.go b/internal/cmd/create.go index bc29a4ad..612585bb 100644 --- a/internal/cmd/create.go +++ b/internal/cmd/create.go @@ -17,6 +17,7 @@ package cmd import ( "context" "fmt" + "os" "strconv" "github.com/spf13/cobra" @@ -26,6 +27,7 @@ import ( "github.com/crunchydata/postgres-operator-client/internal" "github.com/crunchydata/postgres-operator-client/internal/apis/postgres-operator.crunchydata.com/v1beta1" + "github.com/crunchydata/postgres-operator-client/internal/util" ) // newCreateCommand returns the create subcommand of the PGO plugin. @@ -66,9 +68,16 @@ func newCreateClusterCommand(config *internal.Config) *cobra.Command { cmd.Flags().IntVar(&pgMajorVersion, "pg-major-version", 0, "Set the Postgres major version") cobra.CheckErr(cmd.MarkFlagRequired("pg-major-version")) + var backupsDisabled bool + cmd.Flags().BoolVar(&backupsDisabled, "disable-backups", false, "Disable backups") + cmd.Example = internal.FormatExample(`# Create a postgrescluster with Postgres 15 pgo create postgrescluster hippo --pg-major-version 15 +# Create a postgrescluster with backups disabled (only available in CPK v5.7+) +# Requires confirmation +pgo create postgrescluster hippo --disable-backups + ### Example output postgresclusters/hippo created`) @@ -92,6 +101,24 @@ postgresclusters/hippo created`) return err } + if backupsDisabled { + fmt.Print("WARNING: Running a production postgrescluster without backups " + + "is not recommended. \nAre you sure you want " + + "to continue without backups? (yes/no): ") + var confirmed *bool + for i := 0; confirmed == nil && i < 10; i++ { + // retry 10 times or until a confirmation is given or denied, + // whichever comes first + confirmed = util.Confirm(os.Stdin, os.Stdout) + } + + if confirmed == nil || !*confirmed { + return nil + } + + unstructured.RemoveNestedField(cluster.Object, "spec", "backups") + } + u, err := client. Namespace(namespace). Create(ctx, cluster, config.Patch.CreateOptions(metav1.CreateOptions{})) diff --git a/testing/kuttl/e2e/create-without-backups/00--create_cluster.yaml b/testing/kuttl/e2e/create-without-backups/00--create_cluster.yaml new file mode 100644 index 00000000..e73f82e9 --- /dev/null +++ b/testing/kuttl/e2e/create-without-backups/00--create_cluster.yaml @@ -0,0 +1,5 @@ +--- +apiVersion: kuttl.dev/v1beta1 +kind: TestStep +commands: +- script: echo no | kubectl-pgo --namespace $NAMESPACE create postgrescluster --pg-major-version 16 --disable-backups created-without-backups diff --git a/testing/kuttl/e2e/create-without-backups/00-errors.yaml b/testing/kuttl/e2e/create-without-backups/00-errors.yaml new file mode 100644 index 00000000..9c1bd6b4 --- /dev/null +++ b/testing/kuttl/e2e/create-without-backups/00-errors.yaml @@ -0,0 +1,20 @@ +apiVersion: postgres-operator.crunchydata.com/v1beta1 +kind: PostgresCluster +metadata: + name: created-without-backups +spec: + instances: + - dataVolumeClaimSpec: + accessModes: + - "ReadWriteOnce" + resources: + requests: + storage: 1Gi + replicas: 1 + postgresVersion: 16 +status: + instances: + - name: "00" + readyReplicas: 1 + replicas: 1 + updatedReplicas: 1 diff --git a/testing/kuttl/e2e/create-without-backups/01--create_cluster.yaml b/testing/kuttl/e2e/create-without-backups/01--create_cluster.yaml new file mode 100644 index 00000000..de0af849 --- /dev/null +++ b/testing/kuttl/e2e/create-without-backups/01--create_cluster.yaml @@ -0,0 +1,5 @@ +--- +apiVersion: kuttl.dev/v1beta1 +kind: TestStep +commands: +- script: echo yes | kubectl-pgo --namespace $NAMESPACE create postgrescluster --pg-major-version 16 --disable-backups created-without-backups diff --git a/testing/kuttl/e2e/create-without-backups/01-assert.yaml b/testing/kuttl/e2e/create-without-backups/01-assert.yaml new file mode 100644 index 00000000..9c1bd6b4 --- /dev/null +++ b/testing/kuttl/e2e/create-without-backups/01-assert.yaml @@ -0,0 +1,20 @@ +apiVersion: postgres-operator.crunchydata.com/v1beta1 +kind: PostgresCluster +metadata: + name: created-without-backups +spec: + instances: + - dataVolumeClaimSpec: + accessModes: + - "ReadWriteOnce" + resources: + requests: + storage: 1Gi + replicas: 1 + postgresVersion: 16 +status: + instances: + - name: "00" + readyReplicas: 1 + replicas: 1 + updatedReplicas: 1 diff --git a/testing/kuttl/e2e/create-without-backups/02-errors.yaml b/testing/kuttl/e2e/create-without-backups/02-errors.yaml new file mode 100644 index 00000000..6ae43673 --- /dev/null +++ b/testing/kuttl/e2e/create-without-backups/02-errors.yaml @@ -0,0 +1,4 @@ +apiVersion: apps/v1 +kind: StatefulSet +metadata: + name: created-without-backups-repo-host