diff --git a/.github/workflows/ci.yml b/.github/workflows/ci.yml new file mode 100644 index 0000000..5b4e72c --- /dev/null +++ b/.github/workflows/ci.yml @@ -0,0 +1,41 @@ +name: CI + +on: + pull_request: + workflow_dispatch: + +jobs: + ci: + runs-on: ubuntu-latest + steps: + - name: Checkout + uses: actions/checkout@v4 + # We need the full history for the commitlint task + with: + fetch-depth: 0 + ref: ${{ github.event.pull_request.head.sha }} + - name: Install Task + uses: arduino/setup-task@v2 + - name: Install Dagger + env: + # renovate: datasource=github-tags depName=dagger/dagger versioning=semver + DAGGER_VERSION: 0.12.4 + run: | + curl -L https://dl.dagger.io/dagger/install.sh | BIN_DIR=$HOME/.local/bin sh + - name: Run CI task + run: | + task ci + - name: Write manifest + run: | + task manifest + - name: Publish images + env: + REGISTRY_USER: ${{ github.actor }} + REGISTRY_PASSWORD: ${{ secrets.REPO_PAT }} + run: | + task publish + - name: Attach manifest to workflow run + uses: actions/upload-artifact@v4 + with: + name: manifest.yaml + path: ./manifest.yaml diff --git a/.github/workflows/release-please.yml b/.github/workflows/release-please.yml new file mode 100644 index 0000000..73e70f5 --- /dev/null +++ b/.github/workflows/release-please.yml @@ -0,0 +1,59 @@ +name: release-please + +on: + push: + branches: + - main + +permissions: + contents: write + pull-requests: write + +jobs: + release-please: + runs-on: ubuntu-latest + steps: + # TODO: googleapis/release-please-action cannot sign commits yet. + # We'll use the cli until there's a fix for + # https://github.com/googleapis/release-please/issues/2280. + - uses: actions/setup-node@v4 + with: + node-version: 20 + - name: Checkout + uses: actions/checkout@v4 + - name: Install Task + uses: arduino/setup-task@v2 + - name: Install Dagger + env: + # renovate: datasource=github-tags depName=dagger/dagger versioning=semver + DAGGER_VERSION: 0.12.2 + run: | + curl -L https://dl.dagger.io/dagger/install.sh | BIN_DIR=$HOME/.local/bin sh + - name: Create image and manifest + env: + REGISTRY_USER: ${{ github.actor }} + REGISTRY_PASSWORD: ${{ secrets.REPO_PAT }} + run: | + task publish + task manifest + - name: Attach manifest to workflow run + uses: actions/upload-artifact@v4 + with: + name: manifest.yaml + path: ./manifest.yaml + # TODO: remove bump-minor-pre-major when in production. It prevents + # release-please from bumping the major version on breaking changes. + # TODO: remove release-as after first release. Used to set the first + # release version, which would default to 1.0.0. Set the version + # manually also for 1.0.0. + - name: Run release-please + run: | + npx release-please release-pr \ + --token="${{ secrets.REPO_PAT }}" \ + --repo-url="${{ github.repository }}" \ + --bump-minor-pre-major=true \ + --release-as=0.1.0 \ + --signoff "Peggie "; + npx release-please github-release \ + --token="${{ secrets.REPO_PAT }}" \ + --repo-url="${{ github.repository }}" diff --git a/.github/workflows/release-publish.yml b/.github/workflows/release-publish.yml new file mode 100644 index 0000000..b01afa4 --- /dev/null +++ b/.github/workflows/release-publish.yml @@ -0,0 +1,31 @@ +name: Release Publish Artifacts +on: + release: + types: [published] + +jobs: + release-publish-artifacts: + runs-on: ubuntu-latest + steps: + - name: Checkout + uses: actions/checkout@v4 + - name: Install Task + uses: arduino/setup-task@v2 + - name: Install Dagger + env: + # renovate: datasource=github-tags depName=dagger/dagger versioning=semver + DAGGER_VERSION: 0.12.4 + run: | + curl -L https://dl.dagger.io/dagger/install.sh | BIN_DIR=$HOME/.local/bin sh + - name: Create image and manifest + env: + REGISTRY_USER: ${{ github.actor }} + REGISTRY_PASSWORD: ${{ secrets.REPO_PAT }} + run: | + task publish + task manifest + - name: Attach manifest to release + env: + GITHUB_TOKEN: ${{ secrets.REPO_PAT }} + run: | + task upload-manifest-to-release diff --git a/.gitignore b/.gitignore index b6aa873..5743676 100644 --- a/.gitignore +++ b/.gitignore @@ -3,4 +3,5 @@ dist/ .env .vscode/ .idea/ -cnpg-i-hello-world +.task/ +manifest.yaml diff --git a/.golangci.yml b/.golangci.yml index 0914885..2ce4758 100644 --- a/.golangci.yml +++ b/.golangci.yml @@ -8,108 +8,30 @@ linters-settings: - prefix(github.com/cloudnative-pg/cnpg-i-hello-world) - blank - dot + nlreturn: + # Size of the block (including return statement that is still "OK") + # so no return split required. + # Default: 1 + block-size: 3 linters: - # please, do not use `enable-all`: it's deprecated and will be removed soon. - # inverted configuration with `enable-all` and `disable` is not scalable during updates of golangci-lint - disable-all: true - enable: - - asciicheck - - bodyclose - - dogsled - - dupl - - durationcheck - - errcheck - - exportloopref - - gci - - gocognit - - goconst - - gocritic - - gocyclo - - gofmt - - gofumpt - - goheader - - goimports - - gomoddirectives - - gomodguard - - goprintffuncname - - gosec - - gosimple - - govet - - importas - - ineffassign - - lll - - makezero - - misspell - - nakedret - - nestif - - prealloc - - predeclared - - revive - - rowserrcheck - - sqlclosecheck - - staticcheck - - stylecheck - - thelper - - tparallel - - typecheck - - unconvert - - unparam - - unused - - wastedassign - - whitespace - - # to be checked: - # - errorlint - # - forbidigo - # - forcetypeassert - # - goerr113 - # - ifshort - # - nilerr - # - nlreturn - # - noctx - # - nolintlint - # - paralleltest - # - promlinter - # - tagliatelle - # - wrapcheck - - # don't enable: - # - cyclop - # - depguard - # - exhaustive - # - exhaustivestruct - # - funlen - # - gochecknoglobals - # - gochecknoinits - # - godot - # - godox - # - gomnd - # - testpackage - # - wsl - - # deprecated: - # - deadcode - # - golint - # - interfacer - # - maligned - # - scopelint - # - structcheck - # - varcheck + enable-all: true + disable: + - depguard + - execinquery + - exhaustive + - exhaustruct + - err113 + - forbidigo + - funlen + - gochecknoglobals + - gochecknoinits + - godot + - gomnd + - ireturn + - varnamelen + - wrapcheck + - wsl run: - skip-files: "zz_generated.*" - -issues: - exclude-rules: - # Exclude lll issues for lines with long annotations - - linters: - - lll - source: "//\\s*\\+" - # We have no control of this in zz_generated files and it looks like that excluding those files is not enough - # so we disable "ST1016: methods on the same type should have the same receiver name" in api directory - - linters: - - stylecheck - text: "ST1016:" - path: api/ - exclude-use-default: false + timeout: 10m diff --git a/.release-please-manifest.json b/.release-please-manifest.json new file mode 100644 index 0000000..e18ee07 --- /dev/null +++ b/.release-please-manifest.json @@ -0,0 +1,3 @@ +{ + ".": "0.0.0" +} diff --git a/.spellcheck.yaml b/.spellcheck.yaml index 4fd0e12..f7c0e13 100644 --- a/.spellcheck.yaml +++ b/.spellcheck.yaml @@ -1,26 +1,19 @@ matrix: -- name: Python Source - sources: - - ./**/*.go - - ./**/*.md - dictionary: - wordlists: - - .wordlist.txt - aspell: - lang: en - d: en_US - pipeline: - - pyspelling.filters.python: - - pyspelling.filters.context: - context_visible_first: true - escapes: \\[\\`~] - delimiters: - # Ignore multiline content between fences (fences can have 3 or more back ticks) - # ``` - # content - # ``` - - open: '(?s)^(?P *`{3,})$' - close: '^(?P=open)$' - # Ignore text between inline back ticks - - open: '(?P`+)' - close: '(?P=open)' + - name: Markdown + sources: + # Ignore the autogenerated markdown files + - ./**/*.md|!./CHANGELOG.md|!./vendor/** + dictionary: + wordlists: + - .wordlist.txt + aspell: + lang: en + d: en_US + pipeline: + - pyspelling.filters.markdown: + - pyspelling.filters.html: + comments: false + ignores: + - ':matches(code, pre)' + - 'code' + - 'pre' diff --git a/.wordlist.txt b/.wordlist.txt index 0963143..a665e01 100644 --- a/.wordlist.txt +++ b/.wordlist.txt @@ -1,4 +1,25 @@ -sidebarToggle -pvc -ClientConn -NewStream +ClusterLifecycle +CloudNativePG +CNPG +finalizers +GRPC +kubernetes +Kubernetes +lifecycle +MutateCluster +OperatorMutateClusterRequest +OperatorMutateClusterResult +OperatorValidateClusterChangeRequest +OperatorValidateClusterChangeResult +OperatorValidateClusterCreateRequest +OperatorValidateClusterCreateResult +pluginhelper +Postgres +reconcilers +rpc +struct +ValidateClusterChange +ValidateClusterCreate +ValidateCreate +webhook +webhooks diff --git a/Makefile b/Makefile deleted file mode 100644 index 1c78305..0000000 --- a/Makefile +++ /dev/null @@ -1,20 +0,0 @@ -.PHONY: run -run: build image - ./scripts/run.sh - -.PHONY: build -build: - ./scripts/build_proto.sh - ./scripts/build.sh - -.PHONY: check -check: - ./scripts/check.sh - -.PHONY: image -image: - ./scripts/image.sh - -.PHONY: test -test: - ./scripts/test.sh diff --git a/README.md b/README.md index aafc10b..570a2bb 100644 --- a/README.md +++ b/README.md @@ -1,7 +1,7 @@ # CNPG-I-EXAMPLE A "hello world" example implementation of the -[Cloud Native Postgres](https://github.com/cloudnative-pg/cloudnative-pg/) +[CloudNativePG](https://github.com/cloudnative-pg/cloudnative-pg/) plugin interface [CNPG-I](https://github.com/cloudnative-pg/cnpg-i). - [Concepts](doc/concepts.md) diff --git a/Taskfile.yml b/Taskfile.yml new file mode 100644 index 0000000..6734c37 --- /dev/null +++ b/Taskfile.yml @@ -0,0 +1,185 @@ +version: 3 + +tasks: + lint: + desc: Run golangci-lint + env: + # renovate: datasource=git-refs depName=golangci-lint lookupName=https://github.com/sagikazarmark/daggerverse currentValue=main + DAGGER_GOLANGCI_LINT_SHA: 447a362a4fb98d05bbbeb8a290ed9aff7c5eccab + cmds: + - > + GITHUB_REF= dagger -s call -m github.com/sagikazarmark/daggerverse/golangci-lint@${DAGGER_GOLANGCI_LINT_SHA} + run --source . --config .golangci.yml stdout + sources: + - ./**/*.go + + spellcheck: + desc: Run spellcheck + env: + # renovate: datasource=git-refs depName=spellcheck lookupName=https://github.com/cloudnative-pg/daggerverse currentValue=main + DAGGER_SPELLCHECK_SHA: 23ffda6100005d626fddb569e8e471587bf32cbf + cmds: + - > + GITHUB_REF= dagger -s call -m github.com/cloudnative-pg/daggerverse/spellcheck@${DAGGER_SPELLCHECK_SHA} + spellcheck --source . with-exec --use-entrypoint --args="" stdout + sources: + - ./**/*.md + - .spellcheck.yaml + - .wordlist.txt + + commitlint: + desc: Check for conventional commits + env: + # renovate: datasource=git-refs depName=commitlint lookupName=https://github.com/cloudnative-pg/daggerverse currentValue=main + DAGGER_COMMITLINT_SHA: 23ffda6100005d626fddb569e8e471587bf32cbf + cmds: + - > + GITHUB_REF= dagger -s call -m github.com/cloudnative-pg/daggerverse/commitlint@${DAGGER_COMMITLINT_SHA} + lint --source . --args "--from=origin/main" stdout + + uncommitted: + desc: Check for uncommitted changes + env: + # renovate: datasource=git-refs depName=uncommitted lookupName=https://github.com/cloudnative-pg/daggerverse currentValue=main + DAGGER_UNCOMMITTED_SHA: 23ffda6100005d626fddb569e8e471587bf32cbf + cmds: + - GITHUB_REF= dagger -s call -m github.com/cloudnative-pg/daggerverse/uncommitted@${DAGGER_UNCOMMITTED_SHA} check-uncommitted --source . stdout + sources: + - ./** + + go-test: + desc: Run go test + env: + # renovate: datasource=docker depName=golang versioning=semver + GOLANG_IMAGE_VERSION: 1.22.5 + # renovate: datasource=git-refs depName=gotest lookupName=https://github.com/Excoriate/daggerverse currentValue=main + DAGGER_GOTEST_SHA: 90a5d911a70510f9004544d4a25d39d917f1f668 + cmds: + - > + GITHUB_REF= dagger -s call -m github.com/Excoriate/daggerverse/gotest@${DAGGER_GOTEST_SHA} + base --image-url golang:${GOLANG_IMAGE_VERSION} + with-cgo-disabled + run-go-test --src . + sources: + - ./**/*.go + + ci: + desc: Run the CI pipeline + deps: + - spellcheck + - commitlint + - uncommitted + - lint + - go-test + + publish: + desc: Build and publish a container image for the plugin + requires: + # We expect this to run in a GitHub workflow, so we put a few GitHub-specific vars here + # to prevent running this task locally by accident. + vars: + - CI + - GITHUB_REPOSITORY + - GITHUB_REF + - GITHUB_REF_NAME + - REGISTRY_USER + - REGISTRY_PASSWORD + vars: + IMAGE_NAME: ghcr.io/{{.GITHUB_REPOSITORY}}{{if not (hasPrefix "refs/tags/v" .GITHUB_REF)}}-testing{{end}} + # remove /merge suffix from the branch name. This is a workaround for the GitHub workflow on PRs, + # where the branch name is suffixed with /merge. Prepend pr- to the branch name on PRs. + IMAGE_VERSION: '{{regexReplaceAll "(\\d+)/merge" .GITHUB_REF_NAME "pr-${1}"}}' + env: + # renovate: datasource=git-refs depName=docker lookupName=https://github.com/purpleclay/daggerverse currentValue=main + DAGGER_DOCKER_SHA: dc62f69e82ec1b1d57397549acf724d91b76c5d8 + cmds: + - > + dagger -s call -m github.com/purpleclay/daggerverse/docker@${DAGGER_DOCKER_SHA} + --registry ghcr.io --username $REGISTRY_USER --password env:REGISTRY_PASSWORD + build --dir . --platform linux/amd64 + publish --ref {{.IMAGE_NAME}} --tags {{.IMAGE_VERSION}} + + manifest: + desc: Update the image in the Kustomization + requires: + # We expect this to run in a GitHub workflow, so we put a few GitHub-specific vars here + # to prevent running this task locally by accident. + vars: + - CI + - GITHUB_REPOSITORY + - GITHUB_REF + - GITHUB_REF_NAME + vars: + IMAGE_NAME: ghcr.io/{{.GITHUB_REPOSITORY}}{{if not (hasPrefix "refs/tags/v" .GITHUB_REF)}}-testing{{end}} + # remove /merge suffix from the branch name. This is a workaround for the GitHub workflow on PRs, + # where the branch name is suffixed with /merge. Prepend pr- to the branch name on PRs. + IMAGE_VERSION: '{{regexReplaceAll "(\\d+)/merge" .GITHUB_REF_NAME "pr-${1}"}}' + env: + # renovate: datasource=git-refs depName=kustomize lookupName=github.com/sagikazarmark/daggerverse currentValue=main + DAGGER_KUSTOMIZE_SHA: d814d0d7c421348f51cdda96870a05ca2aa8e96a + cmds: + - > + dagger -s call -m github.com/sagikazarmark/daggerverse/kustomize@${DAGGER_KUSTOMIZE_SHA} + edit --source kubernetes set image --image cnpg-i-hello-world={{.IMAGE_NAME}}:{{.IMAGE_VERSION}} + directory export --path kubernetes + - > + dagger -s call -m github.com/sagikazarmark/daggerverse/kustomize@${DAGGER_KUSTOMIZE_SHA} + build --source kubernetes export --path manifest.yaml + + upload-manifest-to-release: + desc: Upload the manifest to the release + requires: + # We expect this to run in a GitHub workflow, so we put a few GitHub-specific vars here + # to prevent running this task locally by accident. + vars: + - CI + - GITHUB_REPOSITORY + - GITHUB_REF + - GITHUB_REF_NAME + - GITHUB_TOKEN + env: + # renovate: datasource=git-refs depName=gh lookupName=github.com/sagikazarmark/daggerverse + DAGGER_GH_SHA: 8f444e2c2b8e8162cea76d702086034ed3edc4f1 + preconditions: + - sh: "[[ {{.GITHUB_REF}} =~ 'refs/tags/v.*' ]]" + msg: not a tag, failing + cmds: + - > + dagger -s call -m github.com/sagikazarmark/daggerverse/gh@${DAGGER_GH_SHA} + with-source --source . + run --repo {{.GITHUB_REPOSITORY}} --token env:GITHUB_TOKEN + --cmd "release upload {{.GITHUB_REF_NAME}} manifest.yaml" + + clean: + desc: Remove autogenerated artifacts + cmds: + - rm -rf .task/ + + # TODO: daggerize this + local-dev-build: + desc: Build the plugin locally + env: + CGO_ENABLED: 0 + cmds: + - go build -o bin/cnpg-i-hello-world main.go + sources: + - ./**/*.go + + # TODO: daggerize this + local-dev-image: + desc: Build a container image for the plugin locally + vars: + IMAGE_VERSION: '{{.IMAGE_VERSION | default "latest"}}' + IMAGE_NAME: ghcr.io/cloudnative-pg/cnpg-i-hello-world:{{.IMAGE_VERSION}} + cmds: + - docker build -t ${IMAGE_NAME} . + sources: + - ./** + + # TODO: daggerize this + local-kind-deploy: + desc: Apply the plugin to a local kind cluster + deps: + - local-dev-image + cmds: + - ./scripts/run.sh diff --git a/commitlint.config.js b/commitlint.config.js new file mode 100644 index 0000000..85ce1e0 --- /dev/null +++ b/commitlint.config.js @@ -0,0 +1,12 @@ +const Configuration= { + extends: ['@commitlint/config-conventional'], + formatter: '@commitlint/format', + rules: { + 'body-empty': [1, 'never'], + 'body-case': [2, 'always', 'sentence-case'], + 'references-empty': [1, 'never'], + 'signed-off-by': [2, 'always', 'Signed-off-by:'], + }, +}; + +module.exports = Configuration; diff --git a/doc/concepts.md b/doc/concepts.md index f68819e..9c3b311 100644 --- a/doc/concepts.md +++ b/doc/concepts.md @@ -24,7 +24,7 @@ This feature enables the plugin to receive events about the cluster creation and mutations, this is defined by the following ``` -// ValidateCreate improves the behaviour of the validating webhook that +// ValidateCreate improves the behavior of the validating webhook that // is called on creation of the Cluster resources rpc ValidateClusterCreate(OperatorValidateClusterCreateRequest) returns (OperatorValidateClusterCreateResult) {} @@ -89,7 +89,3 @@ and Backups. The custom logic can be injected before the reconciliation and after it is executed. [API reference](https://github.com/cloudnative-pg/cnpg-i/blob/main/proto/reconciler.proto) - - - - diff --git a/go.mod b/go.mod index 23103e0..00e1c12 100644 --- a/go.mod +++ b/go.mod @@ -15,6 +15,11 @@ require ( sigs.k8s.io/controller-runtime v0.18.4 ) +require ( + github.com/rogpeppe/go-internal v1.12.0 // indirect + golang.org/x/tools v0.22.0 // indirect +) + require ( github.com/beorn7/perks v1.0.1 // indirect github.com/cespare/xxhash/v2 v2.3.0 // indirect diff --git a/go.sum b/go.sum index bd497de..5bec5ed 100644 --- a/go.sum +++ b/go.sum @@ -127,8 +127,8 @@ github.com/prometheus/procfs v0.12.0 h1:jluTpSng7V9hY0O2R9DzzJHYb2xULk9VTR1V1R/k github.com/prometheus/procfs v0.12.0/go.mod h1:pcuDEFsWDnvcgNzo4EEweacyhjeA9Zk3cnaOZAZEfOo= github.com/robfig/cron v1.2.0 h1:ZjScXvvxeQ63Dbyxy76Fj3AT3Ut0aKsyd2/tl3DTMuQ= github.com/robfig/cron v1.2.0/go.mod h1:JGuDeoQd7Z6yL4zQhZ3OPEVHB7fL6Ka6skscFHfmt2k= -github.com/rogpeppe/go-internal v1.10.0 h1:TMyTOH3F/DB16zRVcYyreMH6GnZZrwQVAoYjRBZyWFQ= -github.com/rogpeppe/go-internal v1.10.0/go.mod h1:UQnix2H7Ngw/k4C5ijL5+65zddjncjaFoBhdsK/akog= +github.com/rogpeppe/go-internal v1.12.0 h1:exVL4IDcn6na9z1rAb56Vxr+CgyK3nn3O+epU5NdKM8= +github.com/rogpeppe/go-internal v1.12.0/go.mod h1:E+RYuTGaKKdloAfM02xzb0FW3Paa99yedzYV+kq4uf4= github.com/russross/blackfriday/v2 v2.1.0/go.mod h1:+Rmxgy9KzJVeS9/2gXHxylqXiyQDYRxCVz55jmeOWTM= github.com/sagikazarmark/locafero v0.4.0 h1:HApY1R9zGo4DBgr7dqsTH/JJxLTTsOt7u6keLGt6kNQ= github.com/sagikazarmark/locafero v0.4.0/go.mod h1:Pe1W6UlPYUk/+wc/6KFhbORCfqzgYEpgQ3O5fPuL3H4= @@ -204,8 +204,8 @@ golang.org/x/tools v0.0.0-20180917221912-90fa682c2a6e/go.mod h1:n7NCudcB/nEzxVGm golang.org/x/tools v0.0.0-20191119224855-298f0cb1881e/go.mod h1:b+2E5dAYhXwXZwtnZ6UAqBI28+e2cm9otk0dWdXHAEo= golang.org/x/tools v0.0.0-20200619180055-7c47624df98f/go.mod h1:EkVYQZoAsY45+roYkvgYkIh4xh/qjgUK9TdY2XT94GE= golang.org/x/tools v0.0.0-20210106214847-113979e3529a/go.mod h1:emZCQorbCU4vsT4fOWvOPXz4eW1wZW4PmDk9uLelYpA= -golang.org/x/tools v0.21.1-0.20240508182429-e35e4ccd0d2d h1:vU5i/LfpvrRCpgM/VPfJLg5KjxD3E+hfT1SH+d9zLwg= -golang.org/x/tools v0.21.1-0.20240508182429-e35e4ccd0d2d/go.mod h1:aiJjzUbINMkxbQROHiO6hDPo2LHcIPhhQsa9DLh0yGk= +golang.org/x/tools v0.22.0 h1:gqSGLZqv+AI9lIQzniJ0nZDRG5GBPsSi+DRNHWNz6yA= +golang.org/x/tools v0.22.0/go.mod h1:aCwcsjqvq7Yqt6TNyX7QMU2enbQ/Gt0bo6krSeEri+c= golang.org/x/xerrors v0.0.0-20190717185122-a985d3407aa7/go.mod h1:I/5z698sn9Ka8TeJc9MKroUUfqBBauWjQqLJ2OPfmY0= golang.org/x/xerrors v0.0.0-20191011141410-1b5146add898/go.mod h1:I/5z698sn9Ka8TeJc9MKroUUfqBBauWjQqLJ2OPfmY0= golang.org/x/xerrors v0.0.0-20191204190536-9bdfabe68543/go.mod h1:I/5z698sn9Ka8TeJc9MKroUUfqBBauWjQqLJ2OPfmY0= diff --git a/internal/config/config.go b/internal/config/config.go index cfa83fe..dc4547e 100644 --- a/internal/config/config.go +++ b/internal/config/config.go @@ -61,14 +61,16 @@ func ValidateChanges( oldConfiguration *Configuration, newConfiguration *Configuration, helper *pluginhelper.Data, -) (result []*operator.ValidationError) { +) []*operator.ValidationError { + validationErrors := make([]*operator.ValidationError, 0) + if !reflect.DeepEqual(oldConfiguration.Labels, newConfiguration.Labels) { - result = append( - result, + validationErrors = append( + validationErrors, helper.ValidationErrorForParameter(labelsParameter, "Labels cannot be changed")) } - return result + return validationErrors } // applyDefaults fills the configuration with the defaults @@ -98,5 +100,6 @@ func (config *Configuration) ToParameters() (map[string]string, error) { } result[labelsParameter] = string(serializedLabels) result[annotationParameter] = string(serializedAnnotations) + return result, nil } diff --git a/internal/k8sclient/k8sclient.go b/internal/k8sclient/k8sclient.go index 53a7adb..2579a6c 100644 --- a/internal/k8sclient/k8sclient.go +++ b/internal/k8sclient/k8sclient.go @@ -48,6 +48,7 @@ func Get() (client.Client, error) { } currentClient = newClient + return currentClient, nil } diff --git a/internal/lifecycle/lifecycle.go b/internal/lifecycle/lifecycle.go index c351859..f5d213a 100644 --- a/internal/lifecycle/lifecycle.go +++ b/internal/lifecycle/lifecycle.go @@ -3,7 +3,7 @@ package lifecycle import ( "context" - "fmt" + "errors" "github.com/cloudnative-pg/cnpg-i-machinery/pkg/logging" "github.com/cloudnative-pg/cnpg-i-machinery/pkg/pluginhelper" @@ -47,16 +47,16 @@ func (impl Implementation) LifecycleHook( ctx context.Context, request *lifecycle.OperatorLifecycleRequest, ) (*lifecycle.OperatorLifecycleResponse, error) { - kind, err := utils.GetKind(request.ObjectDefinition) + kind, err := utils.GetKind(request.GetObjectDefinition()) if err != nil { return nil, err } - operation := request.OperationType.Type.Enum() + operation := request.GetOperationType().GetType().Enum() if operation == nil { - return nil, fmt.Errorf("no operation set") + return nil, errors.New("no operation set") } - // nolint: gocritic + //nolint: gocritic switch kind { case "Pod": switch *operation { @@ -78,8 +78,8 @@ func (impl Implementation) reconcileMetadata( logger := logging.FromContext(ctx).WithName("cnpg_i_example_lifecyle") helper, err := pluginhelper.NewDataBuilder( metadata.PluginName, - request.ClusterDefinition, - ).WithPod(request.ObjectDefinition).Build() + request.GetClusterDefinition(), + ).WithPod(request.GetObjectDefinition()).Build() if err != nil { return nil, err } diff --git a/internal/operator/mutations.go b/internal/operator/mutations.go index 7159ab2..10623c6 100644 --- a/internal/operator/mutations.go +++ b/internal/operator/mutations.go @@ -18,7 +18,7 @@ func (Implementation) MutateCluster( ) (*operator.OperatorMutateClusterResult, error) { helper, err := pluginhelper.NewDataBuilder( metadata.PluginName, - request.Definition, + request.GetDefinition(), ).Build() if err != nil { return nil, err diff --git a/internal/operator/validation.go b/internal/operator/validation.go index ab6145b..5b7a634 100644 --- a/internal/operator/validation.go +++ b/internal/operator/validation.go @@ -20,7 +20,7 @@ func (Implementation) ValidateClusterCreate( helper, err := pluginhelper.NewDataBuilder( metadata.PluginName, - request.Definition, + request.GetDefinition(), ).Build() if err != nil { return nil, err @@ -40,7 +40,7 @@ func (Implementation) ValidateClusterChange( oldClusterHelper, err := pluginhelper.NewDataBuilder( metadata.PluginName, - request.OldCluster, + request.GetOldCluster(), ).Build() if err != nil { return nil, fmt.Errorf("while parsing old cluster: %w", err) @@ -48,7 +48,7 @@ func (Implementation) ValidateClusterChange( newClusterHelper, err := pluginhelper.NewDataBuilder( metadata.PluginName, - request.NewCluster, + request.GetNewCluster(), ).Build() if err != nil { return nil, fmt.Errorf("while parsing new cluster: %w", err) @@ -58,5 +58,6 @@ func (Implementation) ValidateClusterChange( newConfiguration, result.ValidationErrors = config.FromParameters(newClusterHelper) oldConfiguration, _ := config.FromParameters(oldClusterHelper) result.ValidationErrors = config.ValidateChanges(oldConfiguration, newConfiguration, newClusterHelper) + return result, nil } diff --git a/kubernetes/deployment.yaml b/kubernetes/deployment.yaml index 8b2c4b8..63e30dc 100644 --- a/kubernetes/deployment.yaml +++ b/kubernetes/deployment.yaml @@ -18,7 +18,6 @@ spec: spec: containers: - image: cnpg-i-hello-world:latest - imagePullPolicy: Never name: cnpg-i-hello-world ports: - containerPort: 9090 diff --git a/kubernetes/kustomization.yaml b/kubernetes/kustomization.yaml index 0f5019f..bc26767 100644 --- a/kubernetes/kustomization.yaml +++ b/kubernetes/kustomization.yaml @@ -2,8 +2,10 @@ apiVersion: kustomize.config.k8s.io/v1beta1 kind: Kustomization namespace: cnpg-system resources: - - certificate-issuer.yaml - - client-certificate.yaml - - deployment.yaml - - server-certificate.yaml - - service.yaml +- certificate-issuer.yaml +- client-certificate.yaml +- deployment.yaml +- server-certificate.yaml +- service.yaml +images: +- name: cnpg-i-hello-world diff --git a/main.go b/main.go index 7d55ed2..6c5c85d 100644 --- a/main.go +++ b/main.go @@ -6,6 +6,7 @@ import ( "os" "github.com/spf13/cobra" + "github.com/cloudnative-pg/cnpg-i-hello-world/cmd/plugin" ) @@ -17,8 +18,7 @@ func main() { rootCmd.AddCommand(plugin.NewCmd()) - err := rootCmd.Execute() - if err != nil { + if err := rootCmd.Execute(); err != nil { fmt.Println(err) os.Exit(1) } diff --git a/release-please-config.json b/release-please-config.json new file mode 100644 index 0000000..b3f9a1d --- /dev/null +++ b/release-please-config.json @@ -0,0 +1,12 @@ +{ + "changelog-path": "CHANGELOG.md", + "release-type": "go", + "bump-minor-pre-major": false, + "bump-patch-for-minor-pre-major": false, + "draft": false, + "prerelease": false, + "packages": { + ".": {} + }, + "$schema": "https://raw.githubusercontent.com/googleapis/release-please/main/schemas/config.json" +} diff --git a/scripts/build_proto.sh b/scripts/build_proto.sh deleted file mode 100755 index b8bb9b2..0000000 --- a/scripts/build_proto.sh +++ /dev/null @@ -1,20 +0,0 @@ -#!/usr/bin/env bash - -set -eu - -# Get the directory of the script -SCRIPT_DIR="$(cd "$(dirname "${BASH_SOURCE[0]}")" && pwd)" - -# Navigate to the parent directory -cd "$SCRIPT_DIR/.." || { echo "Directory does not exist, skipping build_proto"; exit 0; } - -# Check if the contain any .proto files -if [ ! -d "proto" ] || [ -z "$(find proto -name '*.proto' -print -quit)" ]; then - echo "No .proto files found in the 'proto' directory, skipping build_proto" - exit 0 -fi - -# Recompile protobuf specification -protoc --go_out=. --go_opt=module=github.com/cloudnative-pg/cnpg-i-hello-world \ - --go-grpc_out=. --go-grpc_opt=module=github.com/cloudnative-pg/cnpg-i-hello-world \ - proto/*.proto diff --git a/scripts/check.sh b/scripts/check.sh deleted file mode 100755 index 1bad22f..0000000 --- a/scripts/check.sh +++ /dev/null @@ -1,9 +0,0 @@ -#!/usr/bin/env bash - -cd "$(dirname "$0")/.." || exit - -if [ ! -f "bin/golangci-lint" ]; then - curl -sSfL https://raw.githubusercontent.com/golangci/golangci-lint/master/install.sh | sh -s v1.55.2 -fi - -bin/golangci-lint run diff --git a/scripts/image.sh b/scripts/image.sh deleted file mode 100755 index c81c6e6..0000000 --- a/scripts/image.sh +++ /dev/null @@ -1,10 +0,0 @@ -#!/usr/bin/env bash - -cd "$(dirname "$0")/.." || exit - -if [ -z "$(which docker)" ]; then - echo "Please install docker" - exit 1 -fi - -docker build -t cnpg-i-hello-world:${VERSION:-latest} . diff --git a/scripts/test.sh b/scripts/test.sh deleted file mode 100755 index dc507c1..0000000 --- a/scripts/test.sh +++ /dev/null @@ -1,4 +0,0 @@ -#!/usr/bin/env bash - -cd "$(dirname "$0")/.." || exit -go test ./...