From cd3f552e8b9159cccd725509ed589d0cc4b1c776 Mon Sep 17 00:00:00 2001 From: Hans Hasselberg Date: Sun, 23 Apr 2023 22:06:22 +0000 Subject: [PATCH] backport of commit 112d1d6b97dc25f0cec9141143d11515e30de0d2 --- .changelog/1914.txt | 3 - .changelog/1920.txt | 3 - .changelog/1975.txt | 11 - .changelog/2068.txt | 3 + .changelog/2083.txt | 3 + .changelog/2108.txt | 12 + .circleci/config.yml | 1378 ----------------- .github/workflows/backport.yml | 6 +- .github/workflows/changelog-checker.yml | 2 +- .github/workflows/jira-issues.yaml | 2 + .github/workflows/jira-pr.yaml | 2 + .github/workflows/merge.yml | 31 + .github/workflows/nightly-acceptance.yml | 27 + .github/workflows/pr.yml | 25 + .github/workflows/reusable-acceptance.yml | 157 -- .github/workflows/reusable-golangci-lint.yml | 34 - .github/workflows/reusable-unit.yml | 57 - .github/workflows/test.yml | 399 ----- .../workflows/weekly-acceptance-0-49-x.yml | 29 + .github/workflows/weekly-acceptance-1-0-x.yml | 30 + .github/workflows/weekly-acceptance-1-1-x.yml | 30 + .go-version | 2 +- CHANGELOG.md | 104 +- CONTRIBUTING.md | 211 +-- acceptance/framework/consul/cli_cluster.go | 2 +- acceptance/framework/consul/helm_cluster.go | 75 +- acceptance/framework/helpers/helpers.go | 2 +- .../framework/portforward/port_forward.go | 2 +- acceptance/framework/vault/helpers.go | 14 - acceptance/go.mod | 14 +- acceptance/go.sum | 26 +- acceptance/tests/cli/cli_install_test.go | 42 +- .../bases/crds-oss/proxydefaults.yaml | 11 - .../bases/crds-oss/servicedefaults.yaml | 14 +- acceptance/tests/vault/vault_test.go | 77 +- charts/consul/Chart.yaml | 16 +- charts/consul/templates/_helpers.tpl | 33 +- .../api-gateway-controller-deployment.yaml | 13 +- .../consul/templates/crd-proxydefaults.yaml | 48 - .../consul/templates/crd-servicedefaults.yaml | 68 +- .../consul/templates/server-acl-init-job.yaml | 55 +- .../templates/sync-catalog-deployment.yaml | 2 +- .../webhook-cert-manager-clusterrole.yaml | 2 +- ...bhook-cert-manager-clusterrolebinding.yaml | 2 +- .../webhook-cert-manager-configmap.yaml | 2 +- .../webhook-cert-manager-deployment.yaml | 2 +- ...ebhook-cert-manager-podsecuritypolicy.yaml | 2 +- .../webhook-cert-manager-serviceaccount.yaml | 2 +- .../api-gateway-controller-deployment.bats | 47 + .../test/unit/connect-inject-clusterrole.bats | 3 + .../test/unit/connect-inject-deployment.bats | 24 +- .../consul/test/unit/server-acl-init-job.bats | 148 +- .../test/unit/sync-catalog-deployment.bats | 6 +- .../webhook-cert-manager-clusterrole.bats | 5 +- ...bhook-cert-manager-clusterrolebinding.bats | 5 +- .../unit/webhook-cert-manager-configmap.bats | 5 +- .../unit/webhook-cert-manager-deployment.bats | 5 +- ...ebhook-cert-manager-podsecuritypolicy.bats | 5 +- .../webhook-cert-manager-serviceaccount.bats | 5 +- charts/consul/values.yaml | 53 +- charts/go.mod | 2 +- cli/cmd/install/install.go | 2 +- cli/cmd/install/install_test.go | 18 +- cli/cmd/proxy/loglevel/command.go | 346 ----- cli/cmd/proxy/loglevel/command_test.go | 293 ---- cli/cmd/proxy/read/command.go | 42 +- cli/cmd/proxy/read/command_test.go | 114 +- .../http.go => cmd/proxy/read/config.go} | 60 +- .../proxy/read/config_test.go} | 57 +- .../proxy/read/envoy_types.go} | 2 +- cli/cmd/proxy/read/filters.go | 14 +- cli/cmd/proxy/read/filters_test.go | 46 +- cli/cmd/proxy/read/format.go | 17 +- cli/cmd/proxy/read/format_test.go | 18 +- .../proxy/read}/test_clusters.json | 0 .../proxy/read}/test_config_dump.json | 0 cli/cmd/troubleshoot/command.go | 26 - cli/cmd/troubleshoot/proxy/proxy.go | 282 ---- cli/cmd/troubleshoot/proxy/proxy_test.go | 72 - cli/cmd/troubleshoot/upstreams/upstreams.go | 274 ---- .../troubleshoot/upstreams/upstreams_test.go | 127 -- cli/cmd/upgrade/upgrade.go | 3 +- cli/cmd/upgrade/upgrade_test.go | 4 +- cli/commands.go | 25 +- cli/common/envoy/logger_params.go | 166 -- cli/common/envoy/logger_params_test.go | 172 -- .../envoy/testdata/fetch_debug_levels.txt | 59 - cli/common/terminal/table.go | 18 +- cli/go.mod | 87 +- cli/go.sum | 348 ++--- cli/preset/demo.go | 2 + cli/preset/quickstart.go | 2 + cli/preset/secure.go | 2 + cli/version/version.go | 4 +- control-plane/Dockerfile | 2 +- .../api/v1alpha1/proxydefaults_types.go | 99 +- .../api/v1alpha1/proxydefaults_types_test.go | 267 +--- .../v1alpha1/proxydefaults_webhook_test.go | 2 +- .../api/v1alpha1/servicedefaults_types.go | 80 +- .../v1alpha1/servicedefaults_types_test.go | 302 +--- control-plane/api/v1alpha1/shared_types.go | 66 - .../api/v1alpha1/zz_generated.deepcopy.go | 86 +- control-plane/cni/go.mod | 26 +- control-plane/cni/go.sum | 45 +- .../consul.hashicorp.com_proxydefaults.yaml | 48 - .../consul.hashicorp.com_servicedefaults.yaml | 80 +- control-plane/go.mod | 45 +- control-plane/go.sum | 94 +- .../subcommand/common/common_test.go | 19 +- .../subcommand/inject-connect/command.go | 21 +- .../subcommand/server-acl-init/command.go | 150 +- .../server-acl-init/command_ent_test.go | 3 +- .../server-acl-init/command_test.go | 457 +++--- .../server-acl-init/k8s_secrets_backend.go | 62 - .../server-acl-init/secrets_backend.go | 18 - .../subcommand/server-acl-init/servers.go | 54 +- .../test_fake_secrets_backend.go | 20 - .../server-acl-init/vault_secrets_backend.go | 66 - control-plane/version/version.go | 4 +- docs/admin-partitions-with-acls.md | 98 ++ hack/aws-acceptance-test-cleanup/go.mod | 2 +- hack/copy-crds-to-chart/go.mod | 2 +- hack/copy-crds-to-chart/main.go | 17 +- hack/helm-reference-gen/go.mod | 2 +- hack/helm-reference-gen/main.go | 7 +- 125 files changed, 1619 insertions(+), 6727 deletions(-) delete mode 100644 .changelog/1914.txt delete mode 100644 .changelog/1920.txt delete mode 100644 .changelog/1975.txt create mode 100644 .changelog/2068.txt create mode 100644 .changelog/2083.txt create mode 100644 .changelog/2108.txt delete mode 100644 .circleci/config.yml create mode 100644 .github/workflows/merge.yml create mode 100644 .github/workflows/nightly-acceptance.yml create mode 100644 .github/workflows/pr.yml delete mode 100644 .github/workflows/reusable-acceptance.yml delete mode 100644 .github/workflows/reusable-golangci-lint.yml delete mode 100644 .github/workflows/reusable-unit.yml delete mode 100644 .github/workflows/test.yml create mode 100644 .github/workflows/weekly-acceptance-0-49-x.yml create mode 100644 .github/workflows/weekly-acceptance-1-0-x.yml create mode 100644 .github/workflows/weekly-acceptance-1-1-x.yml delete mode 100644 cli/cmd/proxy/loglevel/command.go delete mode 100644 cli/cmd/proxy/loglevel/command_test.go rename cli/{common/envoy/http.go => cmd/proxy/read/config.go} (91%) rename cli/{common/envoy/http_test.go => cmd/proxy/read/config_test.go} (93%) rename cli/{common/envoy/types.go => cmd/proxy/read/envoy_types.go} (99%) rename cli/{common/envoy/testdata => cmd/proxy/read}/test_clusters.json (100%) rename cli/{common/envoy/testdata => cmd/proxy/read}/test_config_dump.json (100%) delete mode 100644 cli/cmd/troubleshoot/command.go delete mode 100644 cli/cmd/troubleshoot/proxy/proxy.go delete mode 100644 cli/cmd/troubleshoot/proxy/proxy_test.go delete mode 100644 cli/cmd/troubleshoot/upstreams/upstreams.go delete mode 100644 cli/cmd/troubleshoot/upstreams/upstreams_test.go delete mode 100644 cli/common/envoy/logger_params.go delete mode 100644 cli/common/envoy/logger_params_test.go delete mode 100644 cli/common/envoy/testdata/fetch_debug_levels.txt delete mode 100644 control-plane/subcommand/server-acl-init/k8s_secrets_backend.go delete mode 100644 control-plane/subcommand/server-acl-init/secrets_backend.go delete mode 100644 control-plane/subcommand/server-acl-init/test_fake_secrets_backend.go delete mode 100644 control-plane/subcommand/server-acl-init/vault_secrets_backend.go create mode 100644 docs/admin-partitions-with-acls.md diff --git a/.changelog/1914.txt b/.changelog/1914.txt deleted file mode 100644 index 3179f3b0b3..0000000000 --- a/.changelog/1914.txt +++ /dev/null @@ -1,3 +0,0 @@ -```release-note:bug -control-plane: fix issue where consul-connect-injector acl token was unintentionally being deleted and not recreated when a container was restarted due to a livenessProbe failure. -``` \ No newline at end of file diff --git a/.changelog/1920.txt b/.changelog/1920.txt deleted file mode 100644 index 4b1f151fe4..0000000000 --- a/.changelog/1920.txt +++ /dev/null @@ -1,3 +0,0 @@ -```release-note:improvement -helm: When the `global.acls.bootstrapToken` field is set and the content of the secret is empty, the bootstrap ACL token is written to that secret after bootstrapping ACLs. This applies to both the Vault and Consul secrets backends. -``` diff --git a/.changelog/1975.txt b/.changelog/1975.txt deleted file mode 100644 index ba26b1ab1e..0000000000 --- a/.changelog/1975.txt +++ /dev/null @@ -1,11 +0,0 @@ -```release-note:security -upgrade to use Go 1.19.6. This resolves vulnerabilities CVE-2022-41724 in crypto/tls and CVE-2022-41723 in net/http. -``` - -```release-note:improvement -cli: update minimum go version for project to 1.19. -``` - -```release-note:improvement -control-plane: update minimum go version for project to 1.19. -``` \ No newline at end of file diff --git a/.changelog/2068.txt b/.changelog/2068.txt new file mode 100644 index 0000000000..bc17061f51 --- /dev/null +++ b/.changelog/2068.txt @@ -0,0 +1,3 @@ +```release-note:bug +sync-catalog: fix issue where the sync-catalog ACL token were set with an incorrect ENV VAR. +``` \ No newline at end of file diff --git a/.changelog/2083.txt b/.changelog/2083.txt new file mode 100644 index 0000000000..23c0c77592 --- /dev/null +++ b/.changelog/2083.txt @@ -0,0 +1,3 @@ +```release-note:bug +api-gateway: fix issue where the API Gateway controller is unable to start up successfully when Vault is configured as the secrets backend +``` diff --git a/.changelog/2108.txt b/.changelog/2108.txt new file mode 100644 index 0000000000..1c10ef62d9 --- /dev/null +++ b/.changelog/2108.txt @@ -0,0 +1,12 @@ +```release-note:security +Upgrade to use Go 1.19.9. +This resolves vulnerabilities [CVE-2023-24537](https://github.com/advisories/GHSA-9f7g-gqwh-jpf5)(`go/scanner`), +[CVE-2023-24538](https://github.com/advisories/GHSA-v4m2-x4rp-hv22)(`html/template`), +[CVE-2023-24534](https://github.com/advisories/GHSA-8v5j-pwr7-w5f8)(`net/textproto`) and +[CVE-2023-24536](https://github.com/advisories/GHSA-9f7g-gqwh-jpf5)(`mime/multipart`). +Also, `golang.org/x/net` has been updated to v0.7.0 to resolve CVEs [CVE-2022-41721 +](https://github.com/advisories/GHSA-fxg5-wq6x-vr4w +), [CVE-2022-27664](https://github.com/advisories/GHSA-69cg-p879-7622) and [CVE-2022-41723 +](https://github.com/advisories/GHSA-vvpx-j8f3-3w6h +.) +``` \ No newline at end of file diff --git a/.circleci/config.yml b/.circleci/config.yml deleted file mode 100644 index 9c84f112cc..0000000000 --- a/.circleci/config.yml +++ /dev/null @@ -1,1378 +0,0 @@ -# Originally from consul-k8s -version: 2.1 -orbs: - slack: circleci/slack@3.4.2 -# reusable 'executor' object for jobs -executors: - go: - docker: - - image: docker.mirror.hashicorp.services/cimg/go:1.20.1 - environment: - TEST_RESULTS: /tmp/test-results # path to where test results are saved - -slack-channel: &slack-channel C0421KHNAV9 #feed-consul-k8s-ci channel ID -control-plane-path: &control-plane-path control-plane -cli-path: &cli-path cli -acceptance-mod-path: &acceptance-mod-path acceptance -acceptance-test-path: &acceptance-test-path acceptance/tests -acceptance-framework-path: &acceptance-framework-path acceptance/framework -helm-gen-path: &helm-gen-path hack/helm-reference-gen -gke-terraform-path: &gke-terraform-path charts/consul/test/terraform/gke -eks-terraform-path: &eks-terraform-path charts/consul/test/terraform/eks -aks-terraform-path: &aks-terraform-path charts/consul/test/terraform/aks -openshift-terraform-path: &openshift-terraform-path charts/consul/test/terraform/openshift -# This image is built from test/docker/Test.dockerfile -consul-helm-test-image: &consul-helm-test-image docker.mirror.hashicorp.services/hashicorpdev/consul-helm-test:0.15.0 -consul-test-image: &consul-test-image hashicorppreview/consul-enterprise:1.15-dev - -######################## -# COMMANDS -######################## -# Commands define a sequence of steps as a map to be executed and reused in jobs -commands: - install-prereqs: - steps: - - run: - name: Install go, gotestsum, kind, kubectl, and helm - command: | - wget https://golang.org/dl/go1.20.1.linux-amd64.tar.gz - sudo rm -rf /usr/local/go && sudo tar -C /usr/local -xzf go1.20.1.linux-amd64.tar.gz - rm go1.20.1.linux-amd64.tar.gz - echo 'export PATH=$PATH:/usr/local/go/bin' >> $BASH_ENV - - wget https://github.com/gotestyourself/gotestsum/releases/download/v1.8.2/gotestsum_1.8.2_linux_amd64.tar.gz - sudo tar -C /usr/local/bin -xzf gotestsum_1.8.2_linux_amd64.tar.gz - rm gotestsum_1.8.2_linux_amd64.tar.gz - - curl -Lo ./kind https://kind.sigs.k8s.io/dl/v0.17.0/kind-linux-amd64 - chmod +x ./kind - sudo mv ./kind /usr/local/bin/kind - - curl -LO "https://storage.googleapis.com/kubernetes-release/release/$(curl -s https://storage.googleapis.com/kubernetes-release/release/stable.txt)/bin/linux/amd64/kubectl" - chmod +x ./kubectl - sudo mv ./kubectl /usr/local/bin/kubectl - - wget https://get.helm.sh/helm-v3.9.4-linux-amd64.tar.gz - tar -zxvf helm-v3.9.4-linux-amd64.tar.gz - sudo mv linux-amd64/helm /usr/local/bin/helm - custom-checkout: - description: | - custom-checkout will perform a custom checkout procedure if provided with an alternative git reference, - otherwise it will run the CircleCI defined checkout command. This is needed as the CircleCI defined checkout - command does not support subsequent git actions after being called. - parameters: - git-ref: - type: string - default: "" - steps: - - when: - condition: << parameters.git-ref >> - steps: - - run: - name: Checkout code - command: | - ssh-keyscan github.com >> ~/.ssh/known_hosts - if [ -e '/home/circleci/project/.git' ] ; then - echo 'Fetching into existing repository' - existing_repo='true' - cd '/home/circleci/project' - git remote set-url origin "$CIRCLE_REPOSITORY_URL" || true - else - echo 'Cloning git repository' - existing_repo='false' - mkdir -p '/home/circleci/project' - cd '/home/circleci/project' - git clone --no-checkout "$CIRCLE_REPOSITORY_URL" . - fi - - if [ "$existing_repo" = 'true' ] || [ 'false' = 'true' ]; then - echo 'Fetching from remote repository' - git fetch --force origin - git fetch --force --tags origin - fi - - echo 'Checking out branch/tag' - git checkout --force "<< parameters.git-ref >>" - - unless: - condition: << parameters.git-ref >> - steps: - - checkout - create-kind-clusters: - parameters: - version: - type: string - steps: - - run: - name: Create kind clusters - command: | - kind create cluster --name dc1 --image kindest/node:<< parameters.version >> - kind create cluster --name dc2 --image kindest/node:<< parameters.version >> - create-kind-cni-clusters: - parameters: - version: - type: string - steps: - - run: - name: Create CNI kind clusters - command: | - kind create cluster --config=acceptance/framework/environment/cni-kind/kind.config --name dc1 --image kindest/node:<< parameters.version >> - make kind-cni-calico - kind create cluster --config=acceptance/framework/environment/cni-kind/kind.config --name dc2 --image kindest/node:<< parameters.version >> - make kind-cni-calico - build-cli: - steps: - - run: - name: Build consul-k8s CLI - working_directory: *cli-path - command: | - go build -o ./bin/consul-k8s - sudo cp ./bin/consul-k8s /usr/local/go/bin/ - consul-k8s version - - run-acceptance-tests: - description: | - Runs the Kind acceptance tests using a provided consul-k8s image, or else attempts to use the image referenced by the - branch name and git reference of the current git commit - parameters: - failfast: - type: boolean - default: false - additional-flags: - type: string - consul-k8s-image: - type: string - default: "docker.mirror.hashicorp.services/hashicorpdev/consul-k8s-control-plane:$(git rev-parse --short HEAD)" - go-path: - type: string - default: "/home/circleci/.go_workspace" - steps: - - when: - condition: << parameters.failfast >> - steps: - - run: - name: Run acceptance tests - working_directory: *acceptance-test-path - no_output_timeout: 2h - command: | - # Enterprise tests can't run on fork PRs because they require - # a secret. - if [ -z "$CIRCLE_PR_NUMBER" ]; then - ENABLE_ENTERPRISE=true - fi - - # We have to run the tests for each package separately so that we can - # exit early if any test fails (-failfast only works within a single - # package). - exit_code=0 - pkgs=$(go list ./... | circleci tests split --split-by=timings --timings-type=classname) - echo "Running $(echo $pkgs | wc -w) packages:" - echo $pkgs - for pkg in $pkgs - do - if ! gotestsum --format=testname --no-summary=all --jsonfile=jsonfile-${pkg////-} -- $pkg -p 1 -timeout 2h -failfast \ - << parameters.additional-flags >> \ - -enable-multi-cluster \ - ${ENABLE_ENTERPRISE:+-enable-enterprise} \ - -debug-directory="$TEST_RESULTS/debug" \ - -consul-k8s-image=<< parameters.consul-k8s-image >> - then - echo "Tests in ${pkg} failed, aborting early" - exit_code=1 - break - fi - done - gotestsum --format=testname --raw-command --junitfile "$TEST_RESULTS/gotestsum-report.xml" -- cat jsonfile* - exit $exit_code - - - unless: - condition: << parameters.failfast >> - steps: - - run: - name: Run acceptance tests - working_directory: *acceptance-test-path - no_output_timeout: 2h - command: | - # Enterprise tests can't run on fork PRs because they require - # a secret. - if [ -z "$CIRCLE_PR_NUMBER" ]; then - ENABLE_ENTERPRISE=true - fi - - pkgs=$(go list ./... | circleci tests split --split-by=timings --timings-type=classname) - echo "Running $pkgs" - gotestsum --format testname --junitfile "$TEST_RESULTS/gotestsum-report.xml" -- $pkgs -p 1 -timeout 2h -failfast \ - << parameters.additional-flags >> \ - ${ENABLE_ENTERPRISE:+-enable-enterprise} \ - -enable-multi-cluster \ - -debug-directory="$TEST_RESULTS/debug" \ - -consul-k8s-image=<< parameters.consul-k8s-image >> - -######################## -# JOBS -######################## -# Jobs are a collection of steps. These are used in the workflows to define -# what gets run in the pipeline -jobs: - go-fmt-and-vet-control-plane: - executor: go - steps: - - checkout - - # Restore go module cache if there is one - - restore_cache: - keys: - - consul-k8s-modcache-v2-{{ checksum "control-plane/go.mod" }} - - - run: - name: go mod download - working_directory: *control-plane-path - command: go mod download - - # Save go module cache if the go.mod file has changed - - save_cache: - key: consul-k8s-modcache-v2-{{ checksum "control-plane/go.mod" }} - paths: - - "/home/circleci/go/pkg/mod" - - # check go fmt output because it does not report non-zero when there are fmt changes - - run: - name: check go fmt - working_directory: *control-plane-path - command: | - files=$(go fmt ./...) - if [ -n "$files" ]; then - echo "The following file(s) do not conform to go fmt:" - echo "$files" - exit 1 - fi - - run: cd control-plane && go vet ./... - - lint-control-plane: - executor: go - steps: - - checkout - - run: go get -u github.com/hashicorp/lint-consul-retry && lint-consul-retry - - run: - name: run lint - working_directory: *control-plane-path - command: go run hack/lint-api-new-client/main.go - - test-control-plane: - executor: go - environment: - TEST_RESULTS: /tmp/test-results - parallelism: 1 - steps: - - checkout - - run: mkdir -p $TEST_RESULTS - - # Restore go module cache if there is one - - restore_cache: - keys: - - consul-k8s-modcache-v2-{{ checksum "control-plane/go.mod" }} - - # run go tests with gotestsum - - run: - name: run go tests - working_directory: *control-plane-path - command: | - # download and install the consul binary - wget https://releases.hashicorp.com/consul/"${CONSUL_VERSION}"/consul_"${CONSUL_VERSION}"_linux_amd64.zip && \ - unzip consul_"${CONSUL_VERSION}"_linux_amd64.zip -d /home/circleci/bin && - rm consul_"${CONSUL_VERSION}"_linux_amd64.zip - PACKAGE_NAMES=$(go list ./...) - gotestsum --format testname --junitfile $TEST_RESULTS/gotestsum-report.xml -- -p 4 $PACKAGE_NAMES - - - store_test_results: - path: /tmp/test-results - - store_artifacts: - path: /tmp/test-results - - test-enterprise-control-plane: - executor: go - environment: - TEST_RESULTS: /tmp/test-results - parallelism: 1 - steps: - - checkout - - run: mkdir -p $TEST_RESULTS - - # Restore go module cache if there is one - - restore_cache: - keys: - - consul-k8s-modcache-v2-{{ checksum "control-plane/go.mod" }} - - # run go tests with gotestsum - - run: - name: run enterprise go tests - working_directory: *control-plane-path - command: | - # download and install the consul binary - wget https://releases.hashicorp.com/consul/"${CONSUL_ENT_VERSION}"/consul_"${CONSUL_ENT_VERSION}"_linux_amd64.zip && \ - unzip consul_"${CONSUL_ENT_VERSION}"_linux_amd64.zip -d /home/circleci/bin && - rm consul_"${CONSUL_ENT_VERSION}"_linux_amd64.zip - PACKAGE_NAMES=$(go list ./...) - gotestsum --format testname --junitfile $TEST_RESULTS/gotestsum-report.xml -- -tags=enterprise -p 4 $PACKAGE_NAMES - - - store_test_results: - path: /tmp/test-results - - store_artifacts: - path: /tmp/test-results - - build-distro: # defines a parameterized job - description: A job that will build the os/arch distro set by XC_OS and XC_ARCH - parameters: - OS: - description: What OSes to build - default: "" - type: string - ARCH: - description: What architectures to build - default: "" - type: string - executor: go - environment: - GOXPARALLEL: 2 # CircleCI containers are 2 CPU x 4GB RAM - steps: - - checkout - # Restore go module cache if there is one - - restore_cache: - keys: - - consul-k8s-modcache-v2-{{ checksum "control-plane/go.mod" }} - - run: - name: build local - working_directory: *control-plane-path - command: XC_OS="<< parameters.OS >>" XC_ARCH="<< parameters.ARCH >>" ./build-support/scripts/build-local.sh - # persist to downstream job - - persist_to_workspace: - root: . - paths: - - control-plane/pkg/bin - - control-plane/cni/pkg/bin - # save dev build to CircleCI - - store_artifacts: - path: ./control-plane/pkg/bin - - store_artifacts: - path: ./control-plane/cni/pkg/bin - - # upload dev docker image - dev-upload-docker: - machine: - image: ubuntu-2004:202010-01 - environment: - DOCKER_CLI_EXPERIMENTAL: enabled - steps: - - checkout - # get consul-k8s binary - - attach_workspace: - at: . - - run: sudo apt-get update - - run: sudo apt-get install -y qemu-user-static - - run: docker buildx create --use - - run: - name: make ci.dev-docker - working_directory: *control-plane-path - command: make ci.dev-docker - - unit-cli: - executor: go - steps: - - checkout - - # Restore go module cache if there is one - - restore_cache: - keys: - - consul-k8s-cli-modcache-v2-{{ checksum "cli/go.mod" }} - - - run: - name: go mod download - working_directory: *cli-path - command: go mod download - - # Save go module cache if the go.mod file has changed - - save_cache: - key: consul-k8s-cli-modcache-v2-{{ checksum "cli/go.mod" }} - paths: - - "/home/circleci/go/pkg/mod" - - - run: mkdir -p $TEST_RESULTS - - - run: - name: Run tests - working_directory: *cli-path - command: | - gotestsum --format testname --junitfile $TEST_RESULTS/gotestsum-report.xml ./... -- -p 4 - - - store_test_results: - path: /tmp/test-results - - store_artifacts: - path: /tmp/test-results - - go-fmt-and-vet-acceptance: - executor: go - steps: - - checkout - - # Restore go module cache if there is one - - restore_cache: - keys: - - consul-helm-acceptance-modcache-v2-{{ checksum "acceptance/go.mod" }} - - - run: - name: go mod download - working_directory: *acceptance-mod-path - command: go mod download - - # Save go module cache if the go.mod file has changed - - save_cache: - key: consul-helm-acceptance-modcache-v2-{{ checksum "acceptance/go.mod" }} - paths: - - "/home/circleci/go/pkg/mod" - - # check go fmt output because it does not report non-zero when there are fmt changes - - run: - name: check go fmt - working_directory: *acceptance-mod-path - command: | - files=$(go fmt ./...) - if [ -n "$files" ]; then - echo "The following file(s) do not conform to go fmt:" - echo "$files" - exit 1 - fi - - - run: - name: go vet - working_directory: *acceptance-mod-path - command: go vet ./... - - go-fmt-and-vet-helm-gen: - executor: go - steps: - - checkout - - # Restore go module cache if there is one - - restore_cache: - keys: - - consul-helm-helm-gen-modcache-v2-{{ checksum "charts/consul/hack/helm-reference-gen/go.mod" }} - - - run: - name: go mod download - working_directory: *helm-gen-path - command: go mod download - - # Save go module cache if the go.mod file has changed - - save_cache: - key: consul-helm-helm-gen-modcache-v2-{{ checksum "charts/consul/hack/helm-reference-gen/go.mod" }} - paths: - - "/home/circleci/go/pkg/mod" - - # check go fmt output because it does not report non-zero when there are fmt changes - - run: - name: check go fmt - working_directory: *helm-gen-path - command: | - files=$(go fmt ./...) - if [ -n "$files" ]; then - echo "The following file(s) do not conform to go fmt:" - echo "$files" - exit 1 - fi - - - run: - name: go vet - working_directory: *helm-gen-path - command: go vet ./... - - unit-acceptance-framework: - executor: go - steps: - - checkout - - # Restore go module cache if there is one - - restore_cache: - keys: - - consul-helm-acceptance-modcache-v2-{{ checksum "acceptance/go.mod" }} - - - run: mkdir -p $TEST_RESULTS - - - run: - name: Run tests - working_directory: *acceptance-framework-path - command: | - gotestsum --format testname --junitfile $TEST_RESULTS/gotestsum-report.xml ./... -- -p 4 - - - store_test_results: - path: /tmp/test-results - - store_artifacts: - path: /tmp/test-results - - unit-helm-gen: - executor: go - steps: - - checkout - - # Restore go module cache if there is one - - restore_cache: - keys: - - consul-helm-helm-gen-modcache-v2-{{ checksum "charts/consul/hack/helm-reference-gen/go.mod" }} - - - run: mkdir -p $TEST_RESULTS - - - run: - name: Run tests - working_directory: *helm-gen-path - command: | - gotestsum --format testname --junitfile $TEST_RESULTS/gotestsum-report.xml ./... -- -p 4 - - - store_test_results: - path: /tmp/test-results - - store_artifacts: - path: /tmp/test-results - - validate-helm-gen: - executor: go - steps: - - checkout - - # Restore go module cache if there is one - - restore_cache: - keys: - - consul-helm-helm-gen-modcache-v2-{{ checksum "charts/consul/hack/helm-reference-gen/go.mod" }} - - - run: mkdir -p $TEST_RESULTS - - - run: - name: Validate helm gen - working_directory: *helm-gen-path - command: | - go run ./... -validate - - unit-test-helm-templates: - docker: - - image: *consul-helm-test-image - - steps: - - checkout - - - run: - name: Run Unit Tests - working_directory: charts/consul - command: bats --jobs 4 ./test/unit - - ########################### - # KIND ACCEPTANCE TEST JOBS - ########################### - acceptance: - environment: - - TEST_RESULTS: /tmp/test-results - - CONSUL_TEST_IMAGE: *consul-test-image - machine: - image: ubuntu-2004:202010-01 - resource_class: xlarge - parallelism: 6 - steps: - - checkout - - install-prereqs - - create-kind-clusters: - version: "v1.26.0" - - restore_cache: - keys: - - consul-helm-modcache-v2-{{ checksum "acceptance/go.mod" }} - - run: - name: go mod download - working_directory: *acceptance-mod-path - command: go mod download - - save_cache: - key: consul-helm-modcache-v2-{{ checksum "acceptance/go.mod" }} - paths: - - ~/.go_workspace/pkg/mod - - build-cli - - run: mkdir -p $TEST_RESULTS - - run-acceptance-tests: - failfast: true - additional-flags: -use-kind -kubecontext="kind-dc1" -secondary-kubecontext="kind-dc2" -consul-image=$CONSUL_TEST_IMAGE - - store_test_results: - path: /tmp/test-results - - store_artifacts: - path: /tmp/test-results - - acceptance-tproxy: - environment: - - TEST_RESULTS: /tmp/test-results - - CONSUL_TEST_IMAGE: *consul-test-image - machine: - image: ubuntu-2004:202010-01 - resource_class: xlarge - parallelism: 6 - steps: - - checkout - - install-prereqs - - create-kind-clusters: - version: "v1.26.0" - - restore_cache: - keys: - - consul-helm-modcache-v2-{{ checksum "acceptance/go.mod" }} - - run: - name: go mod download - working_directory: *acceptance-mod-path - command: go mod download - - save_cache: - key: consul-helm-modcache-v2-{{ checksum "acceptance/go.mod" }} - paths: - - ~/.go_workspace/pkg/mod - - build-cli - - run: mkdir -p $TEST_RESULTS - - run-acceptance-tests: - failfast: true - additional-flags: -use-kind -kubecontext="kind-dc1" -secondary-kubecontext="kind-dc2" -enable-transparent-proxy -consul-image=$CONSUL_TEST_IMAGE - - store_test_results: - path: /tmp/test-results - - store_artifacts: - path: /tmp/test-results - - acceptance-tproxy-cni: - environment: - - TEST_RESULTS: /tmp/test-results - - CONSUL_TEST_IMAGE: *consul-test-image - machine: - image: ubuntu-2004:202010-01 - resource_class: xlarge - parallelism: 3 - steps: - - checkout - - install-prereqs - - create-kind-cni-clusters: - version: "v1.25.3" - - restore_cache: - keys: - - consul-helm-modcache-v2-{{ checksum "acceptance/go.mod" }} - - run: - name: go mod download - working_directory: *acceptance-mod-path - command: go mod download - - save_cache: - key: consul-helm-modcache-v2-{{ checksum "acceptance/go.mod" }} - paths: - - ~/.go_workspace/pkg/mod - - build-cli - - run: mkdir -p $TEST_RESULTS - - run-acceptance-tests: - failfast: true - additional-flags: -use-kind -kubecontext="kind-dc1" -secondary-kubecontext="kind-dc2" -enable-transparent-proxy -enable-cni -consul-image=$CONSUL_TEST_IMAGE - - store_test_results: - path: /tmp/test-results - - store_artifacts: - path: /tmp/test-results - - ############################## - # CLEANUP CLOUD RESOURCES JOBS - ############################## - cleanup-gcp-resources: - docker: - - image: *consul-helm-test-image - steps: - - run: - name: cleanup leftover resources - command: | - echo "${GOOGLE_CREDENTIALS}" | gcloud auth activate-service-account --key-file=- - clusters=$(gcloud container clusters list --zone us-central1-a --project ${CLOUDSDK_CORE_PROJECT} --format json | jq -r '.[] | select(.name | test("^consul-k8s-\\d+$")) | .name') - for cluster in $clusters; do - echo "Deleting $cluster GKE cluster" - gcloud container clusters delete $cluster --zone us-central1-a --project ${CLOUDSDK_CORE_PROJECT} --quiet - done - - slack/status: - channel: *slack-channel - fail_only: true - failure_message: "GKE cleanup failed" - - cleanup-azure-resources: - docker: - - image: *consul-helm-test-image - steps: - - run: - name: cleanup leftover resources - command: | - az login --service-principal -u "$ARM_CLIENT_ID" -p "$ARM_CLIENT_SECRET" --tenant "$ARM_TENANT_ID" > /dev/null - resource_groups=$(az group list -o json | jq -r '.[] | select(.name | test("^consul-k8s-\\d+$")) | .name') - for group in $resource_groups; do - echo "Deleting $group resource group" - az group delete -n $group --yes - done - - slack/status: - channel: *slack-channel - fail_only: true - failure_message: "AKS cleanup failed" - - cleanup-eks-resources: - docker: - - image: *consul-helm-test-image - steps: - - checkout - - run: - name: cleanup eks resources - command: | - # Assume the role and set environment variables. - aws sts assume-role --role-arn "$AWS_ROLE_ARN" --role-session-name "consul-helm-$CIRCLE_BUILD_NUM" --duration-seconds 10800 > assume-role.json - export AWS_ACCESS_KEY_ID="$(jq -r .Credentials.AccessKeyId assume-role.json)" - export AWS_SECRET_ACCESS_KEY="$(jq -r .Credentials.SecretAccessKey assume-role.json)" - export AWS_SESSION_TOKEN="$(jq -r .Credentials.SessionToken assume-role.json)" - - make ci.aws-acceptance-test-cleanup - - slack/status: - channel: *slack-channel - fail_only: true - failure_message: "EKS cleanup failed" - - ############################# - # CLOUD ACCEPTANCE TEST JOBS - ############################# - acceptance-gke-1-25: - parallelism: 2 - environment: - - TEST_RESULTS: /tmp/test-results - - USE_GKE_GCLOUD_AUTH_PLUGIN: true - - CONSUL_TEST_IMAGE: *consul-test-image - docker: - - image: *consul-helm-test-image - - steps: - - run: - name: Exit if forked PR - command: | - if [ -n "$CIRCLE_PR_NUMBER" ]; then - echo "Skipping acceptance tests for forked PRs; marking step successful." - circleci step halt - fi - - - checkout - - - build-cli - - run: - name: terraform init & apply - working_directory: *gke-terraform-path - command: | - terraform init - echo "${GOOGLE_CREDENTIALS}" | gcloud auth activate-service-account --key-file=- - - # On GKE, we're setting the build number instead of build URL because label values - # cannot contain '/'. - terraform apply \ - -var project=${CLOUDSDK_CORE_PROJECT} \ - -var init_cli=true \ - -var cluster_count=2 \ - -var labels="{\"build_number\": \"$CIRCLE_BUILD_NUM\"}" \ - -auto-approve - - primary_kubeconfig=$(terraform output -json | jq -r .kubeconfigs.value[0]) - secondary_kubeconfig=$(terraform output -json | jq -r .kubeconfigs.value[1]) - - echo "export primary_kubeconfig=$primary_kubeconfig" >> $BASH_ENV - echo "export secondary_kubeconfig=$secondary_kubeconfig" >> $BASH_ENV - - # Restore go module cache if there is one - - restore_cache: - keys: - - consul-helm-acceptance-modcache-v2-{{ checksum "acceptance/go.mod" }} - - - run: mkdir -p $TEST_RESULTS - - - run-acceptance-tests: - additional-flags: -kubeconfig="$primary_kubeconfig" -secondary-kubeconfig="$secondary_kubeconfig" -enable-transparent-proxy -consul-image=$CONSUL_TEST_IMAGE - - - store_test_results: - path: /tmp/test-results - - store_artifacts: - path: /tmp/test-results - - - run: - name: terraform destroy - working_directory: *gke-terraform-path - command: | - terraform destroy -var project=${CLOUDSDK_CORE_PROJECT} -auto-approve - when: always - - - slack/status: - channel: *slack-channel - fail_only: true - failure_message: "GKE acceptance tests failed. Check the logs at: ${CIRCLE_BUILD_URL}" - - acceptance-gke-cni-1-25: - parallelism: 2 - environment: - - TEST_RESULTS: /tmp/test-results - - USE_GKE_GCLOUD_AUTH_PLUGIN: true - - CONSUL_TEST_IMAGE: *consul-test-image - docker: - - image: *consul-helm-test-image - - steps: - - run: - name: Exit if forked PR - command: | - if [ -n "$CIRCLE_PR_NUMBER" ]; then - echo "Skipping acceptance tests for forked PRs; marking step successful." - circleci step halt - fi - - - checkout - - - build-cli - - run: - name: terraform init & apply - working_directory: *gke-terraform-path - command: | - terraform init - echo "${GOOGLE_CREDENTIALS}" | gcloud auth activate-service-account --key-file=- - - # On GKE, we're setting the build number instead of build URL because label values - # cannot contain '/'. - terraform apply \ - -var project=${CLOUDSDK_CORE_PROJECT} \ - -var init_cli=true \ - -var cluster_count=2 \ - -var labels="{\"build_number\": \"$CIRCLE_BUILD_NUM\"}" \ - -auto-approve - - primary_kubeconfig=$(terraform output -json | jq -r .kubeconfigs.value[0]) - secondary_kubeconfig=$(terraform output -json | jq -r .kubeconfigs.value[1]) - - echo "export primary_kubeconfig=$primary_kubeconfig" >> $BASH_ENV - echo "export secondary_kubeconfig=$secondary_kubeconfig" >> $BASH_ENV - - # Restore go module cache if there is one - - restore_cache: - keys: - - consul-helm-acceptance-modcache-v2-{{ checksum "acceptance/go.mod" }} - - - run: mkdir -p $TEST_RESULTS - - - run-acceptance-tests: - additional-flags: -use-gke -kubeconfig="$primary_kubeconfig" -secondary-kubeconfig="$secondary_kubeconfig" -enable-transparent-proxy -enable-cni -consul-image=$CONSUL_TEST_IMAGE - - - store_test_results: - path: /tmp/test-results - - store_artifacts: - path: /tmp/test-results - - - run: - name: terraform destroy - working_directory: *gke-terraform-path - command: | - terraform destroy -var project=${CLOUDSDK_CORE_PROJECT} -auto-approve - when: always - - - slack/status: - channel: *slack-channel - fail_only: true - failure_message: "GKE CNI acceptance tests failed. Check the logs at: ${CIRCLE_BUILD_URL}" - - acceptance-aks-1-24: - parallelism: 3 - environment: - - TEST_RESULTS: /tmp/test-results - - CONSUL_TEST_IMAGE: *consul-test-image - docker: - - image: *consul-helm-test-image - - steps: - - checkout - - - build-cli - - run: - name: terraform init & apply - working_directory: *aks-terraform-path - command: | - terraform init - - terraform apply \ - -var client_id="$ARM_CLIENT_ID" \ - -var client_secret="$ARM_CLIENT_SECRET" \ - -var cluster_count=2 \ - -var tags="{\"build_url\": \"$CIRCLE_BUILD_URL\"}" \ - -auto-approve - - primary_kubeconfig=$(terraform output -json | jq -r .kubeconfigs.value[0]) - secondary_kubeconfig=$(terraform output -json | jq -r .kubeconfigs.value[1]) - - echo "export primary_kubeconfig=$primary_kubeconfig" >> $BASH_ENV - echo "export secondary_kubeconfig=$secondary_kubeconfig" >> $BASH_ENV - - # Restore go module cache if there is one - - restore_cache: - keys: - - consul-helm-acceptance-modcache-v2-{{ checksum "acceptance/go.mod" }} - - - run: mkdir -p $TEST_RESULTS - - - run-acceptance-tests: - additional-flags: -use-aks -kubeconfig="$primary_kubeconfig" -secondary-kubeconfig="$secondary_kubeconfig" -enable-transparent-proxy -consul-image=$CONSUL_TEST_IMAGE - - - store_test_results: - path: /tmp/test-results - - store_artifacts: - path: /tmp/test-results - - - run: - name: terraform destroy - working_directory: *aks-terraform-path - command: | - terraform destroy -auto-approve - when: always - - - slack/status: - channel: *slack-channel - fail_only: true - failure_message: "AKS acceptance tests failed. Check the logs at: ${CIRCLE_BUILD_URL}" - - acceptance-aks-cni-1-24: - parallelism: 3 - environment: - - TEST_RESULTS: /tmp/test-results - - CONSUL_TEST_IMAGE: *consul-test-image - docker: - - image: *consul-helm-test-image - - steps: - - checkout - - - build-cli - - run: - name: terraform init & apply - working_directory: *aks-terraform-path - command: | - terraform init - - terraform apply \ - -var client_id="$ARM_CLIENT_ID" \ - -var client_secret="$ARM_CLIENT_SECRET" \ - -var cluster_count=2 \ - -var tags="{\"build_url\": \"$CIRCLE_BUILD_URL\"}" \ - -auto-approve - - primary_kubeconfig=$(terraform output -json | jq -r .kubeconfigs.value[0]) - secondary_kubeconfig=$(terraform output -json | jq -r .kubeconfigs.value[1]) - - echo "export primary_kubeconfig=$primary_kubeconfig" >> $BASH_ENV - echo "export secondary_kubeconfig=$secondary_kubeconfig" >> $BASH_ENV - - # Restore go module cache if there is one - - restore_cache: - keys: - - consul-helm-acceptance-modcache-v2-{{ checksum "acceptance/go.mod" }} - - - run: mkdir -p $TEST_RESULTS - - - run-acceptance-tests: - additional-flags: -use-aks -kubeconfig="$primary_kubeconfig" -secondary-kubeconfig="$secondary_kubeconfig" -enable-transparent-proxy -enable-cni -consul-image=$CONSUL_TEST_IMAGE - - - store_test_results: - path: /tmp/test-results - - store_artifacts: - path: /tmp/test-results - - - run: - name: terraform destroy - working_directory: *aks-terraform-path - command: | - terraform destroy -auto-approve - when: always - - slack/status: - channel: *slack-channel - fail_only: true - failure_message: "AKS CNI acceptance tests failed. Check the logs at: ${CIRCLE_BUILD_URL}" - - acceptance-eks-1-23: - parallelism: 3 - environment: - - TEST_RESULTS: /tmp/test-results - - CONSUL_TEST_IMAGE: *consul-test-image - docker: - - image: *consul-helm-test-image - - steps: - - checkout - - - build-cli - - run: - name: configure aws - command: | - aws configure --profile helm_user set aws_access_key_id "$AWS_ACCESS_KEY_ID" - aws configure --profile helm_user set aws_secret_access_key "$AWS_SECRET_ACCESS_KEY" - aws configure set role_arn "$AWS_ROLE_ARN" - aws configure set source_profile helm_user - - echo "unset AWS_ACCESS_KEY_ID" >> $BASH_ENV - echo "unset AWS_SECRET_ACCESS_KEY" >> $BASH_ENV - - - run: - name: terraform init & apply - working_directory: *eks-terraform-path - command: | - terraform init - - terraform apply -var cluster_count=2 -var tags="{\"build_url\": \"$CIRCLE_BUILD_URL\"}" -auto-approve - - primary_kubeconfig=$(terraform output -json | jq -r .kubeconfigs.value[0]) - secondary_kubeconfig=$(terraform output -json | jq -r .kubeconfigs.value[1]) - - echo "export primary_kubeconfig=$primary_kubeconfig" >> $BASH_ENV - echo "export secondary_kubeconfig=$secondary_kubeconfig" >> $BASH_ENV - - # Restore go module cache if there is one - - restore_cache: - keys: - - consul-helm-acceptance-modcache-v2-{{ checksum "acceptance/go.mod" }} - - - run: mkdir -p $TEST_RESULTS - - - run-acceptance-tests: - additional-flags: -kubeconfig="$primary_kubeconfig" -secondary-kubeconfig="$secondary_kubeconfig" -enable-transparent-proxy -consul-image=$CONSUL_TEST_IMAGE - - - store_test_results: - path: /tmp/test-results - - store_artifacts: - path: /tmp/test-results - - - run: - name: terraform destroy - working_directory: *eks-terraform-path - command: | - terraform destroy -var cluster_count=2 -auto-approve - when: always - - - slack/status: - channel: *slack-channel - fail_only: true - failure_message: "EKS acceptance tests failed. Check the logs at: ${CIRCLE_BUILD_URL}" - - acceptance-eks-cni-1-23: - parallelism: 3 - environment: - - TEST_RESULTS: /tmp/test-results - - CONSUL_TEST_IMAGE: *consul-test-image - docker: - - image: *consul-helm-test-image - - steps: - - checkout - - - build-cli - - run: - name: configure aws - command: | - aws configure --profile helm_user set aws_access_key_id "$AWS_ACCESS_KEY_ID" - aws configure --profile helm_user set aws_secret_access_key "$AWS_SECRET_ACCESS_KEY" - aws configure set role_arn "$AWS_ROLE_ARN" - aws configure set source_profile helm_user - - echo "unset AWS_ACCESS_KEY_ID" >> $BASH_ENV - echo "unset AWS_SECRET_ACCESS_KEY" >> $BASH_ENV - - - run: - name: terraform init & apply - working_directory: *eks-terraform-path - command: | - terraform init - - terraform apply -var cluster_count=2 -var tags="{\"build_url\": \"$CIRCLE_BUILD_URL\"}" -auto-approve - - primary_kubeconfig=$(terraform output -json | jq -r .kubeconfigs.value[0]) - secondary_kubeconfig=$(terraform output -json | jq -r .kubeconfigs.value[1]) - - echo "export primary_kubeconfig=$primary_kubeconfig" >> $BASH_ENV - echo "export secondary_kubeconfig=$secondary_kubeconfig" >> $BASH_ENV - - # Restore go module cache if there is one - - restore_cache: - keys: - - consul-helm-acceptance-modcache-v2-{{ checksum "acceptance/go.mod" }} - - - run: mkdir -p $TEST_RESULTS - - - run-acceptance-tests: - additional-flags: -kubeconfig="$primary_kubeconfig" -secondary-kubeconfig="$secondary_kubeconfig" -enable-transparent-proxy -enable-cni -consul-image=$CONSUL_TEST_IMAGE - - - store_test_results: - path: /tmp/test-results - - store_artifacts: - path: /tmp/test-results - - - run: - name: terraform destroy - working_directory: *eks-terraform-path - command: | - terraform destroy -var cluster_count=2 -auto-approve - when: always - - - slack/status: - channel: *slack-channel - fail_only: true - failure_message: "EKS CNI acceptance tests failed. Check the logs at: ${CIRCLE_BUILD_URL}" - - acceptance-openshift: - environment: - TEST_RESULTS: /tmp/test-results - CONSUL_TEST_IMAGE: *consul-test-image - parallelism: 1 - docker: - - image: *consul-helm-test-image - - steps: - - checkout - - build-cli - - run: - name: terraform init & apply - working_directory: *openshift-terraform-path - command: | - terraform init - az login --service-principal -u "$ARM_CLIENT_ID" -p "$ARM_CLIENT_SECRET" --tenant "$ARM_TENANT_ID" > /dev/null - terraform apply \ - -var cluster_count=2 \ - -var tags="{\"build_url\": \"$CIRCLE_BUILD_URL\"}" \ - -auto-approve - - primary_kubeconfig=$(terraform output -json | jq -r .kubeconfigs.value[0]) - secondary_kubeconfig=$(terraform output -json | jq -r .kubeconfigs.value[1]) - - echo "export primary_kubeconfig=$primary_kubeconfig" >> $BASH_ENV - echo "export secondary_kubeconfig=$secondary_kubeconfig" >> $BASH_ENV - - # Restore go module cache if there is one - - restore_cache: - keys: - - consul-helm-acceptance-modcache-v2-{{ checksum "acceptance/go.mod" }} - - - run: mkdir -p $TEST_RESULTS - - - run-acceptance-tests: - additional-flags: -kubeconfig="$primary_kubeconfig" -secondary-kubeconfig="$secondary_kubeconfig" -enable-openshift -enable-transparent-proxy -consul-image=$CONSUL_TEST_IMAGE - - - store_test_results: - path: /tmp/test-results - - store_artifacts: - path: /tmp/test-results - - - run: - name: terraform destroy - working_directory: *openshift-terraform-path - command: | - terraform destroy -auto-approve - when: always - - - slack/status: - channel: *slack-channel - fail_only: true - failure_message: "OpenShift acceptance tests failed. Check the logs at: ${CIRCLE_BUILD_URL}" - - acceptance-kind-1-23-consul-compat-nightly-1-12: - environment: - - TEST_RESULTS: /tmp/test-results - - CONSUL_IMAGE: "docker.mirror.hashicorp.services/hashicorppreview/consul-enterprise:1.12-dev" - - ENVOY_IMAGE: "envoyproxy/envoy:v1.22.2" - - HELM_CHART_VERSION: "0.49.0" - - CONSUL_K8S_IMAGE: "docker.mirror.hashicorp.services/hashicorp/consul-k8s-control-plane:0.49.0" - machine: - image: ubuntu-2004:202010-01 - resource_class: xlarge - steps: - - custom-checkout: - git-ref: "v$HELM_CHART_VERSION" - - install-prereqs - - create-kind-clusters: - version: "v1.23.0" - - restore_cache: - keys: - - consul-helm-modcache-v2-{{ checksum "acceptance/go.mod" }} - - run: - name: go mod download - working_directory: *acceptance-mod-path - command: go mod download - - save_cache: - key: consul-helm-modcache-v2-{{ checksum "acceptance/go.mod" }} - paths: - - ~/.go_workspace/pkg/mod - - build-cli - - run: mkdir -p $TEST_RESULTS - - run-acceptance-tests: - consul-k8s-image: $CONSUL_K8S_IMAGE - additional-flags: -use-kind -kubecontext="kind-dc1" -secondary-kubecontext="kind-dc2" -consul-image=$CONSUL_IMAGE -consul-version="1.12" -envoy-image=$ENVOY_IMAGE -helm-chart-version=$HELM_CHART_VERSION -enable-transparent-proxy - - store_test_results: - path: /tmp/test-results - - store_artifacts: - path: /tmp/test-results - - slack/status: - channel: *slack-channel - fail_only: true - failure_message: "Acceptance tests against Kind with Kubernetes v1.25 with Consul 1.12 nightly failed. Check the logs at: ${CIRCLE_BUILD_URL}" - - acceptance-kind-1-23-consul-compat-nightly-1-13: - environment: - - TEST_RESULTS: /tmp/test-results - - CONSUL_IMAGE: "docker.mirror.hashicorp.services/hashicorppreview/consul-enterprise:1.13-dev" - - ENVOY_IMAGE: "envoyproxy/envoy:v1.23.1" - - CONSUL_K8S_IMAGE: "docker.mirror.hashicorp.services/hashicorp/consul-k8s-control-plane:0.49.0" - - HELM_CHART_VERSION: "0.49.0" - machine: - image: ubuntu-2004:202010-01 - resource_class: xlarge - steps: - - custom-checkout: - git-ref: "v$HELM_CHART_VERSION" - - install-prereqs - - create-kind-clusters: - version: "v1.23.0" - - restore_cache: - keys: - - consul-helm-modcache-v2-{{ checksum "acceptance/go.mod" }} - - run: - name: go mod download - working_directory: *acceptance-mod-path - command: go mod download - - save_cache: - key: consul-helm-modcache-v2-{{ checksum "acceptance/go.mod" }} - paths: - - ~/.go_workspace/pkg/mod - - build-cli - - run: mkdir -p $TEST_RESULTS - - run-acceptance-tests: - consul-k8s-image: $CONSUL_K8S_IMAGE - additional-flags: -use-kind -kubecontext="kind-dc1" -secondary-kubecontext="kind-dc2" -consul-image=$CONSUL_IMAGE -consul-version="1.13" -envoy-image=$ENVOY_IMAGE -helm-chart-version=$HELM_CHART_VERSION -enable-transparent-proxy - - store_test_results: - path: /tmp/test-results - - store_artifacts: - path: /tmp/test-results - - slack/status: - channel: *slack-channel - fail_only: true - failure_message: "Acceptance tests against Kind with Kubernetes v1.25 with Consul 1.13 nightly failed. Check the logs at: ${CIRCLE_BUILD_URL}" - -######################## -# WORKFLOWS -######################## -# Workflows are a set of rules for defining a collection of jobs and their run order. -# This is where the pipeline tests and builds are constructed and triggers for running these tests -# are defined -workflows: - version: 2 - test-and-build: - jobs: - # Build this one control-plane binary so that acceptance and acceptance-tproxy will run - # The rest of these CircleCI jobs have been migrated to GitHub Actions. We need to wait until - # there is support for a larger pool of runners before the acceptance tests can - # be moved - # Run acceptance tests using the docker image built for the control plane for this particular - # branch - # This is run on every PR - - build-distro: - OS: "linux" - ARCH: "amd64 arm64" - name: build-distros-linux - - dev-upload-docker: - context: consul-ci - requires: - - build-distros-linux - - acceptance: - context: consul-ci - requires: - - dev-upload-docker - - acceptance-tproxy-cni: - context: consul-ci - requires: - - dev-upload-docker - - acceptance-tproxy: - context: consul-ci - requires: - - dev-upload-docker - - - nightly-cleanup: - triggers: - - schedule: - cron: "0 12 * * *" # Run at 12 pm UTC (5 am PST) - filters: - branches: - only: - - main - jobs: - - cleanup-gcp-resources - - cleanup-azure-resources - - cleanup-eks-resources - - nightly-acceptance-tests-release: - description: | - Tests which run on a release branch nightly. These exist separate from the main - acceptance tests so that they can run at their own cadence, but - contains the same sequence of jobs. - triggers: - - schedule: - cron: "0 0 * * *" # Run at 12 am UTC (5 pm PST) - filters: - branches: - only: - - release/0.49.x - - release/1.0.x - - release/1.1.x - jobs: - - build-distro: - OS: "linux" - ARCH: "amd64 arm64" - name: build-distros-linux - - dev-upload-docker: - requires: - - build-distros-linux - # Disable until we can use UBI images. - # - acceptance-openshift - - acceptance-gke-1-25: - requires: - - dev-upload-docker - - acceptance-gke-cni-1-25: - requires: - - acceptance-gke-1-25 - - acceptance-tproxy: - requires: - - dev-upload-docker - - nightly-acceptance-tests-main: - description: | - Tests which run on the main branch nightly. These exist separate from the release - acceptance tests so that they can run at their own cadence, but - contains the same sequence of jobs. - triggers: - - schedule: - cron: "0 0 * * *" # Run at 12 am UTC (5 pm PST) - filters: - branches: - only: - - main - jobs: - - build-distro: - OS: "linux" - ARCH: "amd64 arm64" - name: build-distros-linux - - dev-upload-docker: - requires: - - build-distros-linux - # Disable until we can use UBI images. - # - acceptance-openshift - - acceptance-gke-1-25: - requires: - - dev-upload-docker - - acceptance-gke-cni-1-25: - requires: - - acceptance-gke-1-25 - - acceptance-eks-1-23: - requires: - - dev-upload-docker - - acceptance-eks-cni-1-23: - requires: - - acceptance-eks-1-23 - - acceptance-aks-1-24: - requires: - - dev-upload-docker - - acceptance-aks-cni-1-24: - requires: - - acceptance-aks-1-24 - - acceptance-tproxy: - requires: - - dev-upload-docker diff --git a/.github/workflows/backport.yml b/.github/workflows/backport.yml index 9c241d9ada..48883e24fa 100644 --- a/.github/workflows/backport.yml +++ b/.github/workflows/backport.yml @@ -2,7 +2,7 @@ name: Backport Assistant Runner on: - pull_request_target: + pull_request: types: - closed - labeled @@ -11,10 +11,10 @@ jobs: backport: if: github.event.pull_request.merged runs-on: ubuntu-latest - container: hashicorpdev/backport-assistant:0.2.5 + container: hashicorpdev/backport-assistant:0.3.3 steps: - name: Run Backport Assistant - run: backport-assistant backport -automerge + run: backport-assistant backport -merge-method=squash -gh-automerge env: BACKPORT_LABEL_REGEXP: "backport/(?P\\d+\\.\\d+\\.x)" BACKPORT_TARGET_TEMPLATE: "release/{{.target}}" diff --git a/.github/workflows/changelog-checker.yml b/.github/workflows/changelog-checker.yml index ae2e88170b..5c60e9a38a 100644 --- a/.github/workflows/changelog-checker.yml +++ b/.github/workflows/changelog-checker.yml @@ -34,7 +34,7 @@ jobs: changelog_file_path=".changelog/[_0-9]*.txt" fi - changelog_files=$(git --no-pager diff --name-only HEAD "$(git merge-base HEAD "origin/main")" | egrep ${changelog_file_path}) + changelog_files=$(git --no-pager diff --name-only HEAD "$(git merge-base HEAD "origin/${{ github.event.pull_request.base.ref }}")" | egrep -e "${changelog_file_path}")) # If we do not find a file in .changelog/, we fail the check if [ -z "$changelog_files" ]; then diff --git a/.github/workflows/jira-issues.yaml b/.github/workflows/jira-issues.yaml index 18705db8e8..dc743e9328 100644 --- a/.github/workflows/jira-issues.yaml +++ b/.github/workflows/jira-issues.yaml @@ -1,3 +1,5 @@ +# Copyright (c) HashiCorp, Inc. + on: issues: types: [opened, closed, deleted, reopened] diff --git a/.github/workflows/jira-pr.yaml b/.github/workflows/jira-pr.yaml index 5c0ba71cd2..c07a92ee77 100644 --- a/.github/workflows/jira-pr.yaml +++ b/.github/workflows/jira-pr.yaml @@ -1,3 +1,5 @@ +# Copyright (c) HashiCorp, Inc. + on: pull_request_target: types: [opened, closed, reopened] diff --git a/.github/workflows/merge.yml b/.github/workflows/merge.yml new file mode 100644 index 0000000000..be1b392f4a --- /dev/null +++ b/.github/workflows/merge.yml @@ -0,0 +1,31 @@ +# Dispatch to the consul-k8s-workflows when a PR is created and on merges to main/release* +name: merge +on: + push: + # Sequence of patterns matched against refs/heads + branches: + # Push events on main branch + - main + # Push events to branches matching refs/heads/release/** + - "release/**" + +# these should be the only settings that you will ever need to change +env: + CONSUL_IMAGE: hashicorppreview/consul-enterprise:1.16-dev # Consul's enterprise version to use in tests. We use this consul image on release branches too + BRANCH: ${{ github.head_ref || github.ref_name }} + CONTEXT: "merge" + SHA: ${{ github.event.pull_request.head.sha || github.sha }} + +jobs: + test: + name: test + runs-on: ubuntu-latest + steps: + - uses: benc-uk/workflow-dispatch@v1.2.2 + name: test + with: + workflow: test.yml + repo: hashicorp/consul-k8s-workflows + ref: main + token: ${{ secrets.ELEVATED_GITHUB_TOKEN }} + inputs: '{ "context":"${{ env.CONTEXT }}", "repository":"${{ github.repository }}", "branch":"${{ env.BRANCH }}", "sha":"${{ env.SHA }}", "token":"${{ secrets.ELEVATED_GITHUB_TOKEN }}", "consul-image":"${{ env.CONSUL_IMAGE }}" }' diff --git a/.github/workflows/nightly-acceptance.yml b/.github/workflows/nightly-acceptance.yml new file mode 100644 index 0000000000..b8b7f50798 --- /dev/null +++ b/.github/workflows/nightly-acceptance.yml @@ -0,0 +1,27 @@ +# Dispatch to the consul-k8s-workflows with a nightly cron +name: nightly-acceptance +on: + schedule: + # * is a special character in YAML so you have to quote this string + # Run nightly at 12AM UTC/8PM EST/5PM PST + - cron: '0 0 * * *' + +# these should be the only settings that you will ever need to change +env: + CONSUL_IMAGE: hashicorppreview/consul-enterprise:1.16-dev # Consul's enterprise version to use in tests + BRANCH: ${{ github.ref_name }} + CONTEXT: "nightly" + +jobs: + cloud: + name: cloud + runs-on: ubuntu-latest + steps: + - uses: benc-uk/workflow-dispatch@v1.2.2 + name: cloud + with: + workflow: cloud.yml + repo: hashicorp/consul-k8s-workflows + ref: main + token: ${{ secrets.ELEVATED_GITHUB_TOKEN }} + inputs: '{ "context":"${{ env.CONTEXT }}", "repository":"${{ github.repository }}", "branch":"${{ env.BRANCH }}", "sha":"${{ github.sha }}", "token":"${{ secrets.ELEVATED_GITHUB_TOKEN }}", "consul-image":"${{ env.CONSUL_IMAGE }}" }' diff --git a/.github/workflows/pr.yml b/.github/workflows/pr.yml new file mode 100644 index 0000000000..6ab7cf8d56 --- /dev/null +++ b/.github/workflows/pr.yml @@ -0,0 +1,25 @@ +# Dispatch to the consul-k8s-workflows when a PR is created and on merges to main/release* +name: pr +on: + pull_request: + +# these should be the only settings that you will ever need to change +env: + CONSUL_IMAGE: hashicorppreview/consul-enterprise:1.14-dev # Consul's enterprise version to use in tests + BRANCH: ${{ github.head_ref || github.ref_name }} + CONTEXT: "pr" + SHA: ${{ github.event.pull_request.head.sha || github.sha }} + +jobs: + test: + name: test + runs-on: ubuntu-latest + steps: + - uses: benc-uk/workflow-dispatch@v1.2.2 + name: test + with: + workflow: test.yml + repo: hashicorp/consul-k8s-workflows + ref: main + token: ${{ secrets.ELEVATED_GITHUB_TOKEN }} + inputs: '{ "context":"${{ env.CONTEXT }}", "repository":"${{ github.repository }}", "branch":"${{ env.BRANCH }}", "sha":"${{ env.SHA }}", "token":"${{ secrets.ELEVATED_GITHUB_TOKEN }}", "consul-image":"${{ env.CONSUL_IMAGE }}" }' diff --git a/.github/workflows/reusable-acceptance.yml b/.github/workflows/reusable-acceptance.yml deleted file mode 100644 index e4401932d3..0000000000 --- a/.github/workflows/reusable-acceptance.yml +++ /dev/null @@ -1,157 +0,0 @@ -name: reusable-acceptance - -on: - workflow_call: - inputs: - name: - required: true - type: string - additional-flags: - required: false - type: string - default: "" - consul-k8s-image: - required: false - type: string - directory: - required: true - type: string - go-version: - required: true - type: string - gotestsum-version: - required: true - type: string - kind-version: - required: false - type: string - default: "v1.24.6" - checkout-ref: - required: false - type: string - default: ${{ github.sha }} - secrets: - CONSUL_ENT_LICENSE: - required: true - VAULT_LICENSE: - required: true - -# Environment variables can only be used at the step level -env: - TEST_RESULTS: /tmp/test-results # path to where test results are saved - CONSUL_ENT_LICENSE: ${{ secrets.CONSUL_ENT_LICENSE }} - VAULT_LICENSE: ${{ secrets.VAULT_LICENSE }} - CONSUL_K8S_IMAGE: ${{ inputs.consul-k8s-image }} - -jobs: - job: - runs-on: [custom, linux, xl] - strategy: - matrix: - include: - - {runner: "0", test-packages: "basic consul-dns metrics"} - - {runner: "1", test-packages: "connect"} - - {runner: "2", test-packages: "controller example"} - - {runner: "3", test-packages: "ingress-gateway"} - - {runner: "4", test-packages: "partitions"} - - {runner: "5", test-packages: "peering"} - - {runner: "6", test-packages: "snapshot-agent vault wan-federation"} - - {runner: "7", test-packages: "cli sync terminating-gateway"} - - fail-fast: false - steps: - - name: Checkout code - uses: actions/checkout@v3 - with: - ref: ${{ inputs.checkout-ref }} - - - name: Setup go - uses: actions/setup-go@v3 - with: - go-version: ${{ inputs.go-version }} - - - name: Setup go mod cache - uses: actions/cache@v3 - with: - path: | - ~/.cache/go-build - ~/go/pkg/mod - key: ${{ runner.os }}-go-${{ hashFiles('**/go.sum') }} - restore-keys: | - ${{ runner.os }}-go- - - - name: Install pre-requisites # Install gotestsum, kind, kubectl, and helm - run: | - wget https://github.com/gotestyourself/gotestsum/releases/download/v1.6.4/gotestsum_1.6.4_linux_amd64.tar.gz - sudo tar -C /usr/local/bin -xzf gotestsum_1.6.4_linux_amd64.tar.gz - rm gotestsum_1.6.4_linux_amd64.tar.gz - - curl -Lo ./kind https://kind.sigs.k8s.io/dl/v0.15.0/kind-linux-amd64 - chmod +x ./kind - sudo mv ./kind /usr/local/bin/kind - - curl -LO "https://storage.googleapis.com/kubernetes-release/release/$(curl -s https://storage.googleapis.com/kubernetes-release/release/stable.txt)/bin/linux/amd64/kubectl" - chmod +x ./kubectl - sudo mv ./kubectl /usr/local/bin/kubectl - - wget https://get.helm.sh/helm-v3.9.4-linux-amd64.tar.gz - tar -zxvf helm-v3.9.4-linux-amd64.tar.gz - sudo mv linux-amd64/helm /usr/local/bin/helm - - - run: mkdir -p ${{ env.TEST_RESULTS }} - - - name: go mod download - working-directory: ${{ inputs.directory }} - run: go mod download - - - name: Create kind clusters - run: | - kind create cluster --name dc1 --image kindest/node:${{ inputs.kind-version }} - kind create cluster --name dc2 --image kindest/node:${{ inputs.kind-version }} - - - name: Build CLI - run: | - sudo make cli-dev - consul-k8s version - - # We have to run the tests for each package separately so that we can - # exit early if any test fails (-failfast only works within a single - # package). - - name: Run acceptance tests ${{ matrix.runner }} - working-directory: ${{ inputs.directory }} - if: github.repository_owner == 'hashicorp' # This prevents running on forks - run: | - exit_code=0 - echo "Running packages: ${{ matrix.test-packages }}" - for pkg in $(echo ${{ matrix.test-packages }}) - do - fullpkg="github.com/hashicorp/consul-k8s/${{ inputs.directory }}/${pkg}" - echo "Testing package: ${fullpkg}" - if ! gotestsum --format=testname --jsonfile=jsonfile-${pkg////-} -- ${fullpkg} -p 1 -timeout 2h -failfast \ - ${{ inputs.additional-flags }} \ - -enable-enterprise \ - -enable-multi-cluster \ - -debug-directory=${{ env.TEST_RESULTS }}/debug \ - -consul-k8s-image=${{ inputs.consul-k8s-image }} - then - echo "Tests in ${pkg} failed, aborting early" - exit_code=1 - break - fi - done - gotestsum --format=testname --raw-command --junitfile "${{ env.TEST_RESULTS }}/gotestsum-report.xml" -- cat jsonfile* - exit $exit_code - - - name: Upload tests - if: always() - uses: actions/upload-artifact@v3 - with: - name: ${{ inputs.name }}-${{ matrix.test-packages }}-gotestsum-report.xml - path: ${{ env.TEST_RESULTS }}/gotestsum-report.xml - - - name: Upload debug (on failure) - if: failure() - uses: actions/upload-artifact@v3 - with: - name: ${{ inputs.name }}-${{ matrix.test-packages }}-debug-info - path: ${{ env.TEST_RESULTS }}/debug diff --git a/.github/workflows/reusable-golangci-lint.yml b/.github/workflows/reusable-golangci-lint.yml deleted file mode 100644 index 30b6a0a3b3..0000000000 --- a/.github/workflows/reusable-golangci-lint.yml +++ /dev/null @@ -1,34 +0,0 @@ -name: golangci-lint - -on: - workflow_call: - inputs: - directory: - required: true - type: string - go-version: - required: true - type: string - args: - required: false - type: string - -jobs: - job: - runs-on: ubuntu-latest - - steps: - - name: Checkout code - uses: actions/checkout@v2 - - - name: Setup go - uses: actions/setup-go@v3 - with: - go-version: ${{ inputs.go-version }} - - - name: golangci-lint-${{inputs.directory}} - uses: golangci/golangci-lint-action@v3.4.0 - with: - version: v1.51 - working-directory: ${{inputs.directory}} - args: ${{inputs.args}} diff --git a/.github/workflows/reusable-unit.yml b/.github/workflows/reusable-unit.yml deleted file mode 100644 index 8ba09377cc..0000000000 --- a/.github/workflows/reusable-unit.yml +++ /dev/null @@ -1,57 +0,0 @@ -name: reusable-unit - -on: - workflow_call: - inputs: - directory: - required: true - type: string - go-version: - required: true - type: string - -# Environment variables can only be used at the step level -env: - TEST_RESULTS: /tmp/test-results # path to where test results are saved - GOTESTSUM_VERSION: 1.8.2 - -jobs: - job: - runs-on: ubuntu-latest - - steps: - - name: Checkout code - uses: actions/checkout@v3 - - - name: Setup go - uses: actions/setup-go@v3 - with: - go-version: ${{inputs.go-version}} - - - name: Setup go mod cache - uses: actions/cache@v3 - with: - path: | - ~/.cache/go-build - ~/go/pkg/mod - key: ${{ runner.os }}-go-${{ hashFiles('**/go.sum') }} - restore-keys: | - ${{ runner.os }}-go- - - - name: Install gotestsum - run: | - wget https://github.com/gotestyourself/gotestsum/releases/download/v${{env.GOTESTSUM_VERSION}}/gotestsum_${{env.GOTESTSUM_VERSION}}_linux_amd64.tar.gz - sudo tar -C /usr/local/bin -xzf gotestsum_${{env.GOTESTSUM_VERSION}}_linux_amd64.tar.gz - rm gotestsum_${{env.GOTESTSUM_VERSION}}_linux_amd64.tar.gz - - - run: mkdir -p ${{env.TEST_RESULTS}} - - - name: go mod download - working-directory: ${{inputs.directory}} - run: go mod download - - - name: Run tests - working-directory: ${{inputs.directory}} - run: | - gotestsum --format=testname --junitfile ${{env.TEST_RESULTS}}/gotestsum-report.xml ./... -- -p 4 - diff --git a/.github/workflows/test.yml b/.github/workflows/test.yml deleted file mode 100644 index 803aed69a4..0000000000 --- a/.github/workflows/test.yml +++ /dev/null @@ -1,399 +0,0 @@ -name: test -on: - push: - -env: - TEST_RESULTS: /tmp/test-results # path to where test results are saved - GOTESTSUM_VERSION: 1.8.2 # You cannot use environment variables with workflows. The gotestsum version is hardcoded in the reusable workflows too. - # We use docker images to copy the consul binary for unit tests. - CONSUL_OSS_DOCKER_IMAGE: hashicorppreview/consul:1.14-dev # Consul's OSS version to use in tests - CONSUL_ENT_DOCKER_IMAGE: hashicorppreview/consul-enterprise:1.14-dev # Consul's enterprise version to use in tests - -jobs: - terraform-fmt-check: - name: "Terraform format check" - runs-on: ubuntu-latest - steps: - - uses: actions/checkout@v3 - - name: Setup Terraform - uses: hashicorp/setup-terraform@v2 - with: - terraform_version: TERRAFORM_VERSION - terraform_wrapper: false - - name: Run Terraform checks - run: | - make terraform-fmt-check TERRAFORM_DIR="${{ github.workspace }}" - - get-go-version: - name: "Determine Go toolchain version" - runs-on: ubuntu-latest - outputs: - go-version: ${{ steps.get-go-version.outputs.go-version }} - steps: - - uses: actions/checkout@v3 - - name: Determine Go version - id: get-go-version - # We use .go-version as our source of truth for current Go - # version, because "goenv" can react to it automatically. - run: | - echo "Building with Go $(cat .go-version)" - echo "::set-output name=go-version::$(cat .go-version)" - - get-product-version: - runs-on: ubuntu-latest - outputs: - product-version: ${{ steps.get-product-version.outputs.product-version }} - steps: - - uses: actions/checkout@v3 - - name: get product version - id: get-product-version - run: | - make version - echo "::set-output name=product-version::$(make version)" - - validate-helm-gen: - needs: - - get-go-version - runs-on: ubuntu-latest - steps: - - name: Checkout code - uses: actions/checkout@v3 - - - name: Setup go - uses: actions/setup-go@v3 - with: - go-version: ${{ needs.get-go-version.outputs.go-version }} - - - name: Setup go mod cache - uses: actions/cache@v3 - with: - path: | - ~/.cache/go-build - ~/go/pkg/mod - key: ${{ runner.os }}-go-${{ hashFiles('**/go.sum') }} - restore-keys: | - ${{ runner.os }}-go- - - - name: Validate helm gen - working-directory: hack/helm-reference-gen - run: | - go run ./... -validate - - golangci-lint-helm-gen: - needs: - - get-go-version - uses: ./.github/workflows/reusable-golangci-lint.yml - with: - directory: hack/helm-reference-gen - go-version: ${{ needs.get-go-version.outputs.go-version }} - #TODO: This is a workaround in order to get pipelines working. godot and staticcheck fail for helm-reference-gen - args: "--no-config --disable-all --enable gofmt,govet" - - unit-helm-gen: - needs: [get-go-version, golangci-lint-helm-gen, validate-helm-gen] - uses: ./.github/workflows/reusable-unit.yml - with: - directory: hack/helm-reference-gen - go-version: ${{ needs.get-go-version.outputs.go-version }} - - unit-test-helm-templates: - needs: - - unit-helm-gen - runs-on: ubuntu-latest - container: - image: docker.mirror.hashicorp.services/hashicorpdev/consul-helm-test:0.15.0 - options: --user 1001 - steps: - - name: Checkout code - uses: actions/checkout@v3 - - - name: Run Unit Tests - working-directory: charts/consul - run: bats --jobs 4 ./test/unit - - lint-control-plane: - needs: - - get-go-version - runs-on: ubuntu-latest - steps: - - name: Checkout code - uses: actions/checkout@v3 - - - name: Setup go - uses: actions/setup-go@v3 - with: - go-version: ${{ needs.get-go-version.outputs.go-version }} - - - run: go install github.com/hashicorp/lint-consul-retry@master && lint-consul-retry - - - name: Run lint - working-directory: control-plane - run: go run hack/lint-api-new-client/main.go - - golangci-lint-control-plane: - needs: - - get-go-version - uses: ./.github/workflows/reusable-golangci-lint.yml - with: - directory: control-plane - go-version: ${{ needs.get-go-version.outputs.go-version }} - - test-control-plane: - needs: [get-go-version, lint-control-plane, golangci-lint-control-plane] - runs-on: ubuntu-latest - steps: - - name: Checkout code - uses: actions/checkout@v3 - - - name: Setup go - uses: actions/setup-go@v3 - with: - go-version: ${{ needs.get-go-version.outputs.go-version }} - - - name: Setup go mod cache - uses: actions/cache@v3 - with: - path: | - ~/.cache/go-build - ~/go/pkg/mod - key: ${{ runner.os }}-go-${{ hashFiles('**/go.sum') }} - restore-keys: | - ${{ runner.os }}-go- - - - name: Install gotestsum - run: | - wget https://github.com/gotestyourself/gotestsum/releases/download/v${{env.GOTESTSUM_VERSION}}/gotestsum_${{env.GOTESTSUM_VERSION}}_linux_amd64.tar.gz - sudo tar -C /usr/local/bin -xzf gotestsum_${{env.GOTESTSUM_VERSION}}_linux_amd64.tar.gz - rm gotestsum_${{env.GOTESTSUM_VERSION}}_linux_amd64.tar.gz - - - run: mkdir -p ${{env.TEST_RESULTS}} - - run: echo "$HOME/bin" >> $GITHUB_PATH - - - name: Download consul - working-directory: control-plane - run: | - mkdir -p $HOME/bin - container_id=$(docker create ${{env.CONSUL_OSS_DOCKER_IMAGE}}) - docker cp "$container_id:/bin/consul" $HOME/bin/consul - docker rm "$container_id" - - name: Run go tests - working-directory: control-plane - run: | - PACKAGE_NAMES=$(go list ./...) - gotestsum --format=testname --junitfile ${{env.TEST_RESULTS}}/gotestsum-report.xml -- -p 4 $PACKAGE_NAMES - - test-enterprise-control-plane: - if: github.repository_owner == 'hashicorp' # Do not run on forks as this requires secrets - needs: [get-go-version, lint-control-plane, golangci-lint-control-plane] - runs-on: ubuntu-latest - env: - CONSUL_LICENSE: ${{secrets.CONSUL_LICENSE}} - steps: - - name: Checkout code - uses: actions/checkout@v3 - - - name: Setup go - uses: actions/setup-go@v3 - with: - go-version: ${{ needs.get-go-version.outputs.go-version }} - - - name: Setup go mod cache - uses: actions/cache@v3 - with: - path: | - ~/.cache/go-build - ~/go/pkg/mod - key: ${{ runner.os }}-go-${{ hashFiles('**/go.sum') }} - restore-keys: | - ${{ runner.os }}-go- - - - name: Install gotestsum - run: | - wget https://github.com/gotestyourself/gotestsum/releases/download/v${{env.GOTESTSUM_VERSION}}/gotestsum_${{env.GOTESTSUM_VERSION}}_linux_amd64.tar.gz - sudo tar -C /usr/local/bin -xzf gotestsum_${{env.GOTESTSUM_VERSION}}_linux_amd64.tar.gz - rm gotestsum_${{env.GOTESTSUM_VERSION}}_linux_amd64.tar.gz - - - run: mkdir -p ${{env.TEST_RESULTS}} - - run: echo "$HOME/bin" >> $GITHUB_PATH - - - name: Download consul - working-directory: control-plane - run: | - mkdir -p $HOME/bin - container_id=$(docker create ${{env.CONSUL_ENT_DOCKER_IMAGE}}) - docker cp "$container_id:/bin/consul" $HOME/bin/consul - docker rm "$container_id" - - - name: Run go tests - working-directory: control-plane - run: | - PACKAGE_NAMES=$(go list ./...) - gotestsum --format=testname --junitfile ${{env.TEST_RESULTS}}/gotestsum-report.xml -- -tags=enterprise -p 4 $PACKAGE_NAMES - - build-distros: - needs: [get-go-version, get-product-version] - runs-on: ubuntu-latest - strategy: - matrix: - include: - # cli - - {go: "${{ needs.get-go-version.outputs.go-version }}", goos: "linux", goarch: "amd64", component: "cli", pkg_name: "consul-k8s", "bin_name": "consul-k8s" } - # control-plane - - {go: "${{ needs.get-go-version.outputs.go-version }}", goos: "linux", goarch: "amd64", component: "control-plane", pkg_name: "consul-k8s-control-plane", "bin_name": "consul-k8s-control-plane" } - # consul-cni - - {go: "${{ needs.get-go-version.outputs.go-version }}", goos: "linux", goarch: "amd64", component: "control-plane/cni", pkg_name: "consul-cni", "bin_name": "consul-cni" } - - fail-fast: true - - name: Go ${{ matrix.go }} ${{ matrix.goos }} ${{ matrix.goarch }} ${{ matrix.component }} build - steps: - - uses: actions/checkout@v3 - - - name: Setup go - uses: actions/setup-go@v3 - with: - go-version: ${{ matrix.go }} - - - name: Build - env: - GOOS: ${{ matrix.goos }} - GOARCH: ${{ matrix.goarch }} - CGO_ENABLED: 0 - working-directory: ${{ matrix.component }} - run: | - mkdir -p dist out - - export GIT_COMMIT=$(git rev-parse --short HEAD) - export GIT_DIRTY=$(test -n "$(git status --porcelain)" && echo "+CHANGES") - export GIT_IMPORT=github.com/hashicorp/consul-k8s/${{ matrix.component }}/version - export GOLDFLAGS="-X ${GIT_IMPORT}.GitCommit=${GIT_COMMIT}${GIT_DIRTY} -X ${GIT_IMPORT}.GitDescribe=${{ needs.get-product-version.outputs.product-version }}" - - CGO_ENABLED=0 go build -o dist/${{ matrix.bin_name }} -ldflags "${GOLDFLAGS}" . - zip -r -j out/${{ matrix.pkg_name }}_${{ needs.get-product-version.outputs.product-version }}_${{ matrix.goos }}_${{ matrix.goarch }}.zip dist/ - - - name: Upload built binaries - uses: actions/upload-artifact@v3 - with: - name: ${{ matrix.pkg_name }}_${{ needs.get-product-version.outputs.product-version }}_${{ matrix.goos }}_${{ matrix.goarch }}.zip - path: ${{ matrix.component}}/out/${{ matrix.pkg_name }}_${{ needs.get-product-version.outputs.product-version }}_${{ matrix.goos }}_${{ matrix.goarch }}.zip - - golangci-lint-acceptance: - needs: - - get-go-version - uses: ./.github/workflows/reusable-golangci-lint.yml - with: - directory: acceptance - go-version: ${{ needs.get-go-version.outputs.go-version }} - - unit-acceptance-framework: - needs: [get-go-version, golangci-lint-acceptance] - uses: ./.github/workflows/reusable-unit.yml - with: - directory: acceptance/framework - go-version: ${{ needs.get-go-version.outputs.go-version }} - - golangci-lint-cli: - needs: - - get-go-version - uses: ./.github/workflows/reusable-golangci-lint.yml - with: - directory: cli - go-version: ${{ needs.get-go-version.outputs.go-version }} - - unit-cli: - needs: [get-go-version, golangci-lint-cli] - uses: ./.github/workflows/reusable-unit.yml - with: - directory: cli - go-version: ${{ needs.get-go-version.outputs.go-version }} - - # upload dev docker image - dev-upload-docker: - if: github.repository_owner == 'hashicorp' # Do not run on forks as this requires secrets - needs: [ get-product-version, build-distros ] - runs-on: ubuntu-latest - strategy: - matrix: - arch: ["amd64"] - env: - repo: ${{ github.event.repository.name }} - version: ${{ needs.get-product-version.outputs.product-version }} - steps: - - uses: actions/checkout@v3 - - uses: actions/download-artifact@v3 - with: - name: consul-cni_${{ needs.get-product-version.outputs.product-version }}_linux_${{ matrix.arch }}.zip - path: control-plane/dist/cni/linux/${{ matrix.arch }} - - uses: actions/download-artifact@v3 - with: - name: consul-k8s-control-plane_${{ needs.get-product-version.outputs.product-version }}_linux_${{ matrix.arch }}.zip - path: control-plane/dist/linux/${{ matrix.arch }} - - name: extract consul-cni zip - env: - ZIP_LOCATION: control-plane/dist/cni/linux/${{ matrix.arch }} - run: | - cd "${ZIP_LOCATION}" - unzip -j *.zip - - name: extract control-plane zip - env: - ZIP_LOCATION: control-plane/dist/linux/${{ matrix.arch }} - run: | - cd "${ZIP_LOCATION}" - unzip -j *.zip - - name: Set up Docker Buildx - uses: docker/setup-buildx-action@v2 - - name: Login to Docker Hub - uses: docker/login-action@v2 - with: - username: ${{ secrets.DOCKER_USER }} - password: ${{ secrets.DOCKER_PASS }} - - name: Docker Build (Action) - uses: docker/build-push-action@v3 - with: - push: true - context: control-plane - platforms: ${{ matrix.arch }} - target: release-default - tags: docker.io/hashicorppreview/${{ env.repo }}-control-plane:${{ env.version }}-pr-${{ github.sha }} - -# Disable GHA acceptance tests until GHA formally supported -# acceptance: -# needs: [ get-product-version, dev-upload-docker, get-go-version ] -# uses: ./.github/workflows/reusable-acceptance.yml -# with: -# name: acceptance -# directory: acceptance/tests -# go-version: ${{ needs.get-go-version.outputs.go-version }} -# additional-flags: "-use-kind -kubecontext=kind-dc1 -secondary-kubecontext=kind-dc2 -consul-image=docker.mirror.hashicorp.services/hashicorppreview/consul-enterprise:1.14-dev" -# gotestsum-version: 1.8.2 -# consul-k8s-image: docker.io/hashicorppreview/${{ github.event.repository.name }}-control-plane:${{ needs.get-product-version.outputs.product-version }}-pr-${{ github.sha }} -# secrets: -# CONSUL_ENT_LICENSE: ${{ secrets.CONSUL_ENT_LICENSE }} -# -# acceptance-tproxy: -# needs: [ get-product-version, dev-upload-docker, get-go-version ] -# uses: ./.github/workflows/reusable-acceptance.yml -# with: -# name: acceptance-tproxy -# directory: acceptance/tests -# go-version: ${{ needs.get-go-version.outputs.go-version }} -# additional-flags: "-use-kind -kubecontext=kind-dc1 -secondary-kubecontext=kind-dc2 -enable-transparent-proxy -consul-image=docker.mirror.hashicorp.services/hashicorppreview/consul-enterprise:1.14-dev" -# gotestsum-version: 1.8.2 -# consul-k8s-image: docker.io/hashicorppreview/${{ github.event.repository.name }}-control-plane:${{ needs.get-product-version.outputs.product-version }}-pr-${{ github.sha }} -# secrets: -# CONSUL_ENT_LICENSE: ${{ secrets.CONSUL_ENT_LICENSE }} -# -# acceptance-cni: -# needs: [ get-product-version, dev-upload-docker, get-go-version ] -# uses: ./.github/workflows/reusable-acceptance.yml -# with: -# name: acceptance -# directory: acceptance/tests -# go-version: ${{ needs.get-go-version.outputs.go-version }} -# additional-flags: "-use-kind -kubecontext=kind-dc1 -secondary-kubecontext=kind-dc2 -enable-transparent-proxy -enable-cni -consul-image=docker.mirror.hashicorp.services/hashicorppreview/consul-enterprise:1.14-dev" -# gotestsum-version: 1.8.2 -# consul-k8s-image: docker.io/hashicorppreview/${{ github.event.repository.name }}-control-plane:${{ needs.get-product-version.outputs.product-version }}-pr-${{ github.sha }} -# secrets: -# CONSUL_ENT_LICENSE: ${{ secrets.CONSUL_ENT_LICENSE }} - - diff --git a/.github/workflows/weekly-acceptance-0-49-x.yml b/.github/workflows/weekly-acceptance-0-49-x.yml new file mode 100644 index 0000000000..7025bcb241 --- /dev/null +++ b/.github/workflows/weekly-acceptance-0-49-x.yml @@ -0,0 +1,29 @@ +# Dispatch to the consul-k8s-workflows with a weekly cron +# +# A separate file is needed for each release because the cron schedules are different for each release. +name: weekly-acceptance-0-49-x +on: + schedule: + # * is a special character in YAML so you have to quote this string + # Run weekly on Monday at 3AM UTC/11PM EST/8PM PST + - cron: '0 3 * * 1' + +# these should be the only settings that you will ever need to change +env: + CONSUL_IMAGE: hashicorppreview/consul-enterprise:1.13-dev # Consul's enterprise version to use in tests + BRANCH: "release/0.49.x" + CONTEXT: "weekly" + +jobs: + cloud: + name: cloud + runs-on: ubuntu-latest + steps: + - uses: benc-uk/workflow-dispatch@v1.2.2 + name: cloud + with: + workflow: cloud.yml + repo: hashicorp/consul-k8s-workflows + ref: main + token: ${{ secrets.ELEVATED_GITHUB_TOKEN }} + inputs: '{ "context":"${{ env.CONTEXT }}", "repository":"${{ github.repository }}", "branch":"${{ env.BRANCH }}", "sha":"${{ github.sha }}", "token":"${{ secrets.ELEVATED_GITHUB_TOKEN }}", "consul-image":"${{ env.CONSUL_IMAGE }}" }' diff --git a/.github/workflows/weekly-acceptance-1-0-x.yml b/.github/workflows/weekly-acceptance-1-0-x.yml new file mode 100644 index 0000000000..4aa49594f3 --- /dev/null +++ b/.github/workflows/weekly-acceptance-1-0-x.yml @@ -0,0 +1,30 @@ +# Dispatch to the consul-k8s-workflows with a weekly cron +# +# A separate file is needed for each release because the cron schedules are different for each release. +name: weekly-acceptance-1-0-x +on: + schedule: + # * is a special character in YAML so you have to quote this string + # Run weekly on Tuesday at 3AM UTC/11PM EST/8PM PST + - cron: '0 3 * * 2' + + +# these should be the only settings that you will ever need to change +env: + CONSUL_IMAGE: hashicorppreview/consul-enterprise:1.14-dev # Consul's enterprise version to use in tests + BRANCH: "release/1.0.x" + CONTEXT: "weekly" + +jobs: + cloud: + name: cloud + runs-on: ubuntu-latest + steps: + - uses: benc-uk/workflow-dispatch@v1.2.2 + name: cloud + with: + workflow: cloud.yml + repo: hashicorp/consul-k8s-workflows + ref: main + token: ${{ secrets.ELEVATED_GITHUB_TOKEN }} + inputs: '{ "context":"${{ env.CONTEXT }}", "repository":"${{ github.repository }}", "branch":"${{ env.BRANCH }}", "sha":"${{ github.sha }}", "token":"${{ secrets.ELEVATED_GITHUB_TOKEN }}", "consul-image":"${{ env.CONSUL_IMAGE }}" }' diff --git a/.github/workflows/weekly-acceptance-1-1-x.yml b/.github/workflows/weekly-acceptance-1-1-x.yml new file mode 100644 index 0000000000..1ffc6f8684 --- /dev/null +++ b/.github/workflows/weekly-acceptance-1-1-x.yml @@ -0,0 +1,30 @@ +# Dispatch to the consul-k8s-workflows with a weekly cron +# +# A separate file is needed for each release because the cron schedules are different for each release. +name: weekly-acceptance-1-1-x +on: + schedule: + # * is a special character in YAML so you have to quote this string + # Run weekly on Wednesday at 3AM UTC/11PM EST/8PM PST + - cron: '0 3 * * 3' + + +# these should be the only settings that you will ever need to change +env: + CONSUL_IMAGE: hashicorppreview/consul-enterprise:1.15-dev # Consul's enterprise version to use in tests + BRANCH: "release/1.1.x" + CONTEXT: "weekly" + +jobs: + cloud: + name: cloud + runs-on: ubuntu-latest + steps: + - uses: benc-uk/workflow-dispatch@v1.2.2 + name: cloud + with: + workflow: cloud.yml + repo: hashicorp/consul-k8s-workflows + ref: main + token: ${{ secrets.ELEVATED_GITHUB_TOKEN }} + inputs: '{ "context":"${{ env.CONTEXT }}", "repository":"${{ github.repository }}", "branch":"${{ env.BRANCH }}", "sha":"${{ github.sha }}", "token":"${{ secrets.ELEVATED_GITHUB_TOKEN }}", "consul-image":"${{ env.CONSUL_IMAGE }}" }' diff --git a/.go-version b/.go-version index 0044d6cb96..91c48c058d 100644 --- a/.go-version +++ b/.go-version @@ -1 +1 @@ -1.20.1 +1.19.9 diff --git a/CHANGELOG.md b/CHANGELOG.md index e0df700efa..85fc6f4382 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -1,33 +1,26 @@ -## 1.0.5 (March 9, 2023) +## 1.0.6 (March 20, 2023) -SECURITY: +IMPROVEMENTS: -* upgrade to use Go 1.19.6. This resolves vulnerabilities CVE-2022-41724 in crypto/tls and CVE-2022-41723 in net/http. [[GH-1976](https://github.com/hashicorp/consul-k8s/issues/1976)] +* helm: Set default `limits.cpu` resource setting to `null` for `consul-connect-inject-init` container to speed up registration times when onboarding services onto the mesh during the init container lifecycle. [[GH-2008](https://github.com/hashicorp/consul-k8s/issues/2008)] -IMPROVEMENTS: +BUG FIXES: -* control-plane: server ACL Init always appends both, the secrets from the serviceAccount's secretRefs and the one created by the Helm chart, to support Openshift secret handling. [[GH-1770](https://github.com/hashicorp/consul-k8s/issues/1770)] -* control-plane: update alpine to 3.17 in the Docker image. [[GH-1934](https://github.com/hashicorp/consul-k8s/issues/1934)] -* helm: update `imageConsulDataplane` value to `hashicorp/consul-dataplane:1.1.0`. [[GH-1953](https://github.com/hashicorp/consul-k8s/issues/1953)] +* api-gateway: fix issue where specifying an external server SNI name while using client nodes resulted in a TLS verification error. [[GH-2013](https://github.com/hashicorp/consul-k8s/issues/2013)] -## 0.49.5 (March 9, 2023) +## 1.0.5 (March 9, 2023) SECURITY: -* upgrade to use Go 1.19.6. This resolves vulnerabilities CVE-2022-41724 in crypto/tls and CVE-2022-41723 in net/http. [[GH-1975](https://github.com/hashicorp/consul-k8s/issues/1975)] +* upgrade to use Go 1.19.6. This resolves vulnerabilities CVE-2022-41724 in crypto/tls and CVE-2022-41723 in net/http. [[GH-1976](https://github.com/hashicorp/consul-k8s/issues/1976)] IMPROVEMENTS: -* cli: update minimum go version for project to 1.19. [[GH-1975](https://github.com/hashicorp/consul-k8s/issues/1975)] * control-plane: server ACL Init always appends both, the secrets from the serviceAccount's secretRefs and the one created by the Helm chart, to support Openshift secret handling. [[GH-1770](https://github.com/hashicorp/consul-k8s/issues/1770)] * control-plane: update alpine to 3.17 in the Docker image. [[GH-1934](https://github.com/hashicorp/consul-k8s/issues/1934)] -* control-plane: update minimum go version for project to 1.19. [[GH-1975](https://github.com/hashicorp/consul-k8s/issues/1975)] - -BUG FIXES: - -* control-plane: fix issue where consul-connect-injector acl token was unintentionally being deleted and not recreated when a container was restarted due to a livenessProbe failure. [[GH-1914](https://github.com/hashicorp/consul-k8s/issues/1914)] +* helm: update `imageConsulDataplane` value to `hashicorp/consul-dataplane:1.1.0`. [[GH-1953](https://github.com/hashicorp/consul-k8s/issues/1953)] -## 1.1.0 (February 27, 2023) +## 1.0.4 (February 7, 2023) BREAKING CHANGES: * Helm: @@ -43,36 +36,10 @@ BREAKING CHANGES: values: ["kube-system","local-path-storage"] ``` [[GH-1869](https://github.com/hashicorp/consul-k8s/pull/1869)] - + IMPROVEMENTS: -* Helm: - * CNI: Add `connectInject.cni.namespace` stanza which allows the CNI plugin resources to be deployed in a namespace other than the namespace that Consul is installed. [[GH-1756](https://github.com/hashicorp/consul-k8s/pull/1756)] - * Kubernetes v1.26 is now supported. Minimum tested version of Kubernetes is now v1.23. [[GH-1852](https://github.com/hashicorp/consul-k8s/pull/1852)] - * Add a `global.extraLabels` stanza to allow setting global Kubernetes labels for all components deployed by the `consul-k8s` Helm chart. [[GH-1778](https://github.com/hashicorp/consul-k8s/pull/1778)] - * Add the `accessLogs` field to the `ProxyDefaults` CRD. [[GH-1816](https://github.com/hashicorp/consul-k8s/pull/1816)] - * Add the `envoyExtensions` field to the `ProxyDefaults` and `ServiceDefaults` CRD. [[GH-1823]](https://github.com/hashicorp/consul-k8s/pull/1823) - * Add the `balanceInboundConnections` field to the `ServiceDefaults` CRD. [[GH-1823]](https://github.com/hashicorp/consul-k8s/pull/1823) - * Add the `upstreamConfig.overrides[].peer` field to the `ServiceDefaults` CRD. [[GH-1853]](https://github.com/hashicorp/consul-k8s/pull/1853) -* Control-Plane - * Update minimum go version for project to 1.20 [[GH-1908](https://github.com/hashicorp/consul-k8s/pull/1908)] - * Add support for the annotation `consul.hashicorp.com/use-proxy-health-check`. When this annotation is used by a service, it configures a readiness endpoint on Consul Dataplane and queries it instead of the proxy's inbound port which forwards requests to the application. [[GH-1824](https://github.com/hashicorp/consul-k8s/pull/1824)], [[GH-1841](https://github.com/hashicorp/consul-k8s/pull/1841)] - * Add health check for synced services based on the status of the Kubernetes readiness probe on synced pod. [[GH-1821](https://github.com/hashicorp/consul-k8s/pull/1821)] - * Remove extraneous `gnupg` dependency from `consul-k8s-control-plane` since it is no longer needed for validating binary artifacts prior to release. [[GH-1882](https://github.com/hashicorp/consul-k8s/pull/1882)] - * Server ACL Init always appends both, the secrets from the serviceAccount's secretRefs and the one created by the Helm chart, to support Openshift secret handling. [[GH-1770](https://github.com/hashicorp/consul-k8s/pull/1770)] - * Update alpine to 3.17 in the Docker image. [[GH-1934](https://github.com/hashicorp/consul-k8s/pull/1934)] -* CLI: - * Update minimum go version for project to 1.20 [[GH-1908](https://github.com/hashicorp/consul-k8s/pull/1908)] - * Add `consul-k8s proxy log podname` command for displaying and modifying Envoy log levels for a given Pod. [GH-1844](https://github.com/hashicorp/consul-k8s/pull/1844), [GH-1849](https://github.com/hashicorp/consul-k8s/pull/1849), [GH-1864](https://github.com/hashicorp/consul-k8s/pull/1864) - -BUG FIXES: -* Control Plane - * Don't incorrectly diff intention config entries when upgrading from Consul pre-1.12 to 1.12+ [[GH-1804](https://github.com/hashicorp/consul-k8s/pull/1804)] - * Add discover binary to control-plane image [[GH-1749](https://github.com/hashicorp/consul-k8s/pull/1749)] -* Helm: - * Don't pass in a CA file to the API Gateway controller when `externalServers.useSystemRoots` is `true`. [[GH-1743](https://github.com/hashicorp/consul-k8s/pull/1743)] - * Use the correct autogenerated cert for the API Gateway Controller when connecting to servers versus clients. [[GH-1753](https://github.com/hashicorp/consul-k8s/pull/1753)] -* Security: - * Upgrade to use Go 1.20.1 This resolves vulnerabilities [CVE-2022-41724](https://go.dev/issue/58001) in `crypto/tls` and [CVE-2022-41723](https://go.dev/issue/57855) in `net/http`. [[GH-1908](https://github.com/hashicorp/consul-k8s/pull/1908)] + * Control Plane + * Remove extraneous `gnupg` dependency from `consul-k8s-control-plane` since it is no longer needed for validating binary artifacts prior to release. [[GH-1882](https://github.com/hashicorp/consul-k8s/pull/1882)] ## 1.0.3 (January 30, 2023) @@ -88,42 +55,19 @@ BUG FIXES: * Control Plane * Don't incorrectly diff intention config entries when upgrading from Consul pre-1.12 to 1.12+ [[GH-1804](https://github.com/hashicorp/consul-k8s/pull/1804)] -## 0.49.3 (January 30, 2023) - -IMPROVEMENTS: -* Helm: - * Add a `global.extraLabels` stanza to allow setting global Kubernetes labels for all components deployed by the `consul-k8s` Helm chart. [[GH-1778](https://github.com/hashicorp/consul-k8s/pull/1778)] -* Control-Plane - * Add support for the annotation `consul.hashicorp.com/use-proxy-health-check`. When this annotation is used by a service, it configures a readiness endpoint on Consul Dataplane and queries it instead of the proxy's inbound port which forwards requests to the application. [[GH-1824](https://github.com/hashicorp/consul-k8s/pull/1824)], [[GH-1843](https://github.com/hashicorp/consul-k8s/pull/1843)] - * Add health check for synced services based on the status of the Kubernetes readiness probe on synced pod. [[GH-1821](https://github.com/hashicorp/consul-k8s/pull/1821)] - -BUG FIXES: -* Control Plane - * Don't incorrectly diff intention config entries when upgrading from Consul pre-1.12 to 1.12+ [[GH-1804](https://github.com/hashicorp/consul-k8s/pull/1804)] - ## 1.0.2 (December 1, 2022) IMPROVEMENTS: * Helm: * CNI: Add `connectInject.cni.namespace` stanza which allows the CNI plugin resources to be deployed in a namespace other than the namespace that Consul is installed. [[GH-1756](https://github.com/hashicorp/consul-k8s/pull/1756)] +* Control Plane: + * Server ACL Init always appends both, the secrets from the serviceAccount's secretRefs and the one created by the Helm chart, to support Openshift secret handling. [[GH-1770](https://github.com/hashicorp/consul-k8s/pull/1770)] BUG FIXES: * Helm: * Use the correct autogenerated cert for the API Gateway Controller when connecting to servers versus clients. [[GH-1753](https://github.com/hashicorp/consul-k8s/pull/1753)] * Don't mount the CA cert when `externalServers.useSystemRoots` is `true`. [[GH-1753](https://github.com/hashicorp/consul-k8s/pull/1753)] -## 0.49.2 (December 1, 2022) - -IMPROVEMENTS: -* Control Plane - * Bump Dockerfile base image for RedHat UBI `consul-k8s-control-plane` image to `ubi-minimal:9.1`. [[GH-1725](https://github.com/hashicorp/consul-k8s/pull/1725)] -* Helm - * Add fields `localConnectTimeoutMs` and `localRequestTimeoutMs` to the `ServiceDefaults` CRD. [[GH-1647](https://github.com/hashicorp/consul-k8s/pull/1647)] - -BUG FIXES: -* Helm: - * Disable PodSecurityPolicies templating for `gossip-encryption-autogenerate` and `partition-init` when `global.enablePodSecurityPolicies` is `false`. [[GH-1693](https://github.com/hashicorp/consul-k8s/pull/1693)] - ## 1.0.1 (November 21, 2022) BUG FIXES: @@ -225,6 +169,7 @@ IMPROVEMENTS: * API Gateway: Allow controller to read MeshServices for use as a route backend. [[GH-1574](https://github.com/hashicorp/consul-k8s/pull/1574)] * API Gateway: Add support for using dynamic server discovery strings when running without agents. [[GH-1732](https://github.com/hashicorp/consul-k8s/pull/1732)] + BUG FIXES: * CLI * Allow optional environment variables for use in the cloud preset to the CLI for cluster bootstrapping. [[GH-1608](https://github.com/hashicorp/consul-k8s/pull/1608)] @@ -233,24 +178,7 @@ BUG FIXES: * Peering * Add `peering:read` permissions to mesh gateway token to fix peering connections through the mesh gateways. [[GH-1685](https://github.com/hashicorp/consul-k8s/pull/1685)] * Helm: - * Disable PodSecurityPolicies in all templates when `global.enablePodSecurityPolicies` is `false`. [[GH-1693](https://github.com/hashicorp/consul-k8s/pull/1693)] - -## 0.49.1 (November 14, 2022) -BREAKING CHANGES: -* Peering: - * Rename `PeerName` to `Peer` in ExportedServices CRD. [[GH-1596](https://github.com/hashicorp/consul-k8s/pull/1596)] - -FEATURES: -* Ingress Gateway - * Add support for MaxConnections, MaxConcurrentRequests, and MaxPendingRequests to Ingress Gateway CRD. [[GH-1691](https://github.com/hashicorp/consul-k8s/pull/1691)] - -IMPROVEMENTS: -* Helm: - * Add `tolerations` and `nodeSelector` to Server ACL init jobs and `nodeSelector` to Webhook cert manager. [[GH-1581](https://github.com/hashicorp/consul-k8s/pull/1581)] - * API Gateway: Allow controller to read MeshServices for use as a route backend. [[GH-1574](https://github.com/hashicorp/consul-k8s/pull/1574)] - * API Gateway: Add `tolerations` to `apiGateway.managedGatewayClass` and `apiGateway.controller` [[GH-1650](https://github.com/hashicorp/consul-k8s/pull/1650)] - * API Gateway: Create PodSecurityPolicy for controller when `global.enablePodSecurityPolicies=true`. [[GH-1656](https://github.com/hashicorp/consul-k8s/pull/1656)] - * API Gateway: Create PodSecurityPolicy and allow controller to bind it to ServiceAccounts that it creates for Gateway Deployments when `global.enablePodSecurityPolicies=true`. [[GH-1672](https://github.com/hashicorp/consul-k8s/pull/1672)] + * Disable PodSecurityPolicies templating for `gossip-encryption-autogenerate` and `partition-init` when `global.enablePodSecurityPolicies` is `false`. [[GH-1693](https://github.com/hashicorp/consul-k8s/pull/1693)] ## 0.49.0 (September 29, 2022) diff --git a/CONTRIBUTING.md b/CONTRIBUTING.md index 8e634e323e..831929236d 100644 --- a/CONTRIBUTING.md +++ b/CONTRIBUTING.md @@ -22,10 +22,10 @@ 1. [Running the tests](#running-the-tests) 1. [Writing Unit tests](#writing-unit-tests) 1. [Writing Acceptance tests](#writing-acceptance-tests) -1. [Using the Acceptance Test Framework to Debug](#using-acceptance-test-framework-to-debug) 1. [Helm Reference Docs](#helm-reference-docs) 1. [Adding a Changelog Entry](#adding-a-changelog-entry) + ## Contributing 101 ### Building and running `consul-k8s-control-plane` @@ -425,27 +425,20 @@ rebase the branch on main, fixing any conflicts along the way before the code ca manage your resource type. ### Testing A New CRD -1. Build a Docker image for consul-k8s via `make control-plane-dev-docker` and push to a docker repository: - ``` - docker tag consul-k8s-control-plane-dev /consul-k8s-control-plane-dev: - docker push /consul-k8s-control-plane-dev: - ``` +1. Build a Docker image for consul-k8s via `make dev-docker` and tagging your image appropriately. Remember to CD into the `control-plane` directory! 1. Install using the updated Helm repository, with a values like: ```yaml global: - imageK8S: lkysow/consul-k8s-control-plane-dev:nov26 + imageK8S: ghcr.io/lkysow/consul-k8s-dev:nov26 name: consul server: replicas: 1 bootstrapExpect: 1 - ui: - enabled: true - connectInject: + controller: enabled: true ``` -1. Create a sample CRD -1. Run `kubectl apply -f ` to apply your sample CRD. -1. Check its synced status (for example CRD called ingressgateway): +1. `kubectl apply` your sample CRD. +1. Check its synced status: ```bash kubectl get ingressgateway NAME SYNCED AGE @@ -948,198 +941,6 @@ Here are some things to consider before adding a test: --- -## Using Acceptance Test Framework to Debug -### Acceptance Tests - -The [consul-k8s](https://github.com/hashicorp/consul-k8s) repository has an extensive list of [acceptance](https://github.com/hashicorp/consul-k8s/tree/main/acceptance/tests) -tests that are used by CI to run per-PR and nightly acceptance tests. -It is built on its own framework that uses Helm and the consul-k8s CLI to deploy consul (and other tools) in various -configurations that provide test coverage for most features that exist and provides coverage for more advanced deployments -than are typically covered in guides. -Importantly, it is **automated**, so you are able to rapidly deploy known working -configurations in known working environments. -It can be very helpful for bootstrapping complex environments such as when using Vault as a CA for Consul or for federating test clusters. - -The tests are organized like this : -```shell -demo $ tree -L 1 -d acceptance/tests -acceptance/tests -├── basic -├── cli -├── config-entries -├── connect -├── consul-dns -├── example -├── fixtures -├── ingress-gateway -├── metrics -├── partitions -├── peering -├── snapshot-agent -├── sync -├── terminating-gateway -├── vault -└── wan-federation -``` - -### Basic Running of Tests -Any given test can be run either through GoLand or another IDE, or via command line using `go test -run`. - -To run all of the connect tests from command line: -```shell -$ cd acceptance/tests -$ go test ./connect/... -v -p 1 -timeout 2h -failfast -use-kind -no-cleanup-on-failure -kubecontext=kind-dc1 -secondary-kubecontext=kind-dc2 -enable-enterprise -enable-multi-cluster -debug-directory=/tmp/debug -consul-k8s-image=kyleschochenmaier/consul-k8s-acls -``` - -When running from command line a few things are important: -* Some tests use Enterprise features, in which case you need: - * Set environment variables `CONSUL_ENT_LICENSE` and possibly `VAULT_LICENSE`. - * Use `-enable-enterprise` on command line when running the test. -* Multi-cluster tests require `-enable-multi-cluster -kubecontext=kind-dc1 -secondary-kubecontext=kind-dc2` -* Using `.//...` is required as part of the command-line to pick up necessary environmental config. - -### Using the framework to debug in an environment -=> NOTE: It is helpful to tune the docker desktop resource settings so that docker has at least 4GB memory, plenty of cpu cores and 2GB of swap. - -* If using Kind, `-use-kind` should be added, and be sure you cluster is up and running: -```shell -$ kind create cluster --name=dc1 && kind create cluster --name=dc2 -``` -* Pick a test which replicates the environment you are wanting to work with. - Ex: pick a test from `partitions/` or `vault/` or `connect/`. -* If you need the environment to persist, add a `time.Sleep(1*time.Hour)` to the end of the test in the test file. -* Use the following flags if you need to use or test out a specific consul/k8s image: - `-consul-k8s-image=` && `-consul-image=` -* You can set custom helm flags by modifying the test file directly in the respective directory. - -Finally, run the test like shown above: -```shell -$ cd acceptance/tests -$ go test -run Vault_WANFederationViaGateways ./vault/... -p 1 -timeout 2h -failfast -use-kind -no-cleanup-on-failure -kubecontext=kind-dc1 -secondary-kubecontext=kind-dc2 -enable-multi-cluster -debug-directory=/tmp/debug -``` -You can interact with the running kubernetes clusters now using `kubectl [COMMAND] --context=` - -* `kind delete clusters --all` is helpful for cleanup! - -### Example Debugging session using the acceptance test framework to bootstrap and debug a Vault backed federated Consul installation: -This test utilizes the `consul-k8s` acceptance test framework, with a custom consul-k8s branch which: -* Modifies the acceptance test to use custom consul+consul-k8s images and sleeps at the end of the test to allow analysis. -* Modifies the helm chart to pass in `connect_ca.intermediate_cert_ttl` and `connect_ca.leaf_cert_ttl` in the `server-configmap` - -1. First clone the consul-k8s repo and then check out the branch locally: `git checkout origin/consul-vault-provider-wanfed-acceptance`. -2. Start the kind clusters: `kind create cluster --name=dc1 && kind create cluster --name=dc2` -3. run the `TestVault_WANFederationViaGateways` acceptance test in `acceptance/tests/vault/vault_wan_fed_test.go` - I use goland, but this command should get you most of the way: -```shell -$ cd acceptance/tests -$ go test -run Vault_WANFederationViaGateways ./vault/... -p 1 -timeout 2h -failfast -use-kind -no-cleanup-on-failure -kubecontext=kind-dc1 -secondary-kubecontext=kind-dc2 -enable-multi-cluster -debug-directory=/tmp/debug -``` -NOTE: This specific acceptance test is considered FLAKY with Kind, if things don't come up it's best to run against GKE/AKS/etc, in which case you just modify the `kubecontext` command parameters to point to your clusters. It is worth noting that you will need to setup any necessary networking for non-Kind clusters manually. - -NOTE: This test requires a VAULT_LICENSE set as an environment variable in the shell where you run `go test` - -4. Wait 10-20 minutes to allow the first intermediate ca renewal, this test is particularly resource intensive so it can take time for everything to come online on a laptop, use `kubectl get pods` to validate that `static-server` and `static-client` have been deployed and are online. - -You can validate the ICA rotation by doing: -```shell -# Fetch the vault root token: -$ kubectl get secrets -root-token -o json //----> b64 decode the `data.token` field. -$ kubectl exec -it -- sh -$ export VAULT_TOKEN= -$ export VAULT_ADDR=https://-vault:8200 - -# Fetch the consul bootstrap token -$ vault kv get consul/secret/bootstrap - -# Examine the vault issuers, there should be 2 by now if ICA renewal has occured: -# NOTE: for a federated setup the issuers url for dc2 is `vault list dc2/connect_inter/issuers`! -$ vault list dc1/connect_inter/issuers - -Keys ----- -29bdffbd-87ec-cfe0-fd05-b78f99eba243 -344eea3c-f085-943a-c3ff-66721ef408f4 - -# Now login to the consul-server -$ kubectl exec -it -- sh -$ export CONSUL_HTTP_TOKEN= -$ export CONSUL_HTTP_ADDR=https://localhost:8501 -$ export CONSUL_HTTP_SSL_VERIFY=false - -# Read the `connect/ca/roots` endpoint: -# It should change + rotate with the expiration of the ICA (defined by `intermediate_cert_ttl` which is `15m` in the branch for this gist. - -$ curl -k --header "X-Consul-Token: 1428da53-5e88-db1a-6ad5-e50212b011da" https://127.0.0.1:8501/v1/agent/connect/ca/roots | jq - . - % Total % Received % Xferd Average Speed Time Time Time Current - Dload Upload Total Spent Left Speed -100 3113 100 3113 0 0 6222 0 --:--:-- --:--:-- --:--:-- 7705 -{ - "ActiveRootID": "36:be:19:0e:56:d1:c2:1a:d8:54:22:97:88:3c:91:17:1d:d2:d3:e0", - "TrustDomain": "34a76791-b9b2-b93e-b0e4-1989ed11a28e.consul", - "Roots": [ - { - "ID": "36:be:19:0e:56:d1:c2:1a:d8:54:22:97:88:3c:91:17:1d:d2:d3:e0", - "Name": "Vault CA Primary Cert", - "SerialNumber": 15998414315735550000, - "SigningKeyID": "fe:b9:d6:0b:c6:ce:2c:25:4f:d8:59:cb:11:ea:a5:42:5f:8e:41:4b", - "ExternalTrustDomain": "34a76791-b9b2-b93e-b0e4-1989ed11a28e", - "NotBefore": "2022-11-16T20:16:15Z", - "NotAfter": "2032-11-13T20:16:45Z", - "RootCert": "-----BEGIN CERTIFICATE-----\nMIICLDCCAdKgAwIBAgIUKQ9BPHF9mtC7yFPC3gXJDpLxCHIwCgYIKoZIzj0EAwIw\nLzEtMCsGA1UEAxMkcHJpLTEwOTJudTEudmF1bHQuY2EuMzRhNzY3OTEuY29uc3Vs\nMB4XDTIyMTExNjIwMTYxNVoXDTMyMTExMzIwMTY0NVowLzEtMCsGA1UEAxMkcHJp\nLTEwOTJudTEudmF1bHQuY2EuMzRhNzY3OTEuY29uc3VsMFkwEwYHKoZIzj0CAQYI\nKoZIzj0DAQcDQgAETnpGixC1kW8ep2JcGjRR2jbdESvjlEm9nSIWVAcilemUGFwi\nJ0YW0XUmJeEzRyfwLXnOw6voPzXRf1zXKjdTD6OByzCByDAOBgNVHQ8BAf8EBAMC\nAQYwDwYDVR0TAQH/BAUwAwEB/zAdBgNVHQ4EFgQUtb6EjDxyI+myIjDc+7KbiN8u\n8XowHwYDVR0jBBgwFoAUtb6EjDxyI+myIjDc+7KbiN8u8XowZQYDVR0RBF4wXIIk\ncHJpLTEwOTJudTEudmF1bHQuY2EuMzRhNzY3OTEuY29uc3VshjRzcGlmZmU6Ly8z\nNGE3Njc5MS1iOWIyLWI5M2UtYjBlNC0xOTg5ZWQxMWEyOGUuY29uc3VsMAoGCCqG\nSM49BAMCA0gAMEUCIHBezFSQAK5Nolf0rs3ErvlDcA8Z9esldh6gHupuGsNkAiEA\n9qL+P9PJAW4CrbTL0iF2yZUyJC2nwSSa2K0nYG8bXWQ=\n-----END CERTIFICATE-----\n", - "IntermediateCerts": [ - "-----BEGIN CERTIFICATE-----\nMIICLzCCAdSgAwIBAgIUbILCP3ODM4ScNBOm0jw59Fxju0swCgYIKoZIzj0EAwIw\nLzEtMCsGA1UEAxMkcHJpLTEwOTJudTEudmF1bHQuY2EuMzRhNzY3OTEuY29uc3Vs\nMB4XDTIyMTExNjIwMzIxNloXDTIyMTExNjIwNDc0NlowMDEuMCwGA1UEAxMlcHJp\nLTE4MThxNWlnLnZhdWx0LmNhLjM0YTc2NzkxLmNvbnN1bDBZMBMGByqGSM49AgEG\nCCqGSM49AwEHA0IABI30ikgrwTjbPaGgfNYkushvrEUUpxLzxMMEBlE82ilog1RW\nqwuEU29Qsa+N4SrfOf37xNv/Ey8SXPs5l2HmXJWjgcwwgckwDgYDVR0PAQH/BAQD\nAgEGMA8GA1UdEwEB/wQFMAMBAf8wHQYDVR0OBBYEFCZpC/BTdaggL2kj6Dfyk3+a\nNqBvMB8GA1UdIwQYMBaAFLW+hIw8ciPpsiIw3Puym4jfLvF6MGYGA1UdEQRfMF2C\nJXByaS0xODE4cTVpZy52YXVsdC5jYS4zNGE3Njc5MS5jb25zdWyGNHNwaWZmZTov\nLzM0YTc2NzkxLWI5YjItYjkzZS1iMGU0LTE5ODllZDExYTI4ZS5jb25zdWwwCgYI\nKoZIzj0EAwIDSQAwRgIhAJ8RHgR5qkyW2q866vGYJy+7BJ4zUXs3OJ76QLmxxU3K\nAiEA70S7wBEm1ZduTAk1ZfZPJEUGxvAXAcgy7EWeO/6MJ5o=\n-----END CERTIFICATE-----\n", - "-----BEGIN CERTIFICATE-----\nMIICLTCCAdKgAwIBAgIUU3qwESuhh4PgW3/tnHDn3qnBMrAwCgYIKoZIzj0EAwIw\nLzEtMCsGA1UEAxMkcHJpLTEwOTJudTEudmF1bHQuY2EuMzRhNzY3OTEuY29uc3Vs\nMB4XDTIyMTExNjIwNDAxNloXDTIyMTExNjIwNTU0NlowLzEtMCsGA1UEAxMkcHJp\nLTFkY2hkbGkudmF1bHQuY2EuMzRhNzY3OTEuY29uc3VsMFkwEwYHKoZIzj0CAQYI\nKoZIzj0DAQcDQgAEpj0BWPkcH82su9XGOo9rN5Zr5+Jyp68LiHy+qlIgH3L+OAir\nYgmXmJfuNwI8S2BB8cu0Gk3w5cTF7O0p/qAghaOByzCByDAOBgNVHQ8BAf8EBAMC\nAQYwDwYDVR0TAQH/BAUwAwEB/zAdBgNVHQ4EFgQU/rnWC8bOLCVP2FnLEeqlQl+O\nQUswHwYDVR0jBBgwFoAUtb6EjDxyI+myIjDc+7KbiN8u8XowZQYDVR0RBF4wXIIk\ncHJpLTFkY2hkbGkudmF1bHQuY2EuMzRhNzY3OTEuY29uc3VshjRzcGlmZmU6Ly8z\nNGE3Njc5MS1iOWIyLWI5M2UtYjBlNC0xOTg5ZWQxMWEyOGUuY29uc3VsMAoGCCqG\nSM49BAMCA0kAMEYCIQCtq4LiZzkiIKUES9MrzUEflg7wcwQf7Km+8RcOGQbz9QIh\nANWHWt1fe8Hl1wQ55qxsV5lSfOpGAox5WHpgnsBC7cwU\n-----END CERTIFICATE-----\n" - ], - "Active": true, - "PrivateKeyType": "ec", - "PrivateKeyBits": 256, - "CreateIndex": 11, - "ModifyIndex": 797 - } - ] -} - -# You can x509 decode the ICA certs to verify they have been updated and have correct expiry: -$ openssl x509 -in cert.crt -text -noout -Certificate: - Data: - Version: 3 (0x2) - Serial Number: - 53:7a:b0:11:2b:a1:87:83:e0:5b:7f:ed:9c:70:e7:de:a9:c1:32:b0 - Signature Algorithm: ecdsa-with-SHA256 - Issuer: CN=pri-1092nu1.vault.ca.34a76791.consul - Validity - Not Before: Nov 16 20:40:16 2022 GMT - Not After : Nov 16 20:55:46 2022 GMT - Subject: CN=pri-1dchdli.vault.ca.34a76791.consul - Subject Public Key Info: - Public Key Algorithm: id-ecPublicKey - Public-Key: (256 bit) - pub: - 04:a6:3d:01:58:f9:1c:1f:cd:ac:bb:d5:c6:3a:8f: - 6b:37:96:6b:e7:e2:72:a7:af:0b:88:7c:be:aa:52: - 20:1f:72:fe:38:08:ab:62:09:97:98:97:ee:37:02: - 3c:4b:60:41:f1:cb:b4:1a:4d:f0:e5:c4:c5:ec:ed: - 29:fe:a0:20:85 - ASN1 OID: prime256v1 - NIST CURVE: P-256 - X509v3 extensions: - X509v3 Key Usage: critical - Certificate Sign, CRL Sign - X509v3 Basic Constraints: critical - CA:TRUE - X509v3 Subject Key Identifier: - FE:B9:D6:0B:C6:CE:2C:25:4F:D8:59:CB:11:EA:A5:42:5F:8E:41:4B - X509v3 Authority Key Identifier: - keyid:B5:BE:84:8C:3C:72:23:E9:B2:22:30:DC:FB:B2:9B:88:DF:2E:F1:7A - - X509v3 Subject Alternative Name: - DNS:pri-1dchdli.vault.ca.34a76791.consul, URI:spiffe://34a76791-b9b2-b93e-b0e4-1989ed11a28e.consul - -``` - ---- - ## Helm Reference Docs The Helm reference docs (https://www.consul.io/docs/k8s/helm) are automatically diff --git a/acceptance/framework/consul/cli_cluster.go b/acceptance/framework/consul/cli_cluster.go index 0a3e688951..271f8f2eae 100644 --- a/acceptance/framework/consul/cli_cluster.go +++ b/acceptance/framework/consul/cli_cluster.go @@ -252,7 +252,7 @@ func (c *CLICluster) SetupConsulClient(t *testing.T, secure bool) (*api.Client, c.logger) // Retry creating the port forward since it can fail occasionally. - retry.RunWith(&retry.Counter{Wait: 3 * time.Second, Count: 60}, t, func(r *retry.R) { + retry.RunWith(&retry.Counter{Wait: 1 * time.Second, Count: 3}, t, func(r *retry.R) { // NOTE: It's okay to pass in `t` to ForwardPortE despite being in a retry // because we're using ForwardPortE (not ForwardPort) so the `t` won't // get used to fail the test, just for logging. diff --git a/acceptance/framework/consul/helm_cluster.go b/acceptance/framework/consul/helm_cluster.go index 3f4d31173d..eab1ba2904 100644 --- a/acceptance/framework/consul/helm_cluster.go +++ b/acceptance/framework/consul/helm_cluster.go @@ -142,11 +142,8 @@ func (h *HelmCluster) Destroy(t *testing.T) { h.helmOptions.ExtraArgs = map[string][]string{ "--wait": nil, } - - retry.RunWith(&retry.Counter{Wait: 1 * time.Second, Count: 15}, t, func(r *retry.R) { - err := helm.DeleteE(t, h.helmOptions, h.releaseName, false) - require.NoError(r, err) - }) + err := helm.DeleteE(t, h.helmOptions, h.releaseName, false) + require.NoError(t, err) // Retry because sometimes certain resources (like PVC) take time to delete // in cloud providers. @@ -327,25 +324,22 @@ func (h *HelmCluster) SetupConsulClient(t *testing.T, secure bool) (client *api. if h.ACLToken != "" { config.Token = h.ACLToken } else { - retry.RunWith(&retry.Counter{Wait: 1 * time.Second, Count: 600}, t, func(r *retry.R) { - // Get the ACL token. First, attempt to read it from the bootstrap token (this will be true in primary Consul servers). - // If the bootstrap token doesn't exist, it means we are running against a secondary cluster - // and will try to read the replication token from the federation secret. - // In secondary servers, we don't create a bootstrap token since ACLs are only bootstrapped in the primary. - // Instead, we provide a replication token that serves the role of the bootstrap token. - aclSecret, err := h.kubernetesClient.CoreV1().Secrets(namespace).Get(context.Background(), h.releaseName+"-consul-bootstrap-acl-token", metav1.GetOptions{}) - if err != nil && errors.IsNotFound(err) { - federationSecret := fmt.Sprintf("%s-consul-federation", h.releaseName) - aclSecret, err = h.kubernetesClient.CoreV1().Secrets(namespace).Get(context.Background(), federationSecret, metav1.GetOptions{}) - require.NoError(r, err) - config.Token = string(aclSecret.Data["replicationToken"]) - } else if err == nil { - config.Token = string(aclSecret.Data["token"]) - } else { - require.NoError(r, err) - } - }) - + // Get the ACL token. First, attempt to read it from the bootstrap token (this will be true in primary Consul servers). + // If the bootstrap token doesn't exist, it means we are running against a secondary cluster + // and will try to read the replication token from the federation secret. + // In secondary servers, we don't create a bootstrap token since ACLs are only bootstrapped in the primary. + // Instead, we provide a replication token that serves the role of the bootstrap token. + aclSecret, err := h.kubernetesClient.CoreV1().Secrets(namespace).Get(context.Background(), h.releaseName+"-consul-bootstrap-acl-token", metav1.GetOptions{}) + if err != nil && errors.IsNotFound(err) { + federationSecret := fmt.Sprintf("%s-consul-federation", h.releaseName) + aclSecret, err = h.kubernetesClient.CoreV1().Secrets(namespace).Get(context.Background(), federationSecret, metav1.GetOptions{}) + require.NoError(t, err) + config.Token = string(aclSecret.Data["replicationToken"]) + } else if err == nil { + config.Token = string(aclSecret.Data["token"]) + } else { + require.NoError(t, err) + } } } @@ -530,24 +524,21 @@ func defaultValues() map[string]string { } func CreateK8sSecret(t *testing.T, client kubernetes.Interface, cfg *config.TestConfig, namespace, secretName, secretKey, secret string) { - - retry.RunWith(&retry.Counter{Wait: 1 * time.Second, Count: 15}, t, func(r *retry.R) { - _, err := client.CoreV1().Secrets(namespace).Get(context.Background(), secretName, metav1.GetOptions{}) - if errors.IsNotFound(err) { - _, err := client.CoreV1().Secrets(namespace).Create(context.Background(), &corev1.Secret{ - ObjectMeta: metav1.ObjectMeta{ - Name: secretName, - }, - StringData: map[string]string{ - secretKey: secret, - }, - Type: corev1.SecretTypeOpaque, - }, metav1.CreateOptions{}) - require.NoError(r, err) - } else { - require.NoError(r, err) - } - }) + _, err := client.CoreV1().Secrets(namespace).Get(context.Background(), secretName, metav1.GetOptions{}) + if errors.IsNotFound(err) { + _, err := client.CoreV1().Secrets(namespace).Create(context.Background(), &corev1.Secret{ + ObjectMeta: metav1.ObjectMeta{ + Name: secretName, + }, + StringData: map[string]string{ + secretKey: secret, + }, + Type: corev1.SecretTypeOpaque, + }, metav1.CreateOptions{}) + require.NoError(t, err) + } else { + require.NoError(t, err) + } helpers.Cleanup(t, cfg.NoCleanupOnFailure, func() { _ = client.CoreV1().Secrets(namespace).Delete(context.Background(), secretName, metav1.DeleteOptions{}) diff --git a/acceptance/framework/helpers/helpers.go b/acceptance/framework/helpers/helpers.go index 5f99a682ae..2c1a6ebf47 100644 --- a/acceptance/framework/helpers/helpers.go +++ b/acceptance/framework/helpers/helpers.go @@ -35,7 +35,7 @@ func CheckForPriorInstallations(t *testing.T, client kubernetes.Interface, optio // Check if there's an existing cluster and fail if there is one. // We may need to retry since this is the first command run once the Kube // cluster is created and sometimes the API server returns errors. - retry.RunWith(&retry.Counter{Wait: 1 * time.Second, Count: 15}, t, func(r *retry.R) { + retry.RunWith(&retry.Counter{Wait: 1 * time.Second, Count: 3}, t, func(r *retry.R) { var err error // NOTE: It's okay to pass in `t` to RunHelmCommandAndGetOutputE despite being in a retry // because we're using RunHelmCommandAndGetOutputE (not RunHelmCommandAndGetOutput) so the `t` won't diff --git a/acceptance/framework/portforward/port_forward.go b/acceptance/framework/portforward/port_forward.go index 30f4aed157..97bf3f7856 100644 --- a/acceptance/framework/portforward/port_forward.go +++ b/acceptance/framework/portforward/port_forward.go @@ -24,7 +24,7 @@ func CreateTunnelToResourcePort(t *testing.T, resourceName string, remotePort in logger) // Retry creating the port forward since it can fail occasionally. - retry.RunWith(&retry.Counter{Wait: 3 * time.Second, Count: 60}, t, func(r *retry.R) { + retry.RunWith(&retry.Counter{Wait: 1 * time.Second, Count: 3}, t, func(r *retry.R) { // NOTE: It's okay to pass in `t` to ForwardPortE despite being in a retry // because we're using ForwardPortE (not ForwardPort) so the `t` won't // get used to fail the test, just for logging. diff --git a/acceptance/framework/vault/helpers.go b/acceptance/framework/vault/helpers.go index 2280aee8b2..4726e246ae 100644 --- a/acceptance/framework/vault/helpers.go +++ b/acceptance/framework/vault/helpers.go @@ -167,20 +167,6 @@ func (config *KV2Secret) SaveSecretAndAddReadPolicy(t *testing.T, vaultClient *v path "%s" { capabilities = ["read"] }`, config.Path) - config.saveSecretAndAddPolicy(t, vaultClient, policy) -} - -// SaveSecretAndAddUpdatePolicy will create an update policy for the PolicyName -// on the KV2Secret and then will save the secret in the KV2 store. -func (config *KV2Secret) SaveSecretAndAddUpdatePolicy(t *testing.T, vaultClient *vapi.Client) { - policy := fmt.Sprintf(` - path "%s" { - capabilities = ["read", "update"] - }`, config.Path) - config.saveSecretAndAddPolicy(t, vaultClient, policy) -} - -func (config *KV2Secret) saveSecretAndAddPolicy(t *testing.T, vaultClient *vapi.Client, policy string) { // Create the Vault Policy for the secret. logger.Log(t, "Creating policy") err := vaultClient.Sys().PutPolicy(config.PolicyName, policy) diff --git a/acceptance/go.mod b/acceptance/go.mod index 66fa6c4b44..ba375f0a6b 100644 --- a/acceptance/go.mod +++ b/acceptance/go.mod @@ -1,12 +1,12 @@ module github.com/hashicorp/consul-k8s/acceptance -go 1.20 +go 1.19 require ( github.com/gruntwork-io/terratest v0.31.2 github.com/hashicorp/consul-k8s/control-plane v0.0.0-20221117191905-0b1cc2b631e3 - github.com/hashicorp/consul/api v1.20.0 - github.com/hashicorp/consul/sdk v0.13.1 + github.com/hashicorp/consul/api v1.17.0 + github.com/hashicorp/consul/sdk v0.13.0 github.com/hashicorp/go-uuid v1.0.3 github.com/hashicorp/go-version v1.6.0 github.com/hashicorp/vault/api v1.2.0 @@ -83,11 +83,11 @@ require ( github.com/urfave/cli v1.22.2 // indirect go.uber.org/atomic v1.7.0 // indirect golang.org/x/crypto v0.0.0-20220411220226-7b82a4e95df4 // indirect - golang.org/x/net v0.0.0-20220127200216-cd36cc0744dd // indirect + golang.org/x/net v0.7.0 // indirect golang.org/x/oauth2 v0.0.0-20211104180415-d3ed0bb246c8 // indirect - golang.org/x/sys v0.0.0-20220728004956-3c1f35247d10 // indirect - golang.org/x/term v0.0.0-20220526004731-065cf7ba2467 // indirect - golang.org/x/text v0.3.7 // indirect + golang.org/x/sys v0.5.0 // indirect + golang.org/x/term v0.5.0 // indirect + golang.org/x/text v0.7.0 // indirect golang.org/x/time v0.0.0-20220210224613-90d013bbcef8 // indirect google.golang.org/appengine v1.6.7 // indirect google.golang.org/genproto v0.0.0-20210602131652-f16073e35f0c // indirect diff --git a/acceptance/go.sum b/acceptance/go.sum index 44969f22ae..a039e9037b 100644 --- a/acceptance/go.sum +++ b/acceptance/go.sum @@ -364,10 +364,10 @@ github.com/gruntwork-io/terratest v0.31.2 h1:xvYHA80MUq5kx670dM18HInewOrrQrAN+Xb github.com/gruntwork-io/terratest v0.31.2/go.mod h1:EEgJie28gX/4AD71IFqgMj6e99KP5mi81hEtzmDjxTo= github.com/hashicorp/consul-k8s/control-plane v0.0.0-20221117191905-0b1cc2b631e3 h1:4wROIZB8Y4cN/wPILChc2zQ/q00z1VyJitdgyLbITdU= github.com/hashicorp/consul-k8s/control-plane v0.0.0-20221117191905-0b1cc2b631e3/go.mod h1:j9Db/whkzvNC+KP2GftY0HxxleLm9swxXjlu3tYaOAw= -github.com/hashicorp/consul/api v1.20.0 h1:9IHTjNVSZ7MIwjlW3N3a7iGiykCMDpxZu8jsxFJh0yc= -github.com/hashicorp/consul/api v1.20.0/go.mod h1:nR64eD44KQ59Of/ECwt2vUmIK2DKsDzAwTmwmLl8Wpo= -github.com/hashicorp/consul/sdk v0.13.1 h1:EygWVWWMczTzXGpO93awkHFzfUka6hLYJ0qhETd+6lY= -github.com/hashicorp/consul/sdk v0.13.1/go.mod h1:SW/mM4LbKfqmMvcFu8v+eiQQ7oitXEFeiBe9StxERb0= +github.com/hashicorp/consul/api v1.17.0 h1:aqytbw31uCPNn37ST+717IyGod+P1eTgSGu3yjRo4bs= +github.com/hashicorp/consul/api v1.17.0/go.mod h1:ZNwemOPAdgtV4cCx9fqxNmw+PI3vliW6gYin2WD+F2g= +github.com/hashicorp/consul/sdk v0.13.0 h1:lce3nFlpv8humJL8rNrrGHYSKc3q+Kxfeg3Ii1m6ZWU= +github.com/hashicorp/consul/sdk v0.13.0/go.mod h1:0hs/l5fOVhJy/VdcoaNqUSi2AUs95eF5WKtv+EYIQqE= github.com/hashicorp/errwrap v1.0.0/go.mod h1:YH+1FKiLXxHSkmPseP+kNlulaMuP3n2brvKWEqk/Jc4= github.com/hashicorp/errwrap v1.1.0 h1:OxrOeh75EUXMY8TBjag2fzXGZ40LB6IKw45YeGUDY2I= github.com/hashicorp/errwrap v1.1.0/go.mod h1:YH+1FKiLXxHSkmPseP+kNlulaMuP3n2brvKWEqk/Jc4= @@ -417,6 +417,7 @@ github.com/hashicorp/go-uuid v1.0.3 h1:2gKiV6YVmrJ1i2CKKa9obLvRieoRGviZFL26PcT/C github.com/hashicorp/go-uuid v1.0.3/go.mod h1:6SBZvOh/SIDV7/2o3Jml5SYk/TvGqwFJ/bN7x4byOro= github.com/hashicorp/go-version v1.1.0/go.mod h1:fltr4n8CU8Ke44wwGCBoEymUuxUHl09ZGVZPK5anwXA= github.com/hashicorp/go-version v1.2.0/go.mod h1:fltr4n8CU8Ke44wwGCBoEymUuxUHl09ZGVZPK5anwXA= +github.com/hashicorp/go-version v1.2.1/go.mod h1:fltr4n8CU8Ke44wwGCBoEymUuxUHl09ZGVZPK5anwXA= github.com/hashicorp/go-version v1.6.0 h1:feTTfFNnjP967rlCxM/I9g701jU+RN74YKx2mOkIeek= github.com/hashicorp/go-version v1.6.0/go.mod h1:fltr4n8CU8Ke44wwGCBoEymUuxUHl09ZGVZPK5anwXA= github.com/hashicorp/golang-lru v0.5.0/go.mod h1:/m3WP610KZHVQ1SGc6re/UDhFvYD7pJ4Ao+sR/qLZy8= @@ -803,8 +804,9 @@ golang.org/x/net v0.0.0-20210405180319-a5a99cb37ef4/go.mod h1:p54w0d4576C0XHj96b golang.org/x/net v0.0.0-20210410081132-afb366fc7cd1/go.mod h1:9tjilg8BloeKEkVJvy7fQ90B1CfIiPueXVOjqfkSzI8= golang.org/x/net v0.0.0-20210428140749-89ef3d95e781/go.mod h1:OJAsFXCWl8Ukc7SiCT/9KSuxbyM7479/AVlXFRxuMCk= golang.org/x/net v0.0.0-20210520170846-37e1c6afe023/go.mod h1:9nx3DQGgdP8bBQD5qxJ1jj9UTztislL4KSBs9R2vV5Y= -golang.org/x/net v0.0.0-20220127200216-cd36cc0744dd h1:O7DYs+zxREGLKzKoMQrtrEacpb0ZVXA5rIwylE2Xchk= -golang.org/x/net v0.0.0-20220127200216-cd36cc0744dd/go.mod h1:CfG3xpIq0wQ8r1q4Su4UZFWDARRcnwPjda9FqA0JpMk= +golang.org/x/net v0.0.0-20211216030914-fe4d6282115f/go.mod h1:9nx3DQGgdP8bBQD5qxJ1jj9UTztislL4KSBs9R2vV5Y= +golang.org/x/net v0.7.0 h1:rJrUqqhjsgNp7KqAIc25s9pZnjU7TUcSY7HcVZjdn1g= +golang.org/x/net v0.7.0/go.mod h1:2Tu9+aMcznHK/AK1HMvgo6xiTLG5rD5rZLDS+rp2Bjs= golang.org/x/oauth2 v0.0.0-20180821212333-d2e6202438be/go.mod h1:N/0e6XlmueqKjAGxoOufVs8QHGRruUQn6yWY3a++T0U= golang.org/x/oauth2 v0.0.0-20190226205417-e64efc72b421/go.mod h1:gOpvHmFTYa4IltrdGE7lF6nIHvwfUNPOp7c8zoXwtLw= golang.org/x/oauth2 v0.0.0-20190604053449-0f29369cfe45/go.mod h1:gOpvHmFTYa4IltrdGE7lF6nIHvwfUNPOp7c8zoXwtLw= @@ -901,14 +903,16 @@ golang.org/x/sys v0.0.0-20210510120138-977fb7262007/go.mod h1:oPkhp1MJrh7nUepCBc golang.org/x/sys v0.0.0-20210616094352-59db8d763f22/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg= golang.org/x/sys v0.0.0-20210630005230-0f9fa26af87c/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg= golang.org/x/sys v0.0.0-20210927094055-39ccf1dd6fa6/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg= +golang.org/x/sys v0.0.0-20220412211240-33da011f77ad/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg= golang.org/x/sys v0.0.0-20220503163025-988cb79eb6c6/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg= -golang.org/x/sys v0.0.0-20220728004956-3c1f35247d10 h1:WIoqL4EROvwiPdUtaip4VcDdpZ4kha7wBWZrbVKCIZg= golang.org/x/sys v0.0.0-20220728004956-3c1f35247d10/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg= +golang.org/x/sys v0.5.0 h1:MUK/U/4lj1t1oPg0HfuXDN/Z1wv31ZJ/YcPiGccS4DU= +golang.org/x/sys v0.5.0/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg= golang.org/x/term v0.0.0-20201117132131-f5c789dd3221/go.mod h1:Nr5EML6q2oocZ2LXRh80K7BxOlk5/8JxuGnuhpl+muw= golang.org/x/term v0.0.0-20201126162022-7de9c90e9dd1/go.mod h1:bj7SfCRtBDWHUb9snDiAeCFNEtKQo2Wmx5Cou7ajbmo= golang.org/x/term v0.0.0-20210220032956-6a3ed077a48d/go.mod h1:bj7SfCRtBDWHUb9snDiAeCFNEtKQo2Wmx5Cou7ajbmo= -golang.org/x/term v0.0.0-20220526004731-065cf7ba2467 h1:CBpWXWQpIRjzmkkA+M7q9Fqnwd2mZr3AFqexg8YTfoM= -golang.org/x/term v0.0.0-20220526004731-065cf7ba2467/go.mod h1:jbD1KX2456YbFQfuXm/mYQcufACuNUgVhRMnK/tPxf8= +golang.org/x/term v0.5.0 h1:n2a8QNdAb0sZNpU9R1ALUXBbY+w51fCQDN+7EdxNBsY= +golang.org/x/term v0.5.0/go.mod h1:jMB1sMXY+tzblOD4FWmEbocvup2/aLOaQEp7JmGp78k= golang.org/x/text v0.0.0-20160726164857-2910a502d2bf/go.mod h1:NqM8EUOU14njkJ3fqMW+pc6Ldnwhi/IjpwHt7yyuwOQ= golang.org/x/text v0.0.0-20170915032832-14c0d48ead0c/go.mod h1:NqM8EUOU14njkJ3fqMW+pc6Ldnwhi/IjpwHt7yyuwOQ= golang.org/x/text v0.3.0/go.mod h1:NqM8EUOU14njkJ3fqMW+pc6Ldnwhi/IjpwHt7yyuwOQ= @@ -918,8 +922,8 @@ golang.org/x/text v0.3.3/go.mod h1:5Zoc/QRtKVWzQhOtBMvqHzDpF6irO9z98xDceosuGiQ= golang.org/x/text v0.3.4/go.mod h1:5Zoc/QRtKVWzQhOtBMvqHzDpF6irO9z98xDceosuGiQ= golang.org/x/text v0.3.5/go.mod h1:5Zoc/QRtKVWzQhOtBMvqHzDpF6irO9z98xDceosuGiQ= golang.org/x/text v0.3.6/go.mod h1:5Zoc/QRtKVWzQhOtBMvqHzDpF6irO9z98xDceosuGiQ= -golang.org/x/text v0.3.7 h1:olpwvP2KacW1ZWvsR7uQhoyTYvKAupfQrRGBFM352Gk= -golang.org/x/text v0.3.7/go.mod h1:u+2+/6zg+i71rQMx5EYifcz6MCKuco9NR6JIITiCfzQ= +golang.org/x/text v0.7.0 h1:4BRB4x83lYWy72KwLD/qYDuTu7q9PjSagHvijDw7cLo= +golang.org/x/text v0.7.0/go.mod h1:mrYo+phRRbMaCq/xk9113O4dZlRixOauAjOtrjsXDZ8= golang.org/x/time v0.0.0-20180412165947-fbb02b2291d2/go.mod h1:tRJNPiyCQ0inRvYxbN9jk5I+vvW/OXSQhTDSoE431IQ= golang.org/x/time v0.0.0-20181108054448-85acf8d2951c/go.mod h1:tRJNPiyCQ0inRvYxbN9jk5I+vvW/OXSQhTDSoE431IQ= golang.org/x/time v0.0.0-20190308202827-9d24e82272b4/go.mod h1:tRJNPiyCQ0inRvYxbN9jk5I+vvW/OXSQhTDSoE431IQ= diff --git a/acceptance/tests/cli/cli_install_test.go b/acceptance/tests/cli/cli_install_test.go index b6c52e9fc4..f8c40d3194 100644 --- a/acceptance/tests/cli/cli_install_test.go +++ b/acceptance/tests/cli/cli_install_test.go @@ -1,7 +1,6 @@ package cli import ( - "context" "fmt" "strings" "testing" @@ -13,7 +12,6 @@ import ( "github.com/hashicorp/consul-k8s/acceptance/framework/logger" "github.com/hashicorp/consul/sdk/testutil/retry" "github.com/stretchr/testify/require" - metav1 "k8s.io/apimachinery/pkg/apis/meta/v1" ) const ipv4RegEx = "(25[0-5]|2[0-4][0-9]|[01]?[0-9][0-9]?)\\.(25[0-5]|2[0-4][0-9]|[01]?[0-9][0-9]?)\\.(25[0-5]|2[0-4][0-9]|[01]?[0-9][0-9]?)\\.(25[0-5]|2[0-4][0-9]|[01]?[0-9][0-9]?)" @@ -23,11 +21,9 @@ const ipv4RegEx = "(25[0-5]|2[0-4][0-9]|[01]?[0-9][0-9]?)\\.(25[0-5]|2[0-4][0-9] func TestInstall(t *testing.T) { cases := map[string]struct { secure bool - tproxy bool }{ - "not-secure": {secure: false, tproxy: false}, - "secure": {secure: true, tproxy: false}, - "not-secure-tproxy": {secure: false, tproxy: true}, + "not-secure": {secure: false}, + "secure": {secure: true}, } for name, c := range cases { @@ -36,7 +32,6 @@ func TestInstall(t *testing.T) { require.NoError(t, err) cfg := suite.Config() - cfg.EnableTransparentProxy = c.tproxy ctx := suite.Environment().DefaultContext(t) connHelper := connhelper.ConnectHelper{ @@ -88,39 +83,6 @@ func TestInstall(t *testing.T) { } }) - // Troubleshoot: Get the client pod so we can portForward to it and get the 'troubleshoot upstreams' output - clientPod, err := connHelper.Ctx.KubernetesClient(t).CoreV1().Pods(connHelper.Ctx.KubectlOptions(t).Namespace).List(context.Background(), metav1.ListOptions{ - LabelSelector: "app=static-client", - }) - require.NoError(t, err) - - clientPodName := clientPod.Items[0].Name - upstreamsOut, err := cli.Run(t, ctx.KubectlOptions(t), "troubleshoot", "upstreams", "-pod", clientPodName) - logger.Log(t, string(upstreamsOut)) - require.NoError(t, err) - - if c.tproxy { - // If tproxy is enabled we are looking for the upstream ip which is the ClusterIP of the Kubernetes Service - serverService, err := connHelper.Ctx.KubernetesClient(t).CoreV1().Services(connHelper.Ctx.KubectlOptions(t).Namespace).List(context.Background(), metav1.ListOptions{ - FieldSelector: "metadata.name=static-server", - }) - require.NoError(t, err) - serverIP := serverService.Items[0].Spec.ClusterIP - - proxyOut, err := cli.Run(t, ctx.KubectlOptions(t), "troubleshoot", "proxy", "-pod", clientPodName, "-upstream-ip", serverIP) - require.NoError(t, err) - require.Regexp(t, "Upstream resources are valid", string(proxyOut)) - logger.Log(t, string(proxyOut)) - } else { - // With tproxy disabled and explicit upstreams we need the envoy-id of the server - require.Regexp(t, "static-server", string(upstreamsOut)) - - proxyOut, err := cli.Run(t, ctx.KubectlOptions(t), "troubleshoot", "proxy", "-pod", clientPodName, "-upstream-envoy-id", "static-server") - require.NoError(t, err) - require.Regexp(t, "Upstream resources are valid", string(proxyOut)) - logger.Log(t, string(proxyOut)) - } - connHelper.TestConnectionSuccess(t) connHelper.TestConnectionFailureWhenUnhealthy(t) }) diff --git a/acceptance/tests/fixtures/bases/crds-oss/proxydefaults.yaml b/acceptance/tests/fixtures/bases/crds-oss/proxydefaults.yaml index 6a90f29506..040da247f8 100644 --- a/acceptance/tests/fixtures/bases/crds-oss/proxydefaults.yaml +++ b/acceptance/tests/fixtures/bases/crds-oss/proxydefaults.yaml @@ -19,14 +19,3 @@ spec: - path: /health listenerPort: 22000 localPathPort: 8080 - envoyExtensions: - - name: builtin/aws/lambda - required: false - arguments: - payloadPassthrough: false - arn: arn:aws:lambda:us-west-2:111111111111:function:lambda-1234 - - name: builtin/aws/lambda - required: false - arguments: - payloadPassthrough: false - arn: arn:aws:lambda:us-east-1:111111111111:function:lambda-1234 diff --git a/acceptance/tests/fixtures/bases/crds-oss/servicedefaults.yaml b/acceptance/tests/fixtures/bases/crds-oss/servicedefaults.yaml index 413eb68d22..7b5f23eff5 100644 --- a/acceptance/tests/fixtures/bases/crds-oss/servicedefaults.yaml +++ b/acceptance/tests/fixtures/bases/crds-oss/servicedefaults.yaml @@ -24,16 +24,4 @@ spec: maxConnections: 5 passiveHealthCheck: interval: 10s - maxFailures: 2 - balanceInboundConnections: "exact_balance" - envoyExtensions: - - name: builtin/aws/lambda - required: false - arguments: - payloadPassthrough: false - arn: arn:aws:lambda:us-west-2:111111111111:function:lambda-1234 - - name: builtin/aws/lambda - required: false - arguments: - payloadPassthrough: false - arn: arn:aws:lambda:us-east-1:111111111111:function:lambda-1234 \ No newline at end of file + maxFailures: 2 \ No newline at end of file diff --git a/acceptance/tests/vault/vault_test.go b/acceptance/tests/vault/vault_test.go index 4d43d8bb5b..fdde364b5b 100644 --- a/acceptance/tests/vault/vault_test.go +++ b/acceptance/tests/vault/vault_test.go @@ -14,7 +14,6 @@ import ( "github.com/hashicorp/consul-k8s/acceptance/framework/logger" "github.com/hashicorp/consul-k8s/acceptance/framework/portforward" "github.com/hashicorp/consul-k8s/acceptance/framework/vault" - "github.com/hashicorp/consul/sdk/testutil/retry" "github.com/hashicorp/go-uuid" "github.com/hashicorp/go-version" "github.com/stretchr/testify/require" @@ -32,29 +31,6 @@ const ( // TestVault installs Vault, bootstraps it with secrets, policies, and Kube Auth Method. // It then configures Consul to use vault as the backend and checks that it works. func TestVault(t *testing.T) { - cases := map[string]struct { - autoBootstrap bool - }{ - "manual ACL bootstrap": {}, - "automatic ACL bootstrap": { - autoBootstrap: true, - }, - } - for name, c := range cases { - c := c - t.Run(name, func(t *testing.T) { - testVault(t, c.autoBootstrap) - }) - } -} - -// testVault is the implementation for TestVault: -// -// - testAutoBootstrap = false. Test when ACL bootstrapping has already occurred. -// The test pre-populates a Vault secret with the bootstrap token. -// - testAutoBootstrap = true. Test that server-acl-init automatically ACL bootstraps -// consul and writes the bootstrap token to Vault. -func testVault(t *testing.T, testAutoBootstrap bool) { cfg := suite.Config() ctx := suite.Environment().DefaultContext(t) kubectlOptions := ctx.KubectlOptions(t) @@ -108,6 +84,20 @@ func testVault(t *testing.T, testAutoBootstrap bool) { } serverPKIConfig.ConfigurePKIAndAuthRole(t, vaultClient) + // Configure controller webhook PKI + controllerWebhookPKIConfig := &vault.PKIAndAuthRoleConfiguration{ + BaseURL: "controller", + PolicyName: "controller-ca-policy", + RoleName: "controller-ca-role", + KubernetesNamespace: ns, + DataCenter: "dc1", + ServiceAccountName: fmt.Sprintf("%s-consul-%s", consulReleaseName, "controller"), + AllowedSubdomain: fmt.Sprintf("%s-consul-%s", consulReleaseName, "controller-webhook"), + MaxTTL: fmt.Sprintf("%ds", expirationInSeconds), + AuthMethodPath: KubernetesAuthMethodPath, + } + controllerWebhookPKIConfig.ConfigurePKIAndAuthRole(t, vaultClient) + // Configure connect injector webhook PKI connectInjectorWebhookPKIConfig := &vault.PKIAndAuthRoleConfiguration{ BaseURL: "connect", @@ -147,22 +137,16 @@ func testVault(t *testing.T, testAutoBootstrap bool) { licenseSecret.SaveSecretAndAddReadPolicy(t, vaultClient) } + // Bootstrap Token + bootstrapToken, err := uuid.GenerateUUID() + require.NoError(t, err) bootstrapTokenSecret := &vault.KV2Secret{ Path: "consul/data/secret/bootstrap", Key: "token", - Value: "", + Value: bootstrapToken, PolicyName: "bootstrap", } - if testAutoBootstrap { - bootstrapTokenSecret.SaveSecretAndAddUpdatePolicy(t, vaultClient) - } else { - id, err := uuid.GenerateUUID() - require.NoError(t, err) - bootstrapTokenSecret.Value = id - bootstrapTokenSecret.SaveSecretAndAddReadPolicy(t, vaultClient) - } - - bootstrapToken := bootstrapTokenSecret.Value + bootstrapTokenSecret.SaveSecretAndAddReadPolicy(t, vaultClient) // ------------------------- // Additional Auth Roles @@ -228,12 +212,15 @@ func testVault(t *testing.T, testAutoBootstrap bool) { "connectInject.replicas": "1", "global.secretsBackend.vault.connectInject.tlsCert.secretName": connectInjectorWebhookPKIConfig.CertPath, "global.secretsBackend.vault.connectInject.caCert.secretName": connectInjectorWebhookPKIConfig.CAPath, + "global.secretsBackend.vault.controller.tlsCert.secretName": controllerWebhookPKIConfig.CertPath, + "global.secretsBackend.vault.controller.caCert.secretName": controllerWebhookPKIConfig.CAPath, "global.secretsBackend.vault.enabled": "true", "global.secretsBackend.vault.consulServerRole": consulServerRole, "global.secretsBackend.vault.consulClientRole": consulClientRole, "global.secretsBackend.vault.consulCARole": serverPKIConfig.RoleName, "global.secretsBackend.vault.connectInjectRole": connectInjectorWebhookPKIConfig.RoleName, + "global.secretsBackend.vault.controllerRole": controllerWebhookPKIConfig.RoleName, "global.secretsBackend.vault.manageSystemACLsRole": manageSystemACLsRole, "global.secretsBackend.vault.ca.secretName": vaultCASecret, @@ -295,26 +282,6 @@ func testVault(t *testing.T, testAutoBootstrap bool) { logger.Logf(t, "Wait %d seconds for certificates to rotate....", expirationInSeconds) time.Sleep(time.Duration(expirationInSeconds) * time.Second) - if testAutoBootstrap { - logger.Logf(t, "Validating the ACL bootstrap token was stored in Vault.") - timer := &retry.Timer{Timeout: 10 * time.Second, Wait: 1 * time.Second} - retry.RunWith(timer, t, func(r *retry.R) { - secret, err := vaultClient.Logical().Read("consul/data/secret/bootstrap") - require.NoError(r, err) - - data, ok := secret.Data["data"].(map[string]interface{}) - require.True(r, ok) - require.NotNil(r, data) - - tok, ok := data["token"].(string) - require.True(r, ok) - require.NotEmpty(r, tok) - - // Set bootstrapToken for subsequent validations. - bootstrapToken = tok - }) - } - // Validate that the gossip encryption key is set correctly. logger.Log(t, "Validating the gossip key has been set correctly.") consulCluster.ACLToken = bootstrapToken diff --git a/charts/consul/Chart.yaml b/charts/consul/Chart.yaml index ffd7961302..e74655ef04 100644 --- a/charts/consul/Chart.yaml +++ b/charts/consul/Chart.yaml @@ -1,8 +1,8 @@ apiVersion: v2 name: consul -version: 1.2.0-dev -appVersion: 1.15.1 -kubeVersion: ">=1.22.0-0" +version: 1.0.6 +appVersion: 1.14.5 +kubeVersion: ">=1.21.0-0" description: Official HashiCorp Consul Chart home: https://www.consul.io icon: https://raw.githubusercontent.com/hashicorp/consul-k8s/main/assets/icon.png @@ -10,16 +10,16 @@ sources: - https://github.com/hashicorp/consul - https://github.com/hashicorp/consul-k8s annotations: - artifacthub.io/prerelease: true + artifacthub.io/prerelease: false artifacthub.io/images: | - name: consul - image: hashicorp/consul:1.15.1 + image: hashicorp/consul:1.14.5 - name: consul-k8s-control-plane - image: docker.mirror.hashicorp.services/hashicorppreview/consul-k8s-control-plane:1.2.0-dev + image: hashicorp/consul-k8s-control-plane:1.0.6 - name: consul-dataplane - image: hashicorp/consul-dataplane:1.1.0 + image: hashicorp/consul-dataplane:1.0.1 - name: envoy - image: envoyproxy/envoy:v1.25.1 + image: envoyproxy/envoy:v1.23.1 artifacthub.io/license: MPL-2.0 artifacthub.io/links: | - name: Documentation diff --git a/charts/consul/templates/_helpers.tpl b/charts/consul/templates/_helpers.tpl index 3552c8c209..e2f735e690 100644 --- a/charts/consul/templates/_helpers.tpl +++ b/charts/consul/templates/_helpers.tpl @@ -73,6 +73,22 @@ as well as the global.name setting. {{ "{{" }}- end -{{ "}}" }} {{- end -}} +{{- define "consul.controllerWebhookTLSCertTemplate" -}} + | + {{ "{{" }}- with secret "{{ .Values.global.secretsBackend.vault.controller.tlsCert.secretName }}" "{{- $name := include "consul.fullname" . -}}{{ printf "common_name=%s-controller-webhook" $name }}" + "alt_names={{ include "consul.controllerWebhookTLSAltNames" . }}" -{{ "}}" }} + {{ "{{" }}- .Data.certificate -{{ "}}" }} + {{ "{{" }}- end -{{ "}}" }} +{{- end -}} + +{{- define "consul.controllerWebhookTLSKeyTemplate" -}} + | + {{ "{{" }}- with secret "{{ .Values.global.secretsBackend.vault.controller.tlsCert.secretName }}" "{{- $name := include "consul.fullname" . -}}{{ printf "common_name=%s-controller-webhook" $name }}" + "alt_names={{ include "consul.controllerWebhookTLSAltNames" . }}" -{{ "}}" }} + {{ "{{" }}- .Data.private_key -{{ "}}" }} + {{ "{{" }}- end -{{ "}}" }} +{{- end -}} + {{- define "consul.serverTLSAltNames" -}} {{- $name := include "consul.fullname" . -}} {{- $ns := .Release.Namespace -}} @@ -93,6 +109,12 @@ as well as the global.name setting. {{ printf "%s-connect-injector,%s-connect-injector.%s,%s-connect-injector.%s.svc,%s-connect-injector.%s.svc.cluster.local" $name $name $ns $name $ns $name $ns}} {{- end -}} +{{- define "consul.controllerWebhookTLSAltNames" -}} +{{- $name := include "consul.fullname" . -}} +{{- $ns := .Release.Namespace -}} +{{ printf "%s-controller-webhook,%s-controller-webhook.%s,%s-controller-webhook.%s.svc,%s-controller-webhook.%s.svc.cluster.local" $name $name $ns $name $ns $name $ns}} +{{- end -}} + {{- define "consul.vaultReplicationTokenTemplate" -}} | {{ "{{" }}- with secret "{{ .Values.global.acls.replicationToken.secretName }}" -{{ "}}" }} @@ -263,17 +285,20 @@ Fails when at least one but not all of the following have been set: - global.secretsBackend.vault.connectInjectRole - global.secretsBackend.vault.connectInject.tlsCert.secretName - global.secretsBackend.vault.connectInject.caCert.secretName +- global.secretsBackend.vault.controllerRole +- global.secretsBackend.vault.controller.tlsCert.secretName +- global.secretsBackend.vault.controller.caCert.secretName The above values are needed in full to turn off web cert manager and allow -connect inject to manage its own webhook certs. +connect inject and controller to manage its own webhook certs. Usage: {{ template "consul.validateVaultWebhookCertConfiguration" . }} */}} {{- define "consul.validateVaultWebhookCertConfiguration" -}} -{{- if or .Values.global.secretsBackend.vault.connectInjectRole .Values.global.secretsBackend.vault.connectInject.tlsCert.secretName .Values.global.secretsBackend.vault.connectInject.caCert.secretName}} -{{- if or (not .Values.global.secretsBackend.vault.connectInjectRole) (not .Values.global.secretsBackend.vault.connectInject.tlsCert.secretName) (not .Values.global.secretsBackend.vault.connectInject.caCert.secretName) }} -{{fail "When one of the following has been set, all must be set: global.secretsBackend.vault.connectInjectRole, global.secretsBackend.vault.connectInject.tlsCert.secretName, global.secretsBackend.vault.connectInject.caCert.secretName"}} +{{- if or .Values.global.secretsBackend.vault.connectInjectRole .Values.global.secretsBackend.vault.connectInject.tlsCert.secretName .Values.global.secretsBackend.vault.connectInject.caCert.secretName .Values.global.secretsBackend.vault.controllerRole .Values.global.secretsBackend.vault.controller.tlsCert.secretName .Values.global.secretsBackend.vault.controller.caCert.secretName}} +{{- if or (not .Values.global.secretsBackend.vault.connectInjectRole) (not .Values.global.secretsBackend.vault.connectInject.tlsCert.secretName) (not .Values.global.secretsBackend.vault.connectInject.caCert.secretName) (not .Values.global.secretsBackend.vault.controllerRole) (not .Values.global.secretsBackend.vault.controller.tlsCert.secretName) (not .Values.global.secretsBackend.vault.controller.caCert.secretName) }} +{{fail "When one of the following has been set, all must be set: global.secretsBackend.vault.connectInjectRole, global.secretsBackend.vault.connectInject.tlsCert.secretName, global.secretsBackend.vault.connectInject.caCert.secretName, global.secretsBackend.vault.controllerRole, global.secretsBackend.vault.controller.tlsCert.secretName, and global.secretsBackend.vault.controller.caCert.secretName."}} {{ end }} {{ end }} {{- end -}} diff --git a/charts/consul/templates/api-gateway-controller-deployment.yaml b/charts/consul/templates/api-gateway-controller-deployment.yaml index 86517d7140..8c5c2fa73e 100644 --- a/charts/consul/templates/api-gateway-controller-deployment.yaml +++ b/charts/consul/templates/api-gateway-controller-deployment.yaml @@ -65,7 +65,14 @@ spec: {{- if or (not (and .Values.externalServers.enabled .Values.externalServers.useSystemRoots)) .Values.client.enabled }} {{- if .Values.global.tls.enabled }} - name: CONSUL_CACERT + {{- /* When Vault is being used as a secrets backend, auto-encrypt must be enabled. Since clients use a separate + root CA from servers when auto-encrypt is enabled, and our controller communicates with the agent when clients are + enabled, we only use the Vault server CA if clients are disabled and our controller will be communicating w/ the server. */}} + {{- if and (not .Values.client.enabled) .Values.global.secretsBackend.vault.enabled }} + value: /vault/secrets/serverca.crt + {{- else }} value: /consul/tls/ca/tls.crt + {{- end }} {{- end }} {{- end }} - name: HOST_IP @@ -156,7 +163,7 @@ spec: - name: consul-bin mountPath: /consul-bin {{- end }} - {{- if or (not (and .Values.externalServers.enabled .Values.externalServers.useSystemRoots)) .Values.client.enabled }} + {{- if or (not (or (and .Values.externalServers.enabled .Values.externalServers.useSystemRoots) .Values.global.secretsBackend.vault.enabled)) .Values.client.enabled }} {{- if .Values.global.tls.enabled }} {{- if and .Values.client.enabled .Values.global.tls.enableAutoEncrypt }} - name: consul-auto-encrypt-ca-cert @@ -186,7 +193,7 @@ spec: emptyDir: { } {{- end }} {{- if .Values.global.tls.enabled }} - {{- if not (and .Values.externalServers.enabled .Values.externalServers.useSystemRoots) }} + {{- if not (or (and .Values.externalServers.enabled .Values.externalServers.useSystemRoots) .Values.global.secretsBackend.vault.enabled) }} - name: consul-ca-cert secret: {{- if .Values.global.tls.caCert.secretName }} @@ -253,7 +260,7 @@ spec: - mountPath: /consul/login name: consul-data readOnly: false - {{- if not (and .Values.externalServers.enabled .Values.externalServers.useSystemRoots) }} + {{- if not (or (and .Values.externalServers.enabled .Values.externalServers.useSystemRoots) .Values.global.secretsBackend.vault.enabled) }} {{- if .Values.global.tls.enabled }} - name: consul-ca-cert mountPath: /consul/tls/ca diff --git a/charts/consul/templates/crd-proxydefaults.yaml b/charts/consul/templates/crd-proxydefaults.yaml index 749f2e4257..e66543637f 100644 --- a/charts/consul/templates/crd-proxydefaults.yaml +++ b/charts/consul/templates/crd-proxydefaults.yaml @@ -57,60 +57,12 @@ spec: spec: description: ProxyDefaultsSpec defines the desired state of ProxyDefaults. properties: - accessLogs: - description: AccessLogs controls all envoy instances' access logging - configuration. - properties: - disableListenerLogs: - description: DisableListenerLogs turns off just listener logs - for connections rejected by Envoy because they don't have a - matching listener filter. - type: boolean - enabled: - description: Enabled turns on all access logging - type: boolean - jsonFormat: - description: 'JSONFormat is a JSON-formatted string of an Envoy - access log format dictionary. See for more info on formatting: - https://www.envoyproxy.io/docs/envoy/latest/configuration/observability/access_log/usage#format-dictionaries - Defining JSONFormat and TextFormat is invalid.' - type: string - path: - description: Path is the output file to write logs for file-type - logging - type: string - textFormat: - description: 'TextFormat is a representation of Envoy access logs - format. See for more info on formatting: https://www.envoyproxy.io/docs/envoy/latest/configuration/observability/access_log/usage#format-strings - Defining JSONFormat and TextFormat is invalid.' - type: string - type: - description: Type selects the output for logs one of "file", "stderr". - "stdout" - type: string - type: object config: description: Config is an arbitrary map of configuration values used by Connect proxies. Any values that your proxy allows can be configured globally here. Supports JSON config values. See https://www.consul.io/docs/connect/proxies/envoy#configuration-formatting type: object x-kubernetes-preserve-unknown-fields: true - envoyExtensions: - description: EnvoyExtensions are a list of extensions to modify Envoy - proxy configuration. - items: - description: EnvoyExtension has configuration for an extension that - patches Envoy resources. - properties: - arguments: - type: object - x-kubernetes-preserve-unknown-fields: true - name: - type: string - required: - type: boolean - type: object - type: array expose: description: Expose controls the default expose path configuration for Envoy. diff --git a/charts/consul/templates/crd-servicedefaults.yaml b/charts/consul/templates/crd-servicedefaults.yaml index 5c6ecc7476..e0306333bd 100644 --- a/charts/consul/templates/crd-servicedefaults.yaml +++ b/charts/consul/templates/crd-servicedefaults.yaml @@ -57,12 +57,6 @@ spec: spec: description: ServiceDefaultsSpec defines the desired state of ServiceDefaults. properties: - balanceInboundConnections: - description: BalanceInboundConnections sets the strategy for allocating - inbound connections to the service across proxy threads. The only - supported value is exact_balance. By default, no connection balancing - is used. Refer to the Envoy Connection Balance config for details. - type: string destination: description: Destination is an address(es)/port combination that represents an endpoint outside the mesh. This is only valid when the mesh is @@ -82,22 +76,6 @@ spec: format: int32 type: integer type: object - envoyExtensions: - description: EnvoyExtensions are a list of extensions to modify Envoy - proxy configuration. - items: - description: EnvoyExtension has configuration for an extension that - patches Envoy resources. - properties: - arguments: - type: object - x-kubernetes-preserve-unknown-fields: true - name: - type: string - required: - type: boolean - type: object - type: array expose: description: Expose controls the default expose path configuration for Envoy. @@ -136,15 +114,15 @@ spec: with an external system. type: string localConnectTimeoutMs: - description: LocalConnectTimeoutMs is the number of milliseconds allowed - to make connections to the local application instance before timing - out. Defaults to 5000. + description: The number of milliseconds allowed to make connections + to the local application instance before timing out. Defaults to + 5000. type: integer localRequestTimeoutMs: - description: LocalRequestTimeoutMs is the timeout for HTTP requests - to the local application instance in milliseconds. Applies to HTTP-based - protocols only. If not specified, inherits the Envoy default for - route timeouts (15s). + description: In milliseconds, the timeout for HTTP requests to the + local application instance. Applies to HTTP-based protocols only. + If not specified, inherits the Envoy default for route timeouts + (15s). type: integer maxInboundConnections: description: MaxInboundConnections is the maximum number of concurrent @@ -258,15 +236,15 @@ spec: type: string type: object name: - description: Name is only accepted within service ServiceDefaultsSpec.UpstreamConfig.Overrides + description: Name is only accepted within a service-defaults config entry. type: string namespace: - description: Namespace is only accepted within service ServiceDefaultsSpec.UpstreamConfig.Overrides + description: Namespace is only accepted within a service-defaults config entry. type: string partition: - description: Partition is only accepted within service ServiceDefaultsSpec.UpstreamConfig.Overrides + description: Partition is only accepted within a service-defaults config entry. type: string passiveHealthCheck: @@ -291,10 +269,6 @@ spec: format: int32 type: integer type: object - peer: - description: Peer is only accepted within service ServiceDefaultsSpec.UpstreamConfig.Overrides - config entry. - type: string protocol: description: Protocol describes the upstream's service protocol. Valid values are "tcp", "http" and "grpc". Anything else @@ -361,15 +335,15 @@ spec: type: string type: object name: - description: Name is only accepted within service ServiceDefaultsSpec.UpstreamConfig.Overrides + description: Name is only accepted within a service-defaults config entry. type: string namespace: - description: Namespace is only accepted within service ServiceDefaultsSpec.UpstreamConfig.Overrides + description: Namespace is only accepted within a service-defaults config entry. type: string partition: - description: Partition is only accepted within service ServiceDefaultsSpec.UpstreamConfig.Overrides + description: Partition is only accepted within a service-defaults config entry. type: string passiveHealthCheck: @@ -377,6 +351,12 @@ spec: how upstream proxy instances will be monitored for removal from the load balancing pool. properties: + baseEjectionTime: + description: The base time that a host is ejected for. The + real time is equal to the base time multiplied by the number + of times the host has been ejected and is capped by + max_ejection_time (Default 300s). Defaults to 30s. + type: string enforcing_consecutive_5xx: description: EnforcingConsecutive5xx is the % chance that a host will be actually ejected when an outlier @@ -389,6 +369,12 @@ spec: sweeps. Each sweep may remove hosts or return hosts to the pool. type: string + maxEjectionPercent: + description: The maximum % of an upstream cluster that + can be ejected due to outlier detection. Defaults to + 10% but will eject at least one host regardless of the value. + format: int32 + type: integer maxFailures: description: MaxFailures is the count of consecutive failures that results in a host being removed from @@ -396,10 +382,6 @@ spec: format: int32 type: integer type: object - peer: - description: Peer is only accepted within service ServiceDefaultsSpec.UpstreamConfig.Overrides - config entry. - type: string protocol: description: Protocol describes the upstream's service protocol. Valid values are "tcp", "http" and "grpc". Anything else diff --git a/charts/consul/templates/server-acl-init-job.yaml b/charts/consul/templates/server-acl-init-job.yaml index e62db41ec2..440ab8bee0 100644 --- a/charts/consul/templates/server-acl-init-job.yaml +++ b/charts/consul/templates/server-acl-init-job.yaml @@ -47,23 +47,14 @@ spec: annotations: "consul.hashicorp.com/connect-inject": "false" {{- if .Values.global.secretsBackend.vault.enabled }} - - {{- /* Run the Vault agent as both an init container and sidecar. - The Vault agent sidecar is needed when server-acl-init bootstraps ACLs - and writes the bootstrap token back to Vault. - * agent-pre-populate: true - Run the Vault agent init container. - * agent-pre-populate-only: false - Also, run the Vault agent sidecar. - * agent-cache-enable: true - Enable the Agent cache listener. - * agent-cache-listener-port: 8200 - (optional) Listen on 127.0.0.1:8200. - * agent-enable-quit: true - Enable a "quit" endpoint. server-acl-init - tells the Vault agent to stop (without this the Job will not complete). - */}} - "vault.hashicorp.com/agent-pre-populate": "true" - "vault.hashicorp.com/agent-pre-populate-only": "false" - "vault.hashicorp.com/agent-cache-enable": "true" - "vault.hashicorp.com/agent-cache-listener-port": "8200" - "vault.hashicorp.com/agent-enable-quit": "true" + "vault.hashicorp.com/agent-pre-populate-only": "true" "vault.hashicorp.com/agent-inject": "true" + {{- if .Values.global.acls.bootstrapToken.secretName }} + {{- with .Values.global.acls.bootstrapToken }} + "vault.hashicorp.com/agent-inject-secret-bootstrap-token": "{{ .secretName }}" + "vault.hashicorp.com/agent-inject-template-bootstrap-token": {{ template "consul.vaultSecretTemplate" . }} + {{- end }} + {{- end }} {{- if .Values.global.acls.partitionToken.secretName }} {{- with .Values.global.acls.partitionToken }} "vault.hashicorp.com/agent-inject-secret-partition-token": "{{ .secretName }}" @@ -110,7 +101,14 @@ spec: path: tls.crt {{- end }} {{- end }} - {{- if and .Values.global.acls.replicationToken.secretName (not .Values.global.secretsBackend.vault.enabled) }} + {{- if (and .Values.global.acls.bootstrapToken.secretName (not .Values.global.secretsBackend.vault.enabled)) }} + - name: bootstrap-token + secret: + secretName: {{ .Values.global.acls.bootstrapToken.secretName }} + items: + - key: {{ .Values.global.acls.bootstrapToken.secretKey }} + path: bootstrap-token + {{- else if and .Values.global.acls.replicationToken.secretName (not .Values.global.secretsBackend.vault.enabled) }} - name: acl-replication-token secret: secretName: {{ .Values.global.acls.replicationToken.secretName }} @@ -131,13 +129,6 @@ spec: valueFrom: fieldRef: fieldPath: metadata.name - # Extract the Vault namespace from the Vault agent annotations. - {{- if .Values.global.secretsBackend.vault.enabled }} - {{- if .Values.global.secretsBackend.vault.agentAnnotations }} - - name: VAULT_NAMESPACE - value: {{ get (tpl .Values.global.secretsBackend.vault.agentAnnotations . | fromYaml) "vault.hashicorp.com/namespace" }} - {{- end }} - {{- end }} {{- include "consul.consulK8sConsulServerEnvVars" . | nindent 8 }} {{- if (or .Values.global.tls.enabled .Values.global.acls.replicationToken.secretName .Values.global.acls.bootstrapToken.secretName) }} volumeMounts: @@ -148,7 +139,11 @@ spec: readOnly: true {{- end }} {{- end }} - {{- if and .Values.global.acls.replicationToken.secretName (not .Values.global.secretsBackend.vault.enabled) }} + {{- if (and .Values.global.acls.bootstrapToken.secretName (not .Values.global.secretsBackend.vault.enabled)) }} + - name: bootstrap-token + mountPath: /consul/acl/tokens + readOnly: true + {{- else if and .Values.global.acls.replicationToken.secretName (not .Values.global.secretsBackend.vault.enabled) }} - name: acl-replication-token mountPath: /consul/acl/tokens readOnly: true @@ -166,15 +161,13 @@ spec: -resource-prefix=${CONSUL_FULLNAME} \ -k8s-namespace={{ .Release.Namespace }} \ -set-server-tokens={{ $serverEnabled }} \ + + {{- if .Values.global.acls.bootstrapToken.secretName }} {{- if .Values.global.secretsBackend.vault.enabled }} - -secrets-backend=vault \ + -bootstrap-token-file=/vault/secrets/bootstrap-token \ {{- else }} - -secrets-backend=kubernetes \ + -bootstrap-token-file=/consul/acl/tokens/bootstrap-token \ {{- end }} - - {{- if .Values.global.acls.bootstrapToken.secretName }} - -bootstrap-token-secret-name={{ .Values.global.acls.bootstrapToken.secretName }} \ - -bootstrap-token-secret-key={{ .Values.global.acls.bootstrapToken.secretKey }} \ {{- end }} {{- if .Values.syncCatalog.enabled }} diff --git a/charts/consul/templates/sync-catalog-deployment.yaml b/charts/consul/templates/sync-catalog-deployment.yaml index f2815d9627..ec1abbfc84 100644 --- a/charts/consul/templates/sync-catalog-deployment.yaml +++ b/charts/consul/templates/sync-catalog-deployment.yaml @@ -100,7 +100,7 @@ spec: fieldRef: fieldPath: metadata.namespace {{- if (and .Values.syncCatalog.aclSyncToken.secretName .Values.syncCatalog.aclSyncToken.secretKey) }} - - name: CONSUL_HTTP_TOKEN + - name: CONSUL_ACL_TOKEN valueFrom: secretKeyRef: name: {{ .Values.syncCatalog.aclSyncToken.secretName }} diff --git a/charts/consul/templates/webhook-cert-manager-clusterrole.yaml b/charts/consul/templates/webhook-cert-manager-clusterrole.yaml index e13e2dc741..c2a2422d02 100644 --- a/charts/consul/templates/webhook-cert-manager-clusterrole.yaml +++ b/charts/consul/templates/webhook-cert-manager-clusterrole.yaml @@ -1,4 +1,4 @@ -{{ $hasConfiguredWebhookCertsUsingVault := (and .Values.global.secretsBackend.vault.enabled .Values.global.secretsBackend.vault.connectInjectRole .Values.global.secretsBackend.vault.connectInject.tlsCert.secretName .Values.global.secretsBackend.vault.connectInject.caCert.secretName) -}} +{{ $hasConfiguredWebhookCertsUsingVault := (and .Values.global.secretsBackend.vault.enabled .Values.global.secretsBackend.vault.connectInjectRole .Values.global.secretsBackend.vault.connectInject.tlsCert.secretName .Values.global.secretsBackend.vault.connectInject.caCert.secretName .Values.global.secretsBackend.vault.controllerRole .Values.global.secretsBackend.vault.controller.tlsCert.secretName .Values.global.secretsBackend.vault.controller.caCert.secretName) -}} {{- if (and .Values.connectInject.enabled (not $hasConfiguredWebhookCertsUsingVault)) }} apiVersion: rbac.authorization.k8s.io/v1 kind: ClusterRole diff --git a/charts/consul/templates/webhook-cert-manager-clusterrolebinding.yaml b/charts/consul/templates/webhook-cert-manager-clusterrolebinding.yaml index 472ef4ee1d..ca2bb84bda 100644 --- a/charts/consul/templates/webhook-cert-manager-clusterrolebinding.yaml +++ b/charts/consul/templates/webhook-cert-manager-clusterrolebinding.yaml @@ -1,4 +1,4 @@ -{{ $hasConfiguredWebhookCertsUsingVault := (and .Values.global.secretsBackend.vault.enabled .Values.global.secretsBackend.vault.connectInjectRole .Values.global.secretsBackend.vault.connectInject.tlsCert.secretName .Values.global.secretsBackend.vault.connectInject.caCert.secretName) -}} +{{ $hasConfiguredWebhookCertsUsingVault := (and .Values.global.secretsBackend.vault.enabled .Values.global.secretsBackend.vault.connectInjectRole .Values.global.secretsBackend.vault.connectInject.tlsCert.secretName .Values.global.secretsBackend.vault.connectInject.caCert.secretName .Values.global.secretsBackend.vault.controllerRole .Values.global.secretsBackend.vault.controller.tlsCert.secretName .Values.global.secretsBackend.vault.controller.caCert.secretName) -}} {{- if (and .Values.connectInject.enabled (not $hasConfiguredWebhookCertsUsingVault)) }} apiVersion: rbac.authorization.k8s.io/v1 kind: ClusterRoleBinding diff --git a/charts/consul/templates/webhook-cert-manager-configmap.yaml b/charts/consul/templates/webhook-cert-manager-configmap.yaml index 293dd32d9f..914d2b87dd 100644 --- a/charts/consul/templates/webhook-cert-manager-configmap.yaml +++ b/charts/consul/templates/webhook-cert-manager-configmap.yaml @@ -1,4 +1,4 @@ -{{ $hasConfiguredWebhookCertsUsingVault := (and .Values.global.secretsBackend.vault.enabled .Values.global.secretsBackend.vault.connectInjectRole .Values.global.secretsBackend.vault.connectInject.tlsCert.secretName .Values.global.secretsBackend.vault.connectInject.caCert.secretName) -}} +{{ $hasConfiguredWebhookCertsUsingVault := (and .Values.global.secretsBackend.vault.enabled .Values.global.secretsBackend.vault.connectInjectRole .Values.global.secretsBackend.vault.connectInject.tlsCert.secretName .Values.global.secretsBackend.vault.connectInject.caCert.secretName .Values.global.secretsBackend.vault.controllerRole .Values.global.secretsBackend.vault.controller.tlsCert.secretName .Values.global.secretsBackend.vault.controller.caCert.secretName) -}} {{- if (and .Values.connectInject.enabled (not $hasConfiguredWebhookCertsUsingVault)) }} apiVersion: v1 kind: ConfigMap diff --git a/charts/consul/templates/webhook-cert-manager-deployment.yaml b/charts/consul/templates/webhook-cert-manager-deployment.yaml index dd93c039d2..a2913dd92b 100644 --- a/charts/consul/templates/webhook-cert-manager-deployment.yaml +++ b/charts/consul/templates/webhook-cert-manager-deployment.yaml @@ -1,4 +1,4 @@ -{{ $hasConfiguredWebhookCertsUsingVault := (and .Values.global.secretsBackend.vault.enabled .Values.global.secretsBackend.vault.connectInjectRole .Values.global.secretsBackend.vault.connectInject.tlsCert.secretName .Values.global.secretsBackend.vault.connectInject.caCert.secretName) -}} +{{ $hasConfiguredWebhookCertsUsingVault := (and .Values.global.secretsBackend.vault.enabled .Values.global.secretsBackend.vault.connectInjectRole .Values.global.secretsBackend.vault.connectInject.tlsCert.secretName .Values.global.secretsBackend.vault.connectInject.caCert.secretName .Values.global.secretsBackend.vault.controllerRole .Values.global.secretsBackend.vault.controller.tlsCert.secretName .Values.global.secretsBackend.vault.controller.caCert.secretName) -}} {{- if (and .Values.connectInject.enabled (not $hasConfiguredWebhookCertsUsingVault)) }} apiVersion: apps/v1 kind: Deployment diff --git a/charts/consul/templates/webhook-cert-manager-podsecuritypolicy.yaml b/charts/consul/templates/webhook-cert-manager-podsecuritypolicy.yaml index 4d685edc39..b67dbda510 100644 --- a/charts/consul/templates/webhook-cert-manager-podsecuritypolicy.yaml +++ b/charts/consul/templates/webhook-cert-manager-podsecuritypolicy.yaml @@ -1,4 +1,4 @@ -{{ $hasConfiguredWebhookCertsUsingVault := (and .Values.global.secretsBackend.vault.enabled .Values.global.secretsBackend.vault.connectInjectRole .Values.global.secretsBackend.vault.connectInject.tlsCert.secretName .Values.global.secretsBackend.vault.connectInject.caCert.secretName) -}} +{{ $hasConfiguredWebhookCertsUsingVault := (and .Values.global.secretsBackend.vault.enabled .Values.global.secretsBackend.vault.connectInjectRole .Values.global.secretsBackend.vault.connectInject.tlsCert.secretName .Values.global.secretsBackend.vault.connectInject.caCert.secretName .Values.global.secretsBackend.vault.controllerRole .Values.global.secretsBackend.vault.controller.tlsCert.secretName .Values.global.secretsBackend.vault.controller.caCert.secretName) -}} {{- if (and .Values.global.enablePodSecurityPolicies (or (and (ne (.Values.connectInject.enabled | toString) "-") .Values.connectInject.enabled) (and (eq (.Values.connectInject.enabled | toString) "-") .Values.global.enabled))) }} {{- if (and .Values.connectInject.enabled (not $hasConfiguredWebhookCertsUsingVault)) }} apiVersion: policy/v1beta1 diff --git a/charts/consul/templates/webhook-cert-manager-serviceaccount.yaml b/charts/consul/templates/webhook-cert-manager-serviceaccount.yaml index 68c54f3c27..fa4b24ef8b 100644 --- a/charts/consul/templates/webhook-cert-manager-serviceaccount.yaml +++ b/charts/consul/templates/webhook-cert-manager-serviceaccount.yaml @@ -1,4 +1,4 @@ -{{ $hasConfiguredWebhookCertsUsingVault := (and .Values.global.secretsBackend.vault.enabled .Values.global.secretsBackend.vault.connectInjectRole .Values.global.secretsBackend.vault.connectInject.tlsCert.secretName .Values.global.secretsBackend.vault.connectInject.caCert.secretName) -}} +{{ $hasConfiguredWebhookCertsUsingVault := (and .Values.global.secretsBackend.vault.enabled .Values.global.secretsBackend.vault.connectInjectRole .Values.global.secretsBackend.vault.connectInject.tlsCert.secretName .Values.global.secretsBackend.vault.connectInject.caCert.secretName .Values.global.secretsBackend.vault.controllerRole .Values.global.secretsBackend.vault.controller.tlsCert.secretName .Values.global.secretsBackend.vault.controller.caCert.secretName) -}} {{- if (and .Values.connectInject.enabled (not $hasConfiguredWebhookCertsUsingVault)) }} apiVersion: v1 kind: ServiceAccount diff --git a/charts/consul/test/unit/api-gateway-controller-deployment.bats b/charts/consul/test/unit/api-gateway-controller-deployment.bats index 880586ab43..327802af07 100755 --- a/charts/consul/test/unit/api-gateway-controller-deployment.bats +++ b/charts/consul/test/unit/api-gateway-controller-deployment.bats @@ -1522,6 +1522,23 @@ load _helpers [ "${actual}" = "true" ] } +@test "apiGateway/Deployment: CONSUL_CACERT has correct path with Vault as secrets backend and client disabled" { + cd `chart_dir` + local actual=$(helm template \ + -s templates/api-gateway-controller-deployment.yaml \ + --set 'apiGateway.enabled=true' \ + --set 'apiGateway.image=bar' \ + --set 'global.tls.enabled=true' \ + --set 'global.tls.caCert.secretName=foo' \ + --set 'server.enabled=true' \ + --set 'client.enabled=false' \ + --set 'global.secretsBackend.vault.enabled=true' \ + --set 'global.secretsBackend.vault.consulServerRole=foo' \ + . | tee /dev/stderr| + yq '.spec.template.spec.containers[0].env[0].value == "/vault/secrets/serverca.crt"' | tee /dev/stderr) + [ "${actual}" = "true" ] +} + @test "apiGateway/Deployment: CONSUL_CACERT is not set when using tls and useSystemRoots" { cd `chart_dir` local actual=$(helm template \ @@ -1555,6 +1572,21 @@ load _helpers [ "${actual}" = "" ] } +@test "apiGateway/Deployment: consul-ca-cert volume mount is not set when using Vault as a secrets backend" { + cd `chart_dir` + local actual=$(helm template \ + -s templates/api-gateway-controller-deployment.yaml \ + --set 'apiGateway.enabled=true' \ + --set 'apiGateway.image=bar' \ + --set 'global.acls.manageSystemACLs=true' \ + --set 'global.tls.enabled=true' \ + --set 'server.enabled=true' \ + --set 'global.secretsBackend.vault.enabled=true' \ + . | tee /dev/stderr | + yq '.spec.template.spec.containers[0].volumeMounts[] | select(.name == "consul-ca-cert")' | tee /dev/stderr) + [ "${actual}" = "" ] +} + @test "apiGateway/Deployment: consul-ca-cert volume mount is not set on acl-init when using externalServers and useSystemRoots" { cd `chart_dir` local actual=$(helm template \ @@ -1572,6 +1604,21 @@ load _helpers [ "${actual}" = "" ] } +@test "apiGateway/Deployment: consul-ca-cert volume mount is not set on acl-init when using Vault as secrets backend" { + cd `chart_dir` + local actual=$(helm template \ + -s templates/api-gateway-controller-deployment.yaml \ + --set 'apiGateway.enabled=true' \ + --set 'apiGateway.image=bar' \ + --set 'global.acls.manageSystemACLs=true' \ + --set 'global.tls.enabled=true' \ + --set 'server.enabled=true' \ + --set 'global.secretsBackend.vault.enabled=true' \ + . | tee /dev/stderr | + yq '.spec.template.spec.initContainers[1].volumeMounts[] | select(.name == "consul-ca-cert")' | tee /dev/stderr) + [ "${actual}" = "" ] +} + @test "apiGateway/Deployment: consul-auto-encrypt-ca-cert volume mount is set when tls.enabled, client.enabled, externalServers, useSystemRoots, and autoencrypt" { cd `chart_dir` local actual=$(helm template \ diff --git a/charts/consul/test/unit/connect-inject-clusterrole.bats b/charts/consul/test/unit/connect-inject-clusterrole.bats index 4acdf211d2..b1ad10a80c 100644 --- a/charts/consul/test/unit/connect-inject-clusterrole.bats +++ b/charts/consul/test/unit/connect-inject-clusterrole.bats @@ -193,6 +193,9 @@ load _helpers --set 'global.secretsBackend.vault.connectInjectRole=inject-ca-role' \ --set 'global.secretsBackend.vault.connectInject.tlsCert.secretName=pki/issue/connect-webhook-cert-dc1' \ --set 'global.secretsBackend.vault.connectInject.caCert.secretName=pki/issue/connect-webhook-cert-dc1' \ + --set 'global.secretsBackend.vault.controllerRole=test' \ + --set 'global.secretsBackend.vault.controller.caCert.secretName=foo/ca' \ + --set 'global.secretsBackend.vault.controller.tlsCert.secretName=foo/tls' \ --set 'global.secretsBackend.vault.consulClientRole=foo' \ --set 'global.secretsBackend.vault.consulServerRole=bar' \ --set 'global.secretsBackend.vault.consulCARole=test2' \ diff --git a/charts/consul/test/unit/connect-inject-deployment.bats b/charts/consul/test/unit/connect-inject-deployment.bats index 90166daca2..48036ad37b 100755 --- a/charts/consul/test/unit/connect-inject-deployment.bats +++ b/charts/consul/test/unit/connect-inject-deployment.bats @@ -1662,6 +1662,9 @@ load _helpers --set 'global.secretsBackend.vault.connectInjectRole=test' \ --set 'global.secretsBackend.vault.connectInject.caCert.secretName=foo/ca' \ --set 'global.secretsBackend.vault.connectInject.tlsCert.secretName=foo/tls' \ + --set 'global.secretsBackend.vault.controllerRole=test' \ + --set 'global.secretsBackend.vault.controller.caCert.secretName=foo/ca' \ + --set 'global.secretsBackend.vault.controller.tlsCert.secretName=foo/tls' \ . | tee /dev/stderr | yq '.spec.template.spec.containers[0].command | any(contains("-enable-webhook-ca-update"))' | tee /dev/stderr) [ "${actual}" = "true" ] @@ -1768,7 +1771,7 @@ load _helpers --set 'global.secretsBackend.vault.connectInjectRole=connectinjectcarole' \ --set 'global.secretsBackend.vault.agentAnnotations=foo: bar' . [ "$status" -eq 1 ] - [[ "$output" =~ "When one of the following has been set, all must be set: global.secretsBackend.vault.connectInjectRole, global.secretsBackend.vault.connectInject.tlsCert.secretName, global.secretsBackend.vault.connectInject.caCert.secretName" ]] + [[ "$output" =~ "When one of the following has been set, all must be set: global.secretsBackend.vault.connectInjectRole, global.secretsBackend.vault.connectInject.tlsCert.secretName, global.secretsBackend.vault.connectInject.caCert.secretName, global.secretsBackend.vault.controllerRole, global.secretsBackend.vault.controller.tlsCert.secretName, and global.secretsBackend.vault.controller.caCert.secretName." ]] } @test "connectInject/Deployment: fails if vault is enabled and global.secretsBackend.vault.connectInject.tlsCert.secretName is set but global.secretsBackend.vault.connectInjectRole and global.secretsBackend.vault.connectInject.caCert.secretName are not" { @@ -1785,7 +1788,7 @@ load _helpers --set 'global.secretsBackend.vault.connectInject.tlsCert.secretName=foo/tls' \ --set 'global.secretsBackend.vault.agentAnnotations=foo: bar' . [ "$status" -eq 1 ] - [[ "$output" =~ "When one of the following has been set, all must be set: global.secretsBackend.vault.connectInjectRole, global.secretsBackend.vault.connectInject.tlsCert.secretName, global.secretsBackend.vault.connectInject.caCert.secretName" ]] + [[ "$output" =~ "When one of the following has been set, all must be set: global.secretsBackend.vault.connectInjectRole, global.secretsBackend.vault.connectInject.tlsCert.secretName, global.secretsBackend.vault.connectInject.caCert.secretName, global.secretsBackend.vault.controllerRole, global.secretsBackend.vault.controller.tlsCert.secretName, and global.secretsBackend.vault.controller.caCert.secretName." ]] } @test "connectInject/Deployment: fails if vault is enabled and global.secretsBackend.vault.connectInject.caCert.secretName is set but global.secretsBackend.vault.connectInjectRole and global.secretsBackend.vault.connectInject.tlsCert.secretName are not" { @@ -1802,7 +1805,7 @@ load _helpers --set 'global.secretsBackend.vault.connectInject.caCert.secretName=foo/ca' \ --set 'global.secretsBackend.vault.agentAnnotations=foo: bar' . [ "$status" -eq 1 ] - [[ "$output" =~ "When one of the following has been set, all must be set: global.secretsBackend.vault.connectInjectRole, global.secretsBackend.vault.connectInject.tlsCert.secretName, global.secretsBackend.vault.connectInject.caCert.secretName" ]] + [[ "$output" =~ "When one of the following has been set, all must be set: global.secretsBackend.vault.connectInjectRole, global.secretsBackend.vault.connectInject.tlsCert.secretName, global.secretsBackend.vault.connectInject.caCert.secretName, global.secretsBackend.vault.controllerRole, global.secretsBackend.vault.controller.tlsCert.secretName, and global.secretsBackend.vault.controller.caCert.secretName." ]] } @test "connectInject/Deployment: vault tls annotations are set when tls is enabled" { @@ -1820,6 +1823,9 @@ load _helpers --set 'global.secretsBackend.vault.connectInjectRole=test' \ --set 'global.secretsBackend.vault.connectInject.caCert.secretName=foo/ca' \ --set 'global.secretsBackend.vault.connectInject.tlsCert.secretName=pki/issue/connect-webhook-cert-dc1' \ + --set 'global.secretsBackend.vault.controllerRole=test' \ + --set 'global.secretsBackend.vault.controller.caCert.secretName=foo/ca' \ + --set 'global.secretsBackend.vault.controller.tlsCert.secretName=foo/tls' \ . | tee /dev/stderr | yq -r '.spec.template.metadata' | tee /dev/stderr) @@ -1893,6 +1899,9 @@ load _helpers --set 'global.secretsBackend.vault.connectInjectRole=inject-ca-role' \ --set 'global.secretsBackend.vault.connectInject.tlsCert.secretName=pki/issue/connect-webhook-cert-dc1' \ --set 'global.secretsBackend.vault.connectInject.caCert.secretName=pki/issue/connect-webhook-cert-dc1' \ + --set 'global.secretsBackend.vault.controllerRole=test' \ + --set 'global.secretsBackend.vault.controller.caCert.secretName=foo/ca' \ + --set 'global.secretsBackend.vault.controller.tlsCert.secretName=foo/tls' \ --set 'global.secretsBackend.vault.consulClientRole=foo' \ --set 'global.secretsBackend.vault.consulServerRole=bar' \ --set 'global.secretsBackend.vault.consulCARole=test2' \ @@ -1915,6 +1924,9 @@ load _helpers --set 'global.secretsBackend.vault.connectInjectRole=inject-ca-role' \ --set 'global.secretsBackend.vault.connectInject.tlsCert.secretName=pki/issue/connect-webhook-cert-dc1' \ --set 'global.secretsBackend.vault.connectInject.caCert.secretName=pki/issue/connect-webhook-cert-dc1' \ + --set 'global.secretsBackend.vault.controllerRole=test' \ + --set 'global.secretsBackend.vault.controller.caCert.secretName=foo/ca' \ + --set 'global.secretsBackend.vault.controller.tlsCert.secretName=foo/tls' \ --set 'server.serverCert.secretName=pki_int/issue/test' \ --set 'global.tls.caCert.secretName=pki_int/cert/ca' \ . | tee /dev/stderr | @@ -1944,6 +1956,9 @@ load _helpers --set 'global.secretsBackend.vault.connectInjectRole=inject-ca-role' \ --set 'global.secretsBackend.vault.connectInject.tlsCert.secretName=pki/issue/connect-webhook-cert-dc1' \ --set 'global.secretsBackend.vault.connectInject.caCert.secretName=pki/issue/connect-webhook-cert-dc1' \ + --set 'global.secretsBackend.vault.controllerRole=test' \ + --set 'global.secretsBackend.vault.controller.caCert.secretName=foo/ca' \ + --set 'global.secretsBackend.vault.controller.tlsCert.secretName=foo/tls' \ . | tee /dev/stderr | yq '.spec.template.spec.volumes[] | select(.name == "certs")' | tee /dev/stderr) [ "${actual}" == "" ] @@ -1963,6 +1978,9 @@ load _helpers --set 'global.secretsBackend.vault.connectInjectRole=inject-ca-role' \ --set 'global.secretsBackend.vault.connectInject.tlsCert.secretName=pki/issue/connect-webhook-cert-dc1' \ --set 'global.secretsBackend.vault.connectInject.caCert.secretName=pki/issue/connect-webhook-cert-dc1' \ + --set 'global.secretsBackend.vault.controllerRole=test' \ + --set 'global.secretsBackend.vault.controller.caCert.secretName=foo/ca' \ + --set 'global.secretsBackend.vault.controller.tlsCert.secretName=foo/tls' \ . | tee /dev/stderr | yq '.spec.template.spec.containers[0].volumeMounts[] | select(.name == "certs")' | tee /dev/stderr) [ "${actual}" == "" ] diff --git a/charts/consul/test/unit/server-acl-init-job.bats b/charts/consul/test/unit/server-acl-init-job.bats index 81064c95eb..63450aa4c2 100644 --- a/charts/consul/test/unit/server-acl-init-job.bats +++ b/charts/consul/test/unit/server-acl-init-job.bats @@ -634,19 +634,7 @@ load _helpers yq -r '.spec.template' | tee /dev/stderr) # Check annotations - actual=$(echo $object | jq -r '.metadata.annotations["vault.hashicorp.com/agent-pre-populate"]' | tee /dev/stderr) - [ "${actual}" = "true" ] - actual=$(echo $object | jq -r '.metadata.annotations["vault.hashicorp.com/agent-pre-populate-only"]' | tee /dev/stderr) - [ "${actual}" = "false" ] - - actual=$(echo $object | jq -r '.metadata.annotations["vault.hashicorp.com/agent-cache-enable"]' | tee /dev/stderr) - [ "${actual}" = "true" ] - - actual=$(echo $object | jq -r '.metadata.annotations["vault.hashicorp.com/agent-cache-listener-port"]' | tee /dev/stderr) - [ "${actual}" = "8200" ] - - actual=$(echo $object | jq -r '.metadata.annotations["vault.hashicorp.com/agent-enable-quit"]' | tee /dev/stderr) [ "${actual}" = "true" ] local actual=$(echo $object | jq -r '.metadata.annotations["vault.hashicorp.com/agent-inject"]' | tee /dev/stderr) @@ -655,13 +643,15 @@ load _helpers local actual=$(echo $object | jq -r '.metadata.annotations["vault.hashicorp.com/role"]' | tee /dev/stderr) [ "${actual}" = "aclrole" ] - local actual=$(echo $object | jq -r '.spec.containers[] | select(.name=="server-acl-init-job").command | any(contains("-secrets-backend=vault"))') - [ "${actual}" = "true" ] + local actual=$(echo $object | jq -r '.metadata.annotations["vault.hashicorp.com/agent-inject-secret-bootstrap-token"]' | tee /dev/stderr) + [ "${actual}" = "foo" ] - local actual=$(echo $object | jq -r '.spec.containers[] | select(.name=="server-acl-init-job").command | any(contains("-bootstrap-token-secret-name=foo"))') - [ "${actual}" = "true" ] + local actual=$(echo $object | jq -r '.metadata.annotations["vault.hashicorp.com/agent-inject-template-bootstrap-token"]' | tee /dev/stderr) + local expected=$'{{- with secret \"foo\" -}}\n{{- .Data.data.bar -}}\n{{- end -}}' + [ "${actual}" = "${expected}" ] - local actual=$(echo $object | jq -r '.spec.containers[] | select(.name=="server-acl-init-job").command | any(contains("-bootstrap-token-secret-key=bar"))') + # Check that the bootstrap token flag is set to the path of the Vault secret. + local actual=$(echo $object | jq -r '.spec.containers[] | select(.name=="server-acl-init-job").command | any(contains("-bootstrap-token-file=/vault/secrets/bootstrap-token"))') [ "${actual}" = "true" ] # Check that no (secret) volumes are not attached @@ -692,31 +682,20 @@ load _helpers yq -r '.spec.template' | tee /dev/stderr) # Check annotations - local actual=$(echo $object | jq -r '.metadata.annotations["vault.hashicorp.com/agent-pre-populate"]' | tee /dev/stderr) - [ "${actual}" = "true" ] - - local actual=$(echo $object | jq -r '.metadata.annotations["vault.hashicorp.com/agent-pre-populate-only"]' | tee /dev/stderr) - [ "${actual}" = "false" ] - - local actual=$(echo $object | jq -r '.metadata.annotations["vault.hashicorp.com/agent-cache-enable"]' | tee /dev/stderr) - [ "${actual}" = "true" ] - - local actual=$(echo $object | jq -r '.metadata.annotations["vault.hashicorp.com/agent-cache-listener-port"]' | tee /dev/stderr) - [ "${actual}" = "8200" ] - - local actual=$(echo $object | jq -r '.metadata.annotations["vault.hashicorp.com/agent-enable-quit"]' | tee /dev/stderr) + local actual + actual=$(echo $object | jq -r '.metadata.annotations["vault.hashicorp.com/agent-pre-populate-only"]' | tee /dev/stderr) [ "${actual}" = "true" ] - - local actual=$(echo $object | jq -r '.metadata.annotations["vault.hashicorp.com/agent-inject"]' | tee /dev/stderr) + local actual + actual=$(echo $object | jq -r '.metadata.annotations["vault.hashicorp.com/agent-inject"]' | tee /dev/stderr) [ "${actual}" = "true" ] - - local actual=$(echo $object | jq -r '.metadata.annotations["vault.hashicorp.com/role"]' | tee /dev/stderr) + local actual + actual=$(echo $object | jq -r '.metadata.annotations["vault.hashicorp.com/role"]' | tee /dev/stderr) [ "${actual}" = "aclrole" ] - - local actual=$(echo $object | jq -r '.metadata.annotations["vault.hashicorp.com/agent-inject-secret-serverca.crt"]' | tee /dev/stderr) + local actual + actual=$(echo $object | jq -r '.metadata.annotations["vault.hashicorp.com/agent-inject-secret-serverca.crt"]' | tee /dev/stderr) [ "${actual}" = "foo" ] - - local actual=$(echo $object | jq -r '.metadata.annotations["vault.hashicorp.com/agent-inject-template-serverca.crt"]' | tee /dev/stderr) + local actual + actual=$(echo $object | jq -r '.metadata.annotations["vault.hashicorp.com/agent-inject-template-serverca.crt"]' | tee /dev/stderr) [ "${actual}" = $'{{- with secret \"foo\" -}}\n{{- .Data.certificate -}}\n{{- end -}}' ] # Check that the consul-ca-cert volume is not attached @@ -902,14 +881,12 @@ load _helpers local expected=$'{{- with secret \"/vault/replication\" -}}\n{{- .Data.data.token -}}\n{{- end -}}' [ "${actual}" = "${expected}" ] - local actual=$(echo $object | jq -r '.spec.containers[] | select(.name=="server-acl-init-job").command | any(contains("-secrets-backend=vault"))') - [ "${actual}" = "true" ] + local actual=$(echo $object | yq -r '.metadata.annotations."vault.hashicorp.com/agent-inject-secret-bootstrap-token"') + [ "${actual}" = "/vault/bootstrap" ] - local actual=$(echo $object | jq -r '.spec.containers[] | select(.name=="server-acl-init-job").command | any(contains("-bootstrap-token-secret-name=/vault/bootstrap"))') - [ "${actual}" = "true" ] - - local actual=$(echo $object | jq -r '.spec.containers[] | select(.name=="server-acl-init-job").command | any(contains("-bootstrap-token-secret-key=token"))') - [ "${actual}" = "true" ] + local actual=$(echo $object | yq -r '.metadata.annotations."vault.hashicorp.com/agent-inject-template-bootstrap-token"') + local expected=$'{{- with secret \"/vault/bootstrap\" -}}\n{{- .Data.data.token -}}\n{{- end -}}' + [ "${actual}" = "${expected}" ] # Check that replication token Kubernetes secret volumes and volumeMounts are not attached. local actual=$(echo $object | jq -r '.spec.volumes') @@ -918,9 +895,12 @@ load _helpers local actual=$(echo $object | jq -r '.spec.containers[] | select(.name=="server-acl-init-job").volumeMounts') [ "${actual}" = "null" ] - # Replication token file is passed. + # Check that the replication and bootstrap token flags are set to the path of the Vault secret. local actual=$(echo $object | jq -r '.spec.containers[] | select(.name=="server-acl-init-job").command | any(contains("-acl-replication-token-file=/vault/secrets/replication-token"))') [ "${actual}" = "true" ] + + local actual=$(echo $object | jq -r '.spec.containers[] | select(.name=="server-acl-init-job").command | any(contains("-bootstrap-token-file=/vault/secrets/bootstrap-token"))') + [ "${actual}" = "true" ] } #-------------------------------------------------------------------- @@ -973,7 +953,7 @@ load _helpers #-------------------------------------------------------------------- # Vault agent annotations -@test "serverACLInit/Job: default vault agent annotations" { +@test "serverACLInit/Job: no vault agent annotations defined by default" { cd `chart_dir` local actual=$(helm template \ -s templates/server-acl-init-job.yaml \ @@ -987,21 +967,8 @@ load _helpers --set 'global.secretsBackend.vault.consulCARole=carole' \ --set 'global.secretsBackend.vault.manageSystemACLsRole=aclrole' \ . | tee /dev/stderr | - yq -r .spec.template.metadata.annotations | tee /dev/stderr) - - local expected=$(echo '{ - "consul.hashicorp.com/connect-inject": "false", - "vault.hashicorp.com/agent-inject": "true", - "vault.hashicorp.com/agent-pre-populate": "true", - "vault.hashicorp.com/agent-pre-populate-only": "false", - "vault.hashicorp.com/agent-cache-enable": "true", - "vault.hashicorp.com/agent-cache-listener-port": "8200", - "vault.hashicorp.com/agent-enable-quit": "true", - "vault.hashicorp.com/role": "aclrole" - }' | tee /dev/stderr) - - local equal=$(jq -n --argjson a "$actual" --argjson b "$expected" '$a == $b') - [ "$equal" = "true" ] + yq -r '.spec.template.metadata.annotations | del(."consul.hashicorp.com/connect-inject") | del(."vault.hashicorp.com/agent-inject") | del(."vault.hashicorp.com/agent-pre-populate-only") | del(."vault.hashicorp.com/role") | del(."vault.hashicorp.com/agent-inject-secret-bootstrap-token") | del(."vault.hashicorp.com/agent-inject-template-bootstrap-token")' | tee /dev/stderr) + [ "${actual}" = "{}" ] } @test "serverACLInit/Job: vault agent annotations can be set" { @@ -1840,23 +1807,55 @@ load _helpers [[ "$output" =~ "both global.acls.bootstrapToken.secretKey and global.acls.bootstrapToken.secretName must be set if one of them is provided" ]] } -@test "serverACLInit/Job: bootstrap token secret is passed when acls.bootstrapToken.secretKey and secretName are set" { +@test "serverACLInit/Job: -bootstrap-token-file is not set by default" { + cd `chart_dir` + local object=$(helm template \ + -s templates/server-acl-init-job.yaml \ + --set 'global.acls.manageSystemACLs=true' \ + . | tee /dev/stderr) + + # Test the flag is not set. + local actual=$(echo "$object" | + yq '.spec.template.spec.containers[0].command | any(contains("-bootstrap-token-file"))' | tee /dev/stderr) + [ "${actual}" = "false" ] + + # Test the volume doesn't exist + local actual=$(echo "$object" | + yq '.spec.template.spec.volumes | length == 0' | tee /dev/stderr) + [ "${actual}" = "true" ] + + # Test the volume mount doesn't exist + local actual=$(echo "$object" | + yq '.spec.template.spec.containers[0].volumeMounts | length == 0' | tee /dev/stderr) + [ "${actual}" = "true" ] +} + +@test "serverACLInit/Job: -bootstrap-token-file is set when acls.bootstrapToken.secretKey and secretName are set" { cd `chart_dir` local object=$(helm template \ -s templates/server-acl-init-job.yaml \ --set 'global.acls.manageSystemACLs=true' \ --set 'global.acls.bootstrapToken.secretName=name' \ --set 'global.acls.bootstrapToken.secretKey=key' \ - . | yq .spec.template | tee /dev/stderr) + . | tee /dev/stderr) - local actual=$(echo "$object" | jq -r '.spec.containers[] | select(.name=="server-acl-init-job").command | any(contains("-bootstrap-token-secret-name=name"))') + # Test the -bootstrap-token-file flag is set. + local actual=$(echo "$object" | + yq '.spec.template.spec.containers[0].command | any(contains("-bootstrap-token-file=/consul/acl/tokens/bootstrap-token"))' | tee /dev/stderr) [ "${actual}" = "true" ] - local actual=$(echo "$object" | jq -r '.spec.containers[] | select(.name=="server-acl-init-job").command | any(contains("-bootstrap-token-secret-key=key"))') + # Test the volume exists + local actual=$(echo "$object" | + yq '.spec.template.spec.volumes | map(select(.name == "bootstrap-token")) | length == 1' | tee /dev/stderr) + [ "${actual}" = "true" ] + + # Test the volume mount exists + local actual=$(echo "$object" | + yq '.spec.template.spec.containers[0].volumeMounts | map(select(.name == "bootstrap-token")) | length == 1' | tee /dev/stderr) [ "${actual}" = "true" ] } -@test "serverACLInit/Job: bootstrap token secret is passed when both acl.bootstrapToken and acls.replicationToken are set" { +@test "serverACLInit/Job: -bootstrap-token-file is preferred when both acls.bootstrapToken and acls.replicationToken are set" { cd `chart_dir` local object=$(helm template \ -s templates/server-acl-init-job.yaml \ @@ -1865,12 +1864,21 @@ load _helpers --set 'global.acls.bootstrapToken.secretKey=key' \ --set 'global.acls.replicationToken.secretName=replication' \ --set 'global.acls.replicationToken.secretKey=token' \ - . | yq .spec.template | tee /dev/stderr) + . | tee /dev/stderr) - local actual=$(echo "$object" | jq -r '.spec.containers[] | select(.name=="server-acl-init-job").command | any(contains("-bootstrap-token-secret-name=name"))') + # Test the -bootstrap-token-file flag is set. + local actual=$(echo "$object" | + yq '.spec.template.spec.containers[0].command | any(contains("-bootstrap-token-file=/consul/acl/tokens/bootstrap-token"))' | tee /dev/stderr) [ "${actual}" = "true" ] - local actual=$(echo "$object" | jq -r '.spec.containers[] | select(.name=="server-acl-init-job").command | any(contains("-bootstrap-token-secret-key=key"))') + # Test the volume exists + local actual=$(echo "$object" | + yq '.spec.template.spec.volumes | map(select(.name == "bootstrap-token")) | length == 1' | tee /dev/stderr) + [ "${actual}" = "true" ] + + # Test the volume mount exists + local actual=$(echo "$object" | + yq '.spec.template.spec.containers[0].volumeMounts | map(select(.name == "bootstrap-token")) | length == 1' | tee /dev/stderr) [ "${actual}" = "true" ] } diff --git a/charts/consul/test/unit/sync-catalog-deployment.bats b/charts/consul/test/unit/sync-catalog-deployment.bats index ae1fe1a854..0b397a55d0 100755 --- a/charts/consul/test/unit/sync-catalog-deployment.bats +++ b/charts/consul/test/unit/sync-catalog-deployment.bats @@ -338,7 +338,7 @@ load _helpers --set 'syncCatalog.enabled=true' \ --set 'syncCatalog.aclSyncToken.secretKey=bar' \ . | tee /dev/stderr | - yq '[.spec.template.spec.containers[0].env[].name] | any(contains("CONSUL_HTTP_TOKEN"))' | tee /dev/stderr) + yq '[.spec.template.spec.containers[0].env[].name] | any(contains("CONSUL_ACL_TOKEN"))' | tee /dev/stderr) [ "${actual}" = "false" ] } @@ -349,7 +349,7 @@ load _helpers --set 'syncCatalog.enabled=true' \ --set 'syncCatalog.aclSyncToken.secretName=foo' \ . | tee /dev/stderr | - yq '[.spec.template.spec.containers[0].env[].name] | any(contains("CONSUL_HTTP_TOKEN"))' | tee /dev/stderr) + yq '[.spec.template.spec.containers[0].env[].name] | any(contains("CONSUL_ACL_TOKEN"))' | tee /dev/stderr) [ "${actual}" = "false" ] } @@ -361,7 +361,7 @@ load _helpers --set 'syncCatalog.aclSyncToken.secretName=foo' \ --set 'syncCatalog.aclSyncToken.secretKey=bar' \ . | tee /dev/stderr | - yq '[.spec.template.spec.containers[0].env[].name] | any(contains("CONSUL_HTTP_TOKEN"))' | tee /dev/stderr) + yq '[.spec.template.spec.containers[0].env[].name] | any(contains("CONSUL_ACL_TOKEN"))' | tee /dev/stderr) [ "${actual}" = "true" ] } diff --git a/charts/consul/test/unit/webhook-cert-manager-clusterrole.bats b/charts/consul/test/unit/webhook-cert-manager-clusterrole.bats index 4d1a4abdd2..d58ce20928 100644 --- a/charts/consul/test/unit/webhook-cert-manager-clusterrole.bats +++ b/charts/consul/test/unit/webhook-cert-manager-clusterrole.bats @@ -130,7 +130,7 @@ load _helpers #-------------------------------------------------------------------- # Vault -@test "webhookCertManager/ClusterRole: disabled when the following are configured - global.secretsBackend.vault.enabled, global.secretsBackend.vault.enabled, global.secretsBackend.vault.connectInjectRole, global.secretsBackend.vault.connectInject.tlsCert.secretName, and global.secretsBackend.vault.connectInject.caCert.secretName" { +@test "webhookCertManager/ClusterRole: disabled when the following are configured - global.secretsBackend.vault.enabled, global.secretsBackend.vault.enabled, global.secretsBackend.vault.connectInjectRole, global.secretsBackend.vault.connectInject.tlsCert.secretName, global.secretsBackend.vault.connectInject.caCert.secretName, global.secretsBackend.vault.controllerRole, global.secretsBackend.vault.controller.tlsCert.secretName, and .global.secretsBackend.vault.controller.caCert.secretName" { cd `chart_dir` assert_empty helm template \ -s templates/webhook-cert-manager-clusterrole.yaml \ @@ -142,6 +142,9 @@ load _helpers --set 'global.secretsBackend.vault.connectInjectRole=inject-ca-role' \ --set 'global.secretsBackend.vault.connectInject.tlsCert.secretName=pki/issue/connect-webhook-cert-dc1' \ --set 'global.secretsBackend.vault.connectInject.caCert.secretName=pki/issue/connect-webhook-cert-dc1' \ + --set 'global.secretsBackend.vault.controllerRole=test' \ + --set 'global.secretsBackend.vault.controller.caCert.secretName=foo/ca' \ + --set 'global.secretsBackend.vault.controller.tlsCert.secretName=foo/tls' \ --set 'global.secretsBackend.vault.consulClientRole=foo' \ --set 'global.secretsBackend.vault.consulServerRole=bar' \ --set 'global.secretsBackend.vault.consulCARole=test2' \ diff --git a/charts/consul/test/unit/webhook-cert-manager-clusterrolebinding.bats b/charts/consul/test/unit/webhook-cert-manager-clusterrolebinding.bats index 2e507d279d..89a60a0ef3 100644 --- a/charts/consul/test/unit/webhook-cert-manager-clusterrolebinding.bats +++ b/charts/consul/test/unit/webhook-cert-manager-clusterrolebinding.bats @@ -24,7 +24,7 @@ load _helpers #-------------------------------------------------------------------- # Vault -@test "webhookCertManager/ClusterRoleBinding: disabled when the following are configured - global.secretsBackend.vault.enabled, global.secretsBackend.vault.enabled, global.secretsBackend.vault.connectInjectRole, global.secretsBackend.vault.connectInject.tlsCert.secretName, and global.secretsBackend.vault.connectInject.caCert.secretName" { +@test "webhookCertManager/ClusterRoleBinding: disabled when the following are configured - global.secretsBackend.vault.enabled, global.secretsBackend.vault.enabled, global.secretsBackend.vault.connectInjectRole, global.secretsBackend.vault.connectInject.tlsCert.secretName, global.secretsBackend.vault.connectInject.caCert.secretName, global.secretsBackend.vault.controllerRole, global.secretsBackend.vault.controller.tlsCert.secretName, and .global.secretsBackend.vault.controller.caCert.secretName" { cd `chart_dir` assert_empty helm template \ -s templates/webhook-cert-manager-clusterrolebinding.yaml \ @@ -36,6 +36,9 @@ load _helpers --set 'global.secretsBackend.vault.connectInjectRole=inject-ca-role' \ --set 'global.secretsBackend.vault.connectInject.tlsCert.secretName=pki/issue/connect-webhook-cert-dc1' \ --set 'global.secretsBackend.vault.connectInject.caCert.secretName=pki/issue/connect-webhook-cert-dc1' \ + --set 'global.secretsBackend.vault.controllerRole=test' \ + --set 'global.secretsBackend.vault.controller.caCert.secretName=foo/ca' \ + --set 'global.secretsBackend.vault.controller.tlsCert.secretName=foo/tls' \ --set 'global.secretsBackend.vault.consulClientRole=foo' \ --set 'global.secretsBackend.vault.consulServerRole=bar' \ --set 'global.secretsBackend.vault.consulCARole=test2' \ diff --git a/charts/consul/test/unit/webhook-cert-manager-configmap.bats b/charts/consul/test/unit/webhook-cert-manager-configmap.bats index 196da220d4..774ada21d1 100644 --- a/charts/consul/test/unit/webhook-cert-manager-configmap.bats +++ b/charts/consul/test/unit/webhook-cert-manager-configmap.bats @@ -24,7 +24,7 @@ load _helpers #-------------------------------------------------------------------- # Vault -@test "webhookCertManager/Configmap: disabled when the following are configured - global.secretsBackend.vault.enabled, global.secretsBackend.vault.enabled, global.secretsBackend.vault.connectInjectRole, global.secretsBackend.vault.connectInject.tlsCert.secretName, and global.secretsBackend.vault.connectInject.caCert.secretName" { +@test "webhookCertManager/Configmap: disabled when the following are configured - global.secretsBackend.vault.enabled, global.secretsBackend.vault.enabled, global.secretsBackend.vault.connectInjectRole, global.secretsBackend.vault.connectInject.tlsCert.secretName, global.secretsBackend.vault.connectInject.caCert.secretName, global.secretsBackend.vault.controllerRole, global.secretsBackend.vault.controller.tlsCert.secretName, and .global.secretsBackend.vault.controller.caCert.secretName" { cd `chart_dir` assert_empty helm template \ -s templates/webhook-cert-manager-configmap.yaml \ @@ -36,6 +36,9 @@ load _helpers --set 'global.secretsBackend.vault.connectInjectRole=inject-ca-role' \ --set 'global.secretsBackend.vault.connectInject.tlsCert.secretName=pki/issue/connect-webhook-cert-dc1' \ --set 'global.secretsBackend.vault.connectInject.caCert.secretName=pki/issue/connect-webhook-cert-dc1' \ + --set 'global.secretsBackend.vault.controllerRole=test' \ + --set 'global.secretsBackend.vault.controller.caCert.secretName=foo/ca' \ + --set 'global.secretsBackend.vault.controller.tlsCert.secretName=foo/tls' \ --set 'global.secretsBackend.vault.consulClientRole=foo' \ --set 'global.secretsBackend.vault.consulServerRole=bar' \ --set 'global.secretsBackend.vault.consulCARole=test2' \ diff --git a/charts/consul/test/unit/webhook-cert-manager-deployment.bats b/charts/consul/test/unit/webhook-cert-manager-deployment.bats index 7d1a028d20..c0e54ccd25 100644 --- a/charts/consul/test/unit/webhook-cert-manager-deployment.bats +++ b/charts/consul/test/unit/webhook-cert-manager-deployment.bats @@ -66,7 +66,7 @@ load _helpers #-------------------------------------------------------------------- # Vault -@test "webhookCertManager/Deployment: disabled when the following are configured - global.secretsBackend.vault.enabled, global.secretsBackend.vault.enabled, global.secretsBackend.vault.connectInjectRole, global.secretsBackend.vault.connectInject.tlsCert.secretName, and global.secretsBackend.vault.connectInject.caCert.secretName" { +@test "webhookCertManager/Deployment: disabled when the following are configured - global.secretsBackend.vault.enabled, global.secretsBackend.vault.enabled, global.secretsBackend.vault.connectInjectRole, global.secretsBackend.vault.connectInject.tlsCert.secretName, global.secretsBackend.vault.connectInject.caCert.secretName, global.secretsBackend.vault.controllerRole, global.secretsBackend.vault.controller.tlsCert.secretName, and .global.secretsBackend.vault.controller.caCert.secretName" { cd `chart_dir` assert_empty helm template \ -s templates/webhook-cert-manager-deployment.yaml \ @@ -78,6 +78,9 @@ load _helpers --set 'global.secretsBackend.vault.connectInjectRole=inject-ca-role' \ --set 'global.secretsBackend.vault.connectInject.tlsCert.secretName=pki/issue/connect-webhook-cert-dc1' \ --set 'global.secretsBackend.vault.connectInject.caCert.secretName=pki/issue/connect-webhook-cert-dc1' \ + --set 'global.secretsBackend.vault.controllerRole=test' \ + --set 'global.secretsBackend.vault.controller.caCert.secretName=foo/ca' \ + --set 'global.secretsBackend.vault.controller.tlsCert.secretName=foo/tls' \ --set 'global.secretsBackend.vault.consulClientRole=foo' \ --set 'global.secretsBackend.vault.consulServerRole=bar' \ --set 'global.secretsBackend.vault.consulCARole=test2' \ diff --git a/charts/consul/test/unit/webhook-cert-manager-podsecuritypolicy.bats b/charts/consul/test/unit/webhook-cert-manager-podsecuritypolicy.bats index d8e16f867c..820be91404 100644 --- a/charts/consul/test/unit/webhook-cert-manager-podsecuritypolicy.bats +++ b/charts/consul/test/unit/webhook-cert-manager-podsecuritypolicy.bats @@ -35,7 +35,7 @@ load _helpers #-------------------------------------------------------------------- # Vault -@test "webhookCertManager/PodSecurityPolicy: disabled when the following are configured - global.secretsBackend.vault.enabled, global.secretsBackend.vault.enabled, global.secretsBackend.vault.connectInjectRole, global.secretsBackend.vault.connectInject.tlsCert.secretName, and global.secretsBackend.vault.connectInject.caCert.secretName" { +@test "webhookCertManager/PodSecurityPolicy: disabled when the following are configured - global.secretsBackend.vault.enabled, global.secretsBackend.vault.enabled, global.secretsBackend.vault.connectInjectRole, global.secretsBackend.vault.connectInject.tlsCert.secretName, global.secretsBackend.vault.connectInject.caCert.secretName, global.secretsBackend.vault.controllerRole, global.secretsBackend.vault.controller.tlsCert.secretName, and .global.secretsBackend.vault.controller.caCert.secretName" { cd `chart_dir` assert_empty helm template \ -s templates/webhook-cert-manager-podsecuritypolicy.yaml \ @@ -48,6 +48,9 @@ load _helpers --set 'global.secretsBackend.vault.connectInjectRole=inject-ca-role' \ --set 'global.secretsBackend.vault.connectInject.tlsCert.secretName=pki/issue/connect-webhook-cert-dc1' \ --set 'global.secretsBackend.vault.connectInject.caCert.secretName=pki/issue/connect-webhook-cert-dc1' \ + --set 'global.secretsBackend.vault.controllerRole=test' \ + --set 'global.secretsBackend.vault.controller.caCert.secretName=foo/ca' \ + --set 'global.secretsBackend.vault.controller.tlsCert.secretName=foo/tls' \ --set 'global.secretsBackend.vault.consulClientRole=foo' \ --set 'global.secretsBackend.vault.consulServerRole=bar' \ --set 'global.secretsBackend.vault.consulCARole=test2' \ diff --git a/charts/consul/test/unit/webhook-cert-manager-serviceaccount.bats b/charts/consul/test/unit/webhook-cert-manager-serviceaccount.bats index f420e7319c..766d20fb66 100644 --- a/charts/consul/test/unit/webhook-cert-manager-serviceaccount.bats +++ b/charts/consul/test/unit/webhook-cert-manager-serviceaccount.bats @@ -45,7 +45,7 @@ load _helpers #-------------------------------------------------------------------- # Vault -@test "webhookCertManager/ServiceAccount: disabled when the following are configured - global.secretsBackend.vault.enabled, global.secretsBackend.vault.connectInjectRole, global.secretsBackend.vault.connectInject.tlsCert.secretName, and global.secretsBackend.vault.connectInject.caCert.secretName" { +@test "webhookCertManager/ServiceAccount: disabled when the following are configured - global.secretsBackend.vault.enabled, global.secretsBackend.vault.connectInjectRole, global.secretsBackend.vault.connectInject.tlsCert.secretName, global.secretsBackend.vault.connectInject.caCert.secretName, global.secretsBackend.vault.controllerRole, global.secretsBackend.vault.controller.tlsCert.secretName, and .global.secretsBackend.vault.controller.caCert.secretName" { cd `chart_dir` assert_empty helm template \ -s templates/webhook-cert-manager-serviceaccount.yaml \ @@ -57,6 +57,9 @@ load _helpers --set 'global.secretsBackend.vault.connectInjectRole=inject-ca-role' \ --set 'global.secretsBackend.vault.connectInject.tlsCert.secretName=pki/issue/connect-webhook-cert-dc1' \ --set 'global.secretsBackend.vault.connectInject.caCert.secretName=pki/issue/connect-webhook-cert-dc1' \ + --set 'global.secretsBackend.vault.controllerRole=test' \ + --set 'global.secretsBackend.vault.controller.caCert.secretName=foo/ca' \ + --set 'global.secretsBackend.vault.controller.tlsCert.secretName=foo/tls' \ --set 'global.secretsBackend.vault.consulClientRole=foo' \ --set 'global.secretsBackend.vault.consulServerRole=bar' \ --set 'global.secretsBackend.vault.consulCARole=test2' \ diff --git a/charts/consul/values.yaml b/charts/consul/values.yaml index 3ccac77c22..a98c145d71 100644 --- a/charts/consul/values.yaml +++ b/charts/consul/values.yaml @@ -63,7 +63,7 @@ global: # image: "hashicorp/consul-enterprise:1.10.0-ent" # ``` # @default: hashicorp/consul: - image: "hashicorp/consul:1.15.1" + image: "hashicorp/consul:1.14.5" # Array of objects containing image pull secret names that will be applied to each service account. # This can be used to reference image pull secrets if using a custom consul or consul-k8s-control-plane Docker image. @@ -83,7 +83,7 @@ global: # image that is used for functionality such as catalog sync. # This can be overridden per component. # @default: hashicorp/consul-k8s-control-plane: - imageK8S: docker.mirror.hashicorp.services/hashicorppreview/consul-k8s-control-plane:1.2.0-dev + imageK8S: hashicorp/consul-k8s-control-plane:1.0.6 # The name of the datacenter that the agents should # register as. This can't be changed once the Consul cluster is up and running @@ -161,6 +161,12 @@ global: # and check the name of `metadata.name`. adminPartitionsRole: "" + # The Vault role to read Consul controller's webhook's + # CA and issue a certificate and private key. + # A Vault policy must be created which grants issue capabilities to + # `global.secretsBackend.vault.controller.tlsCert.secretName`. + controllerRole: "" + # The Vault role to read Consul connect-injector webhook's CA # and issue a certificate and private key. # A Vault policy must be created which grants issue capabilities to @@ -236,6 +242,25 @@ global: additionalConfig: | {} + controller: + # Configuration to the Vault Secret that Kubernetes will use on + # Kubernetes CRD creation, deletion, and update, to get TLS certificates + # used issued from vault to send webhooks to the controller. + tlsCert: + # The Vault secret path that issues TLS certificates for controller + # webhooks. + # @type: string + secretName: null + + # Configuration to the Vault Secret that Kubernetes will use on + # Kubernetes CRD creation, deletion, and update, to get CA certificates + # used issued from vault to send webhooks to the controller. + caCert: + # The Vault secret path that contains the CA certificate for controller + # webhooks. + # @type: string + secretName: null + connectInject: # Configuration to the Vault Secret that Kubernetes uses on # Kubernetes pod creation, deletion, and update, to get CA certificates @@ -392,20 +417,14 @@ global: # This requires Consul >= 1.4. manageSystemACLs: false - # A Kubernetes or Vault secret containing the bootstrap token to use for creating policies and - # tokens for all Consul and consul-k8s-control-plane components. If `secretName` and `secretKey` - # are unset, a default secret name and secret key are used. If the secret is populated, then - # we will skip ACL bootstrapping of the servers and will only initialize ACLs for the Consul - # clients and consul-k8s-control-plane system components. - # If the secret is empty, then we will bootstrap ACLs on the Consul servers, and write the - # bootstrap token to this secret. If ACLs are already bootstrapped on the servers, then the - # secret must contain the bootstrap token. + # A Kubernetes or Vault secret containing the bootstrap token to use for + # creating policies and tokens for all Consul and consul-k8s-control-plane components. + # If set, we will skip ACL bootstrapping of the servers and will only + # initialize ACLs for the Consul clients and consul-k8s-control-plane system components. bootstrapToken: # The name of the Kubernetes or Vault secret that holds the bootstrap token. - # If unset, this defaults to `{{ global.name }}-bootstrap-acl-token`. secretName: null # The key within the Kubernetes or Vault secret that holds the bootstrap token. - # If unset, this defaults to `token`. secretKey: null # If true, an ACL token will be created that can be used in secondary @@ -2565,7 +2584,8 @@ meshGateway: # for a specific gateway. # Requirements: consul >= 1.8.0 ingressGateways: - # Enable ingress gateway deployment. Requires `connectInject.enabled=true`. + # Enable ingress gateway deployment. Requires `connectInject.enabled=true` + # and `client.enabled=true`. enabled: false # Defaults sets default values for all gateway fields. With the exception @@ -2731,7 +2751,8 @@ ingressGateways: # for a specific gateway. # Requirements: consul >= 1.8.0 terminatingGateways: - # Enable terminating gateway deployment. Requires `connectInject.enabled=true`. + # Enable terminating gateway deployment. Requires `connectInject.enabled=true` + # and `client.enabled=true`. enabled: false # Defaults sets default values for all gateway fields. With the exception @@ -2878,7 +2899,7 @@ apiGateway: # The name (and tag) of the Envoy Docker image used for the # apiGateway. For other Consul compoenents, imageEnvoy has been replaced with Consul Dataplane. # @default: envoyproxy/envoy: - imageEnvoy: "envoyproxy/envoy:v1.25.1" + imageEnvoy: "envoyproxy/envoy:v1.23.1" # Override global log verbosity level for api-gateway-controller pods. One of "debug", "info", "warn", or "error". # @type: string @@ -2924,7 +2945,7 @@ apiGateway: # ```yaml # service: # annotations: | - # - external-dns.alpha.kubernetes.io/hostname + # - external-dns.alpha.kubernetes.io/hostname # ``` # # @type: string diff --git a/charts/go.mod b/charts/go.mod index f76282d756..cdb23e46b0 100644 --- a/charts/go.mod +++ b/charts/go.mod @@ -1,3 +1,3 @@ module github.com/hashicorp/consul-k8s/charts -go 1.20 +go 1.19 diff --git a/cli/cmd/install/install.go b/cli/cmd/install/install.go index cdfef4f670..7b5d5bb31c 100644 --- a/cli/cmd/install/install.go +++ b/cli/cmd/install/install.go @@ -589,7 +589,7 @@ func (c *Command) validateFlags(args []string) error { return fmt.Errorf("cannot set both -%s and -%s", flagNameConfigFile, flagNamePreset) } if ok := slices.Contains(preset.Presets, c.flagPreset); c.flagPreset != defaultPreset && !ok { - return fmt.Errorf("'%s' is not a valid preset (valid presets: %s)", c.flagPreset, strings.Join(preset.Presets, ", ")) + return fmt.Errorf("'%s' is not a valid preset", c.flagPreset) } if !common.IsValidLabel(c.flagNamespace) { return fmt.Errorf("'%s' is an invalid namespace. Namespaces follow the RFC 1123 label convention and must "+ diff --git a/cli/cmd/install/install_test.go b/cli/cmd/install/install_test.go index da77b740f8..04c250b1e4 100644 --- a/cli/cmd/install/install_test.go +++ b/cli/cmd/install/install_test.go @@ -162,45 +162,39 @@ func TestValidateFlags(t *testing.T) { testCases := []struct { description string input []string - expErr string }{ { "Should disallow non-flag arguments.", []string{"foo", "-auto-approve"}, - "should have no non-flag arguments", }, { "Should disallow specifying both values file AND presets.", []string{"-f='f.txt'", "-preset=demo"}, - "cannot set both -config-file and -preset", }, { "Should error on invalid presets.", []string{"-preset=foo"}, - "'foo' is not a valid preset (valid presets: cloud, quickstart, secure)", }, { "Should error on invalid timeout.", []string{"-timeout=invalid-timeout"}, - "unable to parse -timeout: time: invalid duration \"invalid-timeout\"", }, { "Should error on an invalid namespace. If this failed, TestValidLabel() probably did too.", []string{"-namespace=\" nsWithSpace\""}, - "'\" nsWithSpace\"' is an invalid namespace. Namespaces follow the RFC 1123 label convention and must consist of a lower case alphanumeric character or '-' and must start/end with an alphanumeric character", }, { - "Should have errored on a non-existent file.", + "Should have errored on a non-existant file.", []string{"-f=\"does_not_exist.txt\""}, - "file '\"does_not_exist.txt\"' does not exist", }, } for _, testCase := range testCases { c := getInitializedCommand(t, nil) t.Run(testCase.description, func(t *testing.T) { - err := c.validateFlags(testCase.input) - require.EqualError(t, err, testCase.expErr) + if err := c.validateFlags(testCase.input); err == nil { + t.Errorf("Test case should have failed.") + } }) } } @@ -564,7 +558,7 @@ func TestInstall(t *testing.T) { }, messages: []string{ "\n==> Checking if Consul can be installed\n ✓ No existing Consul installations found.\n ✓ No existing Consul persistent volume claims found\n ✓ No existing Consul secrets found.\n", - "\n==> Consul Installation Summary\n Name: consul\n Namespace: consul\n \n Helm value overrides\n --------------------\n connectInject:\n enabled: true\n metrics:\n defaultEnableMerging: true\n defaultEnabled: true\n enableGatewayMetrics: true\n global:\n metrics:\n enableAgentMetrics: true\n enabled: true\n name: consul\n prometheus:\n enabled: true\n server:\n replicas: 1\n ui:\n enabled: true\n service:\n enabled: true\n \n", + "\n==> Consul Installation Summary\n Name: consul\n Namespace: consul\n \n Helm value overrides\n --------------------\n connectInject:\n enabled: true\n metrics:\n defaultEnableMerging: true\n defaultEnabled: true\n enableGatewayMetrics: true\n controller:\n enabled: true\n global:\n metrics:\n enableAgentMetrics: true\n enabled: true\n name: consul\n prometheus:\n enabled: true\n server:\n replicas: 1\n ui:\n enabled: true\n service:\n enabled: true\n \n", "\n==> Installing Consul\n ✓ Downloaded charts.\n ✓ Consul installed in namespace \"consul\".\n", }, helmActionsRunner: &helm.MockActionRunner{}, @@ -580,7 +574,7 @@ func TestInstall(t *testing.T) { }, messages: []string{ "\n==> Checking if Consul can be installed\n ✓ No existing Consul installations found.\n ✓ No existing Consul persistent volume claims found\n ✓ No existing Consul secrets found.\n", - "\n==> Consul Installation Summary\n Name: consul\n Namespace: consul\n \n Helm value overrides\n --------------------\n connectInject:\n enabled: true\n global:\n acls:\n manageSystemACLs: true\n gossipEncryption:\n autoGenerate: true\n name: consul\n tls:\n enableAutoEncrypt: true\n enabled: true\n server:\n replicas: 1\n \n", + "\n==> Consul Installation Summary\n Name: consul\n Namespace: consul\n \n Helm value overrides\n --------------------\n connectInject:\n enabled: true\n controller:\n enabled: true\n global:\n acls:\n manageSystemACLs: true\n gossipEncryption:\n autoGenerate: true\n name: consul\n tls:\n enableAutoEncrypt: true\n enabled: true\n server:\n replicas: 1\n \n", "\n==> Installing Consul\n ✓ Downloaded charts.\n ✓ Consul installed in namespace \"consul\".\n", }, helmActionsRunner: &helm.MockActionRunner{}, diff --git a/cli/cmd/proxy/loglevel/command.go b/cli/cmd/proxy/loglevel/command.go deleted file mode 100644 index 4355997ed3..0000000000 --- a/cli/cmd/proxy/loglevel/command.go +++ /dev/null @@ -1,346 +0,0 @@ -package loglevel - -import ( - "context" - "errors" - "fmt" - "strings" - "sync" - - "github.com/posener/complete" - helmCLI "helm.sh/helm/v3/pkg/cli" - "k8s.io/apimachinery/pkg/api/validation" - metav1 "k8s.io/apimachinery/pkg/apis/meta/v1" - "k8s.io/client-go/kubernetes" - "k8s.io/client-go/rest" - - "github.com/hashicorp/consul-k8s/cli/common" - "github.com/hashicorp/consul-k8s/cli/common/envoy" - "github.com/hashicorp/consul-k8s/cli/common/flag" - "github.com/hashicorp/consul-k8s/cli/common/terminal" -) - -const ( - defaultAdminPort = 19000 - flagNameNamespace = "namespace" - flagNameUpdateLevel = "update-level" - flagNameReset = "reset" - flagNameKubeConfig = "kubeconfig" - flagNameKubeContext = "context" -) - -var ErrIncorrectArgFormat = errors.New("Exactly one positional argument is required: ") - -type LoggerConfig map[string]string - -var levelToColor = map[string]string{ - "trace": terminal.Green, - "debug": terminal.HiWhite, - "info": terminal.Blue, - "warning": terminal.Yellow, - "error": terminal.Red, - "critical": terminal.Magenta, - "off": "", -} - -type LogLevelCommand struct { - *common.BaseCommand - - kubernetes kubernetes.Interface - set *flag.Sets - - // Command Flags - podName string - namespace string - level string - reset bool - kubeConfig string - kubeContext string - - once sync.Once - help string - restConfig *rest.Config - envoyLoggingCaller func(context.Context, common.PortForwarder, *envoy.LoggerParams) (map[string]string, error) -} - -func (l *LogLevelCommand) init() { - l.Log.ResetNamed("loglevel") - l.set = flag.NewSets() - f := l.set.NewSet("Command Options") - f.StringVar(&flag.StringVar{ - Name: flagNameNamespace, - Target: &l.namespace, - Usage: "The namespace where the target Pod can be found.", - Aliases: []string{"n"}, - }) - - f.StringVar(&flag.StringVar{ - Name: flagNameUpdateLevel, - Target: &l.level, - Usage: "Update the level for the logger. Can be either `-update-level warning` to change all loggers to warning, or a comma delineated list of loggers with level can be passed like `-update-level grpc:warning,http:info` to only modify specific loggers.", - Aliases: []string{"u"}, - }) - - f.BoolVar(&flag.BoolVar{ - Name: flagNameReset, - Target: &l.reset, - Usage: "Reset the log level for all loggers in a pod to the Envoy default (info).", - Aliases: []string{"r"}, - }) - - f = l.set.NewSet("Global Options") - f.StringVar(&flag.StringVar{ - Name: flagNameKubeConfig, - Aliases: []string{"c"}, - Target: &l.kubeConfig, - Usage: "Set the path to kubeconfig file.", - }) - f.StringVar(&flag.StringVar{ - Name: flagNameKubeContext, - Target: &l.kubeContext, - Usage: "Set the Kubernetes context to use.", - }) - - l.help = l.set.Help() -} - -func (l *LogLevelCommand) Run(args []string) int { - l.once.Do(l.init) - defer common.CloseWithError(l.BaseCommand) - - err := l.parseFlags(args) - if err != nil { - return l.logOutputAndDie(err) - } - err = l.validateFlags() - if err != nil { - return l.logOutputAndDie(err) - } - - // if we're resetting the default log level for envoy is info: https://www.envoyproxy.io/docs/envoy/latest/start/quick-start/run-envoy#debugging-envoy - if l.reset { - l.level = "info" - } - - if l.envoyLoggingCaller == nil { - l.envoyLoggingCaller = envoy.CallLoggingEndpoint - } - - err = l.initKubernetes() - if err != nil { - return l.logOutputAndDie(err) - } - - adminPorts, err := l.fetchAdminPorts() - if err != nil { - return l.logOutputAndDie(err) - } - - err = l.fetchOrSetLogLevels(adminPorts) - if err != nil { - return l.logOutputAndDie(err) - } - - return 0 -} - -func (l *LogLevelCommand) parseFlags(args []string) error { - if len(args) == 0 { - return ErrIncorrectArgFormat - } - - positional := []string{} - // Separate positional args from keyed args - for _, arg := range args { - if strings.HasPrefix(arg, "-") { - break - } - positional = append(positional, arg) - } - keyed := args[len(positional):] - - if len(positional) != 1 { - return ErrIncorrectArgFormat - } - - l.podName = positional[0] - - err := l.set.Parse(keyed) - if err != nil { - return err - } - - return nil -} - -func (l *LogLevelCommand) validateFlags() error { - if l.level != "" && l.reset { - return fmt.Errorf("cannot set log level to %q and reset to 'info' at the same time", l.level) - } - if l.namespace == "" { - return nil - } - - errs := validation.ValidateNamespaceName(l.namespace, false) - if len(errs) > 0 { - return fmt.Errorf("invalid namespace name passed for -namespace/-n: %v", strings.Join(errs, "; ")) - } - - return nil -} - -func (l *LogLevelCommand) initKubernetes() error { - settings := helmCLI.New() - var err error - - if l.kubeConfig != "" { - settings.KubeConfig = l.kubeConfig - } - - if l.kubeContext != "" { - settings.KubeContext = l.kubeContext - } - - if l.restConfig == nil { - l.restConfig, err = settings.RESTClientGetter().ToRESTConfig() - if err != nil { - return fmt.Errorf("error creating Kubernetes REST config %v", err) - } - - } - - if l.kubernetes == nil { - l.kubernetes, err = kubernetes.NewForConfig(l.restConfig) - if err != nil { - return fmt.Errorf("error creating Kubernetes client %v", err) - } - } - if l.namespace == "" { - l.namespace = settings.Namespace() - } - - return nil -} - -// fetchAdminPorts retrieves all admin ports for Envoy Proxies running in a pod given namespace. -func (l *LogLevelCommand) fetchAdminPorts() (map[string]int, error) { - adminPorts := make(map[string]int, 0) - pod, err := l.kubernetes.CoreV1().Pods(l.namespace).Get(l.Ctx, l.podName, metav1.GetOptions{}) - if err != nil { - return adminPorts, err - } - - connectService, isMultiport := pod.Annotations["consul.hashicorp.com/connect-service"] - - if !isMultiport { - // Return the default port configuration. - adminPorts[l.podName] = defaultAdminPort - return adminPorts, nil - } - - for idx, svc := range strings.Split(connectService, ",") { - adminPorts[svc] = defaultAdminPort + idx - } - - return adminPorts, nil -} - -func (l *LogLevelCommand) fetchOrSetLogLevels(adminPorts map[string]int) error { - loggers := make(map[string]LoggerConfig, 0) - - for name, port := range adminPorts { - pf := common.PortForward{ - Namespace: l.namespace, - PodName: l.podName, - RemotePort: port, - KubeClient: l.kubernetes, - RestConfig: l.restConfig, - } - params, err := parseParams(l.level) - if err != nil { - return err - } - logLevels, err := l.envoyLoggingCaller(l.Ctx, &pf, params) - if err != nil { - return err - } - loggers[name] = logLevels - } - - l.outputLevels(loggers) - return nil -} - -func parseParams(params string) (*envoy.LoggerParams, error) { - loggerParams := envoy.NewLoggerParams() - if len(params) == 0 { - return loggerParams, nil - } - - // contains global log level change - if !strings.Contains(params, ":") { - err := loggerParams.SetGlobalLoggerLevel(params) - if err != nil { - return nil, err - } - return loggerParams, nil - } - - // contains changes to at least 1 specific log level - loggerChanges := strings.Split(params, ",") - - for _, logger := range loggerChanges { - levelValues := strings.Split(logger, ":") - err := loggerParams.SetLoggerLevel(levelValues[0], levelValues[1]) - if err != nil { - return nil, err - } - } - return loggerParams, nil -} - -func (l *LogLevelCommand) outputLevels(logLevels map[string]LoggerConfig) { - l.UI.Output(fmt.Sprintf("Envoy log configuration for %s in namespace default:", l.podName)) - for n, levels := range logLevels { - l.UI.Output(fmt.Sprintf("Log Levels for %s", n), terminal.WithHeaderStyle()) - table := terminal.NewTable("Name", "Level") - for name, level := range levels { - table.AddRow([]string{name, level}, []string{"", levelToColor[level]}) - } - l.UI.Table(table) - l.UI.Output("") - } -} - -func (l *LogLevelCommand) Help() string { - l.once.Do(l.init) - return fmt.Sprintf("%s\n\nUsage: consul-k8s proxy log [flags]\n\n%s", l.Synopsis(), l.help) -} - -func (l *LogLevelCommand) Synopsis() string { - return "Inspect and Modify the Envoy Log configuration for a given Pod." -} - -// AutocompleteFlags returns a mapping of supported flags and autocomplete -// options for this command. The map key for the Flags map should be the -// complete flag such as "-foo" or "--foo". -func (l *LogLevelCommand) AutocompleteFlags() complete.Flags { - return complete.Flags{ - fmt.Sprintf("-%s", flagNameNamespace): complete.PredictNothing, - fmt.Sprintf("-%s", flagNameKubeConfig): complete.PredictFiles("*"), - fmt.Sprintf("-%s", flagNameKubeContext): complete.PredictNothing, - } -} - -// AutocompleteArgs returns the argument predictor for this command. -// Since argument completion is not supported, this will return -// complete.PredictNothing. -func (l *LogLevelCommand) AutocompleteArgs() complete.Predictor { - return complete.PredictNothing -} - -func (l *LogLevelCommand) logOutputAndDie(err error) int { - l.UI.Output(err.Error(), terminal.WithErrorStyle()) - l.UI.Output(fmt.Sprintf("\n%s", l.Help())) - return 1 -} diff --git a/cli/cmd/proxy/loglevel/command_test.go b/cli/cmd/proxy/loglevel/command_test.go deleted file mode 100644 index 1c5387fd5f..0000000000 --- a/cli/cmd/proxy/loglevel/command_test.go +++ /dev/null @@ -1,293 +0,0 @@ -package loglevel - -import ( - "bytes" - "context" - "fmt" - "io" - "os" - "regexp" - "testing" - - "github.com/stretchr/testify/require" - v1 "k8s.io/api/core/v1" - metav1 "k8s.io/apimachinery/pkg/apis/meta/v1" - "k8s.io/client-go/kubernetes/fake" - - "github.com/hashicorp/consul-k8s/cli/common" - "github.com/hashicorp/consul-k8s/cli/common/envoy" - "github.com/hashicorp/consul-k8s/cli/common/terminal" - "github.com/hashicorp/go-hclog" -) - -func TestFlagParsingFails(t *testing.T) { - t.Parallel() - testCases := map[string]struct { - args []string - out int - }{ - "No args": { - args: []string{}, - out: 1, - }, - "Multiple podnames passed": { - args: []string{"podname", "podname2"}, - out: 1, - }, - "Nonexistent flag passed, -foo bar": { - args: []string{"podName", "-foo", "bar"}, - out: 1, - }, - "Invalid argument passed, -namespace YOLO": { - args: []string{"podName", "-namespace", "YOLO"}, - out: 1, - }, - } - podName := "now-this-is-pod-racing" - fakePod := v1.Pod{ - ObjectMeta: metav1.ObjectMeta{ - Name: podName, - Namespace: "default", - }, - } - - for name, tc := range testCases { - t.Run(name, func(t *testing.T) { - c := setupCommand(bytes.NewBuffer([]byte{})) - c.kubernetes = fake.NewSimpleClientset(&v1.PodList{Items: []v1.Pod{fakePod}}) - c.envoyLoggingCaller = func(context.Context, common.PortForwarder, *envoy.LoggerParams) (map[string]string, error) { - return testLogConfig, nil - } - - out := c.Run(tc.args) - require.Equal(t, tc.out, out) - }) - } -} - -func TestFlagParsingSucceeds(t *testing.T) { - t.Parallel() - podName := "now-this-is-pod-racing" - testCases := map[string]struct { - args []string - podNamespace string - out int - }{ - "With single pod name": { - args: []string{podName}, - podNamespace: "default", - out: 0, - }, - "With single pod name and namespace": { - args: []string{podName, "-n", "another"}, - podNamespace: "another", - out: 0, - }, - "With single pod name and blanket level": { - args: []string{podName, "-u", "warning"}, - podNamespace: "default", - out: 0, - }, - "With single pod name and single level": { - args: []string{podName, "-u", "grpc:warning"}, - podNamespace: "default", - out: 0, - }, - "With single pod name and multiple levels": { - args: []string{podName, "-u", "grpc:warning,http:info"}, - podNamespace: "default", - out: 0, - }, - "With single pod name and blanket level full flag": { - args: []string{podName, "-update-level", "warning"}, - podNamespace: "default", - out: 0, - }, - "With single pod name and single level full flag": { - args: []string{podName, "-update-level", "grpc:warning"}, - podNamespace: "default", - out: 0, - }, - "With single pod name and multiple levels full flag": { - args: []string{podName, "-update-level", "grpc:warning,http:info"}, - podNamespace: "default", - out: 0, - }, - } - - for name, tc := range testCases { - t.Run(name, func(t *testing.T) { - fakePod := v1.Pod{ - ObjectMeta: metav1.ObjectMeta{ - Name: podName, - Namespace: tc.podNamespace, - }, - } - - c := setupCommand(bytes.NewBuffer([]byte{})) - c.kubernetes = fake.NewSimpleClientset(&v1.PodList{Items: []v1.Pod{fakePod}}) - c.envoyLoggingCaller = func(context.Context, common.PortForwarder, *envoy.LoggerParams) (map[string]string, error) { - return testLogConfig, nil - } - - out := c.Run(tc.args) - require.Equal(t, tc.out, out) - }) - } -} - -func TestOutputForGettingLogLevels(t *testing.T) { - t.Parallel() - podName := "now-this-is-pod-racing" - expectedHeader := fmt.Sprintf("Envoy log configuration for %s in namespace default:", podName) - fakePod := v1.Pod{ - ObjectMeta: metav1.ObjectMeta{ - Name: podName, - Namespace: "default", - }, - } - - buf := bytes.NewBuffer([]byte{}) - c := setupCommand(buf) - newLogLevel := "warning" - config := make(map[string]string, len(testLogConfig)) - for logger := range testLogConfig { - config[logger] = newLogLevel - } - - c.envoyLoggingCaller = func(context.Context, common.PortForwarder, *envoy.LoggerParams) (map[string]string, error) { - return config, nil - } - c.kubernetes = fake.NewSimpleClientset(&v1.PodList{Items: []v1.Pod{fakePod}}) - - args := []string{podName, "-u", newLogLevel} - out := c.Run(args) - require.Equal(t, 0, out) - - actual := buf.String() - - require.Regexp(t, expectedHeader, actual) - require.Regexp(t, "Log Levels for now-this-is-pod-racing", actual) - for logger, level := range config { - require.Regexp(t, regexp.MustCompile(logger+`.*`+level), actual) - } -} - -func TestOutputForSettingLogLevels(t *testing.T) { - t.Parallel() - podName := "now-this-is-pod-racing" - expectedHeader := fmt.Sprintf("Envoy log configuration for %s in namespace default:", podName) - fakePod := v1.Pod{ - ObjectMeta: metav1.ObjectMeta{ - Name: podName, - Namespace: "default", - }, - } - - buf := bytes.NewBuffer([]byte{}) - c := setupCommand(buf) - c.envoyLoggingCaller = func(context.Context, common.PortForwarder, *envoy.LoggerParams) (map[string]string, error) { - return testLogConfig, nil - } - c.kubernetes = fake.NewSimpleClientset(&v1.PodList{Items: []v1.Pod{fakePod}}) - - args := []string{podName, "-u", "warning"} - out := c.Run(args) - require.Equal(t, 0, out) - - actual := buf.String() - - require.Regexp(t, expectedHeader, actual) - require.Regexp(t, "Log Levels for now-this-is-pod-racing", actual) - for logger, level := range testLogConfig { - require.Regexp(t, regexp.MustCompile(logger+`.*`+level), actual) - } -} - -func TestHelp(t *testing.T) { - t.Parallel() - buf := bytes.NewBuffer([]byte{}) - c := setupCommand(buf) - expectedSynposis := "Inspect and Modify the Envoy Log configuration for a given Pod." - expectedUsage := `Usage: consul-k8s proxy log \[flags\]` - actual := c.Help() - require.Regexp(t, expectedSynposis, actual) - require.Regexp(t, expectedUsage, actual) -} - -func setupCommand(buf io.Writer) *LogLevelCommand { - log := hclog.New(&hclog.LoggerOptions{ - Name: "test", - Level: hclog.Debug, - Output: os.Stdout, - }) - - command := &LogLevelCommand{ - BaseCommand: &common.BaseCommand{ - Log: log, - UI: terminal.NewUI(context.Background(), buf), - }, - } - command.init() - return command -} - -var testLogConfig = map[string]string{ - "admin": "debug", - "alternate_protocols_cache": "debug", - "aws": "debug", - "assert": "debug", - "backtrace": "debug", - "cache_filter": "debug", - "client": "debug", - "config": "debug", - "connection": "debug", - "conn_handler": "debug", - "decompression": "debug", - "dns": "debug", - "dubbo": "debug", - "envoy_bug": "debug", - "ext_authz": "debug", - "ext_proc": "debug", - "rocketmq": "debug", - "file": "debug", - "filter": "debug", - "forward_proxy": "debug", - "grpc": "debug", - "happy_eyeballs": "debug", - "hc": "debug", - "health_checker": "debug", - "http": "debug", - "http2": "debug", - "hystrix": "debug", - "init": "debug", - "io": "debug", - "jwt": "debug", - "kafka": "debug", - "key_value_store": "debug", - "lua": "debug", - "main": "debug", - "matcher": "debug", - "misc": "debug", - "mongo": "debug", - "multi_connection": "debug", - "oauth2": "debug", - "quic": "debug", - "quic_stream": "debug", - "pool": "debug", - "rbac": "debug", - "rds": "debug", - "redis": "debug", - "router": "debug", - "runtime": "debug", - "stats": "debug", - "secret": "debug", - "tap": "debug", - "testing": "debug", - "thrift": "debug", - "tracing": "debug", - "upstream": "debug", - "udp": "debug", - "wasm": "debug", - "websocket": "debug", -} diff --git a/cli/cmd/proxy/read/command.go b/cli/cmd/proxy/read/command.go index e85d7166e9..ad2bb96303 100644 --- a/cli/cmd/proxy/read/command.go +++ b/cli/cmd/proxy/read/command.go @@ -7,6 +7,9 @@ import ( "strings" "sync" + "github.com/hashicorp/consul-k8s/cli/common" + "github.com/hashicorp/consul-k8s/cli/common/flag" + "github.com/hashicorp/consul-k8s/cli/common/terminal" "github.com/posener/complete" helmCLI "helm.sh/helm/v3/pkg/cli" "k8s.io/apimachinery/pkg/api/validation" @@ -14,11 +17,6 @@ import ( "k8s.io/client-go/kubernetes" "k8s.io/client-go/rest" "k8s.io/utils/strings/slices" - - "github.com/hashicorp/consul-k8s/cli/common" - "github.com/hashicorp/consul-k8s/cli/common/envoy" - "github.com/hashicorp/consul-k8s/cli/common/flag" - "github.com/hashicorp/consul-k8s/cli/common/terminal" ) // defaultAdminPort is the port where the Envoy admin API is exposed. @@ -69,7 +67,7 @@ type ReadCommand struct { flagKubeConfig string flagKubeContext string - fetchConfig func(context.Context, common.PortForwarder) (*envoy.EnvoyConfig, error) + fetchConfig func(context.Context, common.PortForwarder) (*EnvoyConfig, error) restConfig *rest.Config @@ -79,7 +77,7 @@ type ReadCommand struct { func (c *ReadCommand) init() { if c.fetchConfig == nil { - c.fetchConfig = envoy.FetchConfig + c.fetchConfig = FetchConfig } c.set = flag.NewSets() @@ -322,8 +320,8 @@ func (c *ReadCommand) fetchAdminPorts() (map[string]int, error) { return adminPorts, nil } -func (c *ReadCommand) fetchConfigs(adminPorts map[string]int) (map[string]*envoy.EnvoyConfig, error) { - configs := make(map[string]*envoy.EnvoyConfig, 0) +func (c *ReadCommand) fetchConfigs(adminPorts map[string]int) (map[string]*EnvoyConfig, error) { + configs := make(map[string]*EnvoyConfig, 0) for name, adminPort := range adminPorts { pf := common.PortForward{ @@ -345,7 +343,7 @@ func (c *ReadCommand) fetchConfigs(adminPorts map[string]int) (map[string]*envoy return configs, nil } -func (c *ReadCommand) outputConfigs(configs map[string]*envoy.EnvoyConfig) error { +func (c *ReadCommand) outputConfigs(configs map[string]*EnvoyConfig) error { switch c.flagOutput { case Table: return c.outputTables(configs) @@ -398,7 +396,7 @@ func (c *ReadCommand) filterWarnings() []string { return warnings } -func (c *ReadCommand) outputTables(configs map[string]*envoy.EnvoyConfig) error { +func (c *ReadCommand) outputTables(configs map[string]*EnvoyConfig) error { if c.flagFQDN != "" || c.flagAddress != "" || c.flagPort != -1 { c.UI.Output("Filters applied", terminal.WithHeaderStyle()) @@ -433,7 +431,7 @@ func (c *ReadCommand) outputTables(configs map[string]*envoy.EnvoyConfig) error return nil } -func (c *ReadCommand) outputJSON(configs map[string]*envoy.EnvoyConfig) error { +func (c *ReadCommand) outputJSON(configs map[string]*EnvoyConfig) error { cfgs := make(map[string]interface{}) for name, config := range configs { cfg := make(map[string]interface{}) @@ -469,11 +467,11 @@ func (c *ReadCommand) outputJSON(configs map[string]*envoy.EnvoyConfig) error { return nil } -func (c *ReadCommand) outputRaw(configs map[string]*envoy.EnvoyConfig) error { +func (c *ReadCommand) outputRaw(configs map[string]*EnvoyConfig) error { cfgs := make(map[string]interface{}, 0) for name, config := range configs { var cfg interface{} - if err := json.Unmarshal(config.RawCfg, &cfg); err != nil { + if err := json.Unmarshal(config.rawCfg, &cfg); err != nil { return err } @@ -490,7 +488,7 @@ func (c *ReadCommand) outputRaw(configs map[string]*envoy.EnvoyConfig) error { return nil } -func (c *ReadCommand) outputClustersTable(clusters []envoy.Cluster) { +func (c *ReadCommand) outputClustersTable(clusters []Cluster) { if !c.shouldPrintTable(c.flagClusters) { return } @@ -498,16 +496,14 @@ func (c *ReadCommand) outputClustersTable(clusters []envoy.Cluster) { c.UI.Output(fmt.Sprintf("Clusters (%d)", len(clusters)), terminal.WithHeaderStyle()) table := terminal.NewTable("Name", "FQDN", "Endpoints", "Type", "Last Updated") for _, cluster := range clusters { - table.AddRow([]string{ - cluster.Name, cluster.FullyQualifiedDomainName, strings.Join(cluster.Endpoints, ", "), - cluster.Type, cluster.LastUpdated, - }, []string{}) + table.AddRow([]string{cluster.Name, cluster.FullyQualifiedDomainName, strings.Join(cluster.Endpoints, ", "), + cluster.Type, cluster.LastUpdated}, []string{}) } c.UI.Table(table) c.UI.Output("") } -func (c *ReadCommand) outputEndpointsTable(endpoints []envoy.Endpoint) { +func (c *ReadCommand) outputEndpointsTable(endpoints []Endpoint) { if !c.shouldPrintTable(c.flagEndpoints) { return } @@ -516,7 +512,7 @@ func (c *ReadCommand) outputEndpointsTable(endpoints []envoy.Endpoint) { c.UI.Table(formatEndpoints(endpoints)) } -func (c *ReadCommand) outputListenersTable(listeners []envoy.Listener) { +func (c *ReadCommand) outputListenersTable(listeners []Listener) { if !c.shouldPrintTable(c.flagListeners) { return } @@ -525,7 +521,7 @@ func (c *ReadCommand) outputListenersTable(listeners []envoy.Listener) { c.UI.Table(formatListeners(listeners)) } -func (c *ReadCommand) outputRoutesTable(routes []envoy.Route) { +func (c *ReadCommand) outputRoutesTable(routes []Route) { if !c.shouldPrintTable(c.flagRoutes) { return } @@ -534,7 +530,7 @@ func (c *ReadCommand) outputRoutesTable(routes []envoy.Route) { c.UI.Table(formatRoutes(routes)) } -func (c *ReadCommand) outputSecretsTable(secrets []envoy.Secret) { +func (c *ReadCommand) outputSecretsTable(secrets []Secret) { if !c.shouldPrintTable(c.flagSecrets) { return } diff --git a/cli/cmd/proxy/read/command_test.go b/cli/cmd/proxy/read/command_test.go index 1e439bce91..27f19e7370 100644 --- a/cli/cmd/proxy/read/command_test.go +++ b/cli/cmd/proxy/read/command_test.go @@ -9,18 +9,16 @@ import ( "os" "testing" + "github.com/hashicorp/consul-k8s/cli/common" + cmnFlag "github.com/hashicorp/consul-k8s/cli/common/flag" + "github.com/hashicorp/consul-k8s/cli/common/terminal" + "github.com/hashicorp/go-hclog" "github.com/posener/complete" "github.com/stretchr/testify/assert" "github.com/stretchr/testify/require" v1 "k8s.io/api/core/v1" metav1 "k8s.io/apimachinery/pkg/apis/meta/v1" "k8s.io/client-go/kubernetes/fake" - - "github.com/hashicorp/consul-k8s/cli/common" - "github.com/hashicorp/consul-k8s/cli/common/envoy" - cmnFlag "github.com/hashicorp/consul-k8s/cli/common/flag" - "github.com/hashicorp/consul-k8s/cli/common/terminal" - "github.com/hashicorp/go-hclog" ) func TestFlagParsing(t *testing.T) { @@ -67,48 +65,38 @@ func TestReadCommandOutput(t *testing.T) { // These regular expressions must be present in the output. expectedHeader := fmt.Sprintf("Envoy configuration for %s in namespace default:", podName) expected := map[string][]string{ - "-clusters": { - "==> Clusters \\(5\\)", + "-clusters": {"==> Clusters \\(5\\)", "Name.*FQDN.*Endpoints.*Type.*Last Updated", "local_agent.*192\\.168\\.79\\.187:8502.*STATIC.*2022-05-13T04:22:39\\.553Z", "local_app.*127\\.0\\.0\\.1:8080.*STATIC.*2022-05-13T04:22:39\\.655Z", "client.*client\\.default\\.dc1\\.internal\\.bc3815c2-1a0f-f3ff-a2e9-20d791f08d00\\.consul.*EDS", "frontend.*frontend\\.default\\.dc1\\.internal\\.bc3815c2-1a0f-f3ff-a2e9-20d791f08d00\\.consul", - "original-destination.*ORIGINAL_DST", - }, + "original-destination.*ORIGINAL_DST"}, - "-endpoints": { - "==> Endpoints \\(6\\)", + "-endpoints": {"==> Endpoints \\(6\\)", "Address:Port.*Cluster.*Weight.*Status", "192.168.79.187:8502.*local_agent.*1.00.*HEALTHY", "127.0.0.1:8080.*local_app.*1.00.*HEALTHY", "192.168.18.110:20000.*client.*1.00.*HEALTHY", "192.168.52.101:20000.*client.*1.00.*HEALTHY", "192.168.65.131:20000.*client.*1.00.*HEALTHY", - "192.168.63.120:20000.*frontend.*1.00.*HEALTHY", - }, + "192.168.63.120:20000.*frontend.*1.00.*HEALTHY"}, - "-listeners": { - "==> Listeners \\(2\\)", + "-listeners": {"==> Listeners \\(2\\)", "Name.*Address:Port.*Direction.*Filter Chain Match.*Filters.*Last Updated", "public_listener.*192\\.168\\.69\\.179:20000.*INBOUND.*Any.*\\* -> local_app/", "outbound_listener.*127.0.0.1:15001.*OUTBOUND.*10\\.100\\.134\\.173/32, 240\\.0\\.0\\.3/32.*TCP: -> client", "10\\.100\\.31\\.2/32, 240\\.0\\.0\\.5/32.*TCP: -> frontend", - "Any.*TCP: -> original-destination", - }, + "Any.*TCP: -> original-destination"}, - "-routes": { - "==> Routes \\(1\\)", + "-routes": {"==> Routes \\(1\\)", "Name.*Destination Cluster.*Last Updated", - "public_listener.*local_app/", - }, + "public_listener.*local_app/"}, - "-secrets": { - "==> Secrets \\(2\\)", + "-secrets": {"==> Secrets \\(2\\)", "Name.*Type.*Last Updated", "default.*Dynamic Active", - "ROOTCA.*Dynamic Warming", - }, + "ROOTCA.*Dynamic Warming"}, } cases := map[string][]string{ @@ -134,7 +122,7 @@ func TestReadCommandOutput(t *testing.T) { c.kubernetes = fake.NewSimpleClientset(&v1.PodList{Items: []v1.Pod{fakePod}}) // A fetchConfig function that just returns the test Envoy config. - c.fetchConfig = func(context.Context, common.PortForwarder) (*envoy.EnvoyConfig, error) { + c.fetchConfig = func(context.Context, common.PortForwarder) (*EnvoyConfig, error) { return testEnvoyConfig, nil } @@ -242,7 +230,7 @@ func TestFilterWarnings(t *testing.T) { buf := new(bytes.Buffer) c := setupCommand(buf) c.kubernetes = fake.NewSimpleClientset(&v1.PodList{Items: []v1.Pod{fakePod}}) - c.fetchConfig = func(context.Context, common.PortForwarder) (*envoy.EnvoyConfig, error) { + c.fetchConfig = func(context.Context, common.PortForwarder) (*EnvoyConfig, error) { return testEnvoyConfig, nil } @@ -307,73 +295,3 @@ func TestTaskCreateCommand_AutocompleteArgs(t *testing.T) { c := cmd.AutocompleteArgs() assert.Equal(t, complete.PredictNothing, c) } - -// testEnvoyConfig is what we expect the config at `test_config_dump.json` to be. - -var testEnvoyConfig = &envoy.EnvoyConfig{ - Clusters: []envoy.Cluster{ - {Name: "local_agent", FullyQualifiedDomainName: "local_agent", Endpoints: []string{"192.168.79.187:8502"}, Type: "STATIC", LastUpdated: "2022-05-13T04:22:39.553Z"}, - - {Name: "client", FullyQualifiedDomainName: "client.default.dc1.internal.bc3815c2-1a0f-f3ff-a2e9-20d791f08d00.consul", Endpoints: []string{"192.168.18.110:20000", "192.168.52.101:20000", "192.168.65.131:20000"}, Type: "EDS", LastUpdated: "2022-08-10T12:30:32.326Z"}, - - {Name: "frontend", FullyQualifiedDomainName: "frontend.default.dc1.internal.bc3815c2-1a0f-f3ff-a2e9-20d791f08d00.consul", Endpoints: []string{"192.168.63.120:20000"}, Type: "EDS", LastUpdated: "2022-08-10T12:30:32.233Z"}, - - {Name: "local_app", FullyQualifiedDomainName: "local_app", Endpoints: []string{"127.0.0.1:8080"}, Type: "STATIC", LastUpdated: "2022-05-13T04:22:39.655Z"}, - - {Name: "original-destination", FullyQualifiedDomainName: "original-destination", Endpoints: []string{}, Type: "ORIGINAL_DST", LastUpdated: "2022-05-13T04:22:39.743Z"}, - }, - - Endpoints: []envoy.Endpoint{ - {Address: "192.168.79.187:8502", Cluster: "local_agent", Weight: 1, Status: "HEALTHY"}, - - {Address: "192.168.18.110:20000", Cluster: "client", Weight: 1, Status: "HEALTHY"}, - - {Address: "192.168.52.101:20000", Cluster: "client", Weight: 1, Status: "HEALTHY"}, - - {Address: "192.168.65.131:20000", Cluster: "client", Weight: 1, Status: "HEALTHY"}, - - {Address: "192.168.63.120:20000", Cluster: "frontend", Weight: 1, Status: "HEALTHY"}, - - {Address: "127.0.0.1:8080", Cluster: "local_app", Weight: 1, Status: "HEALTHY"}, - }, - - Listeners: []envoy.Listener{ - {Name: "public_listener", Address: "192.168.69.179:20000", FilterChain: []envoy.FilterChain{{Filters: []string{"HTTP: * -> local_app/"}, FilterChainMatch: "Any"}}, Direction: "INBOUND", LastUpdated: "2022-08-10T12:30:47.142Z"}, - - {Name: "outbound_listener", Address: "127.0.0.1:15001", FilterChain: []envoy.FilterChain{ - {Filters: []string{"TCP: -> client"}, FilterChainMatch: "10.100.134.173/32, 240.0.0.3/32"}, - - {Filters: []string{"TCP: -> frontend"}, FilterChainMatch: "10.100.31.2/32, 240.0.0.5/32"}, - - {Filters: []string{"TCP: -> original-destination"}, FilterChainMatch: "Any"}, - }, Direction: "OUTBOUND", LastUpdated: "2022-07-18T15:31:03.246Z"}, - }, - - Routes: []envoy.Route{ - { - Name: "public_listener", - - DestinationCluster: "local_app/", - - LastUpdated: "2022-08-10T12:30:47.141Z", - }, - }, - - Secrets: []envoy.Secret{ - { - Name: "default", - - Type: "Dynamic Active", - - LastUpdated: "2022-05-24T17:41:59.078Z", - }, - - { - Name: "ROOTCA", - - Type: "Dynamic Warming", - - LastUpdated: "2022-03-15T05:14:22.868Z", - }, - }, -} diff --git a/cli/common/envoy/http.go b/cli/cmd/proxy/read/config.go similarity index 91% rename from cli/common/envoy/http.go rename to cli/cmd/proxy/read/config.go index 88299d6724..e7e6bcad34 100644 --- a/cli/common/envoy/http.go +++ b/cli/cmd/proxy/read/config.go @@ -1,10 +1,8 @@ -package envoy +package read import ( - "bytes" "context" "encoding/json" - "errors" "fmt" "io" "net" @@ -14,13 +12,11 @@ import ( "github.com/hashicorp/consul-k8s/cli/common" ) -var ErrNoLoggersReturned = errors.New("No loggers were returned from Envoy") - // EnvoyConfig represents the configuration retrieved from a config dump at the // admin endpoint. It wraps the Envoy ConfigDump struct to give us convenient // access to the different sections of the config. type EnvoyConfig struct { - RawCfg []byte + rawCfg []byte Clusters []Cluster Endpoints []Endpoint Listeners []Listener @@ -73,54 +69,6 @@ type Secret struct { LastUpdated string } -// CallLoggingEndpoint requests the logging endpoint from Envoy Admin Interface for a given port -// This is used to both read and update the logging levels (the envoy admin interface uses the same endpoint for both) -// more can be read about that endpoint https://www.envoyproxy.io/docs/envoy/latest/operations/admin#post--logging -func CallLoggingEndpoint(ctx context.Context, portForward common.PortForwarder, params *LoggerParams) (map[string]string, error) { - endpoint, err := portForward.Open(ctx) - if err != nil { - return nil, err - } - - defer portForward.Close() - - // this endpoint does not support returning json, so we've gotta parse the plain text - response, err := http.Post(fmt.Sprintf("http://%s/logging%s", endpoint, params), "text/plain", bytes.NewBuffer([]byte{})) - if err != nil { - return nil, err - } - - body, err := io.ReadAll(response.Body) - if err != nil { - return nil, fmt.Errorf("failed to reach envoy: %v", err) - } - - if response.StatusCode >= 400 { - return nil, fmt.Errorf("call to envoy failed with status code: %d, and message: %s", response.StatusCode, body) - } - - loggers := strings.Split(string(body), "\n") - if len(loggers) == 0 { - return nil, ErrNoLoggersReturned - } - - logLevels := make(map[string]string) - var name string - var level string - - // the first line here is just a header - for _, logger := range loggers[1:] { - if len(logger) == 0 { - continue - } - fmt.Sscanf(logger, "%s %s", &name, &level) - name = strings.TrimRight(name, ":") - logLevels[name] = level - } - - return logLevels, nil -} - // FetchConfig opens a port forward to the Envoy admin API and fetches the // configuration from the config dump endpoint. func FetchConfig(ctx context.Context, portForward common.PortForwarder) (*EnvoyConfig, error) { @@ -169,7 +117,7 @@ func FetchConfig(ctx context.Context, portForward common.PortForwarder) (*EnvoyC // JSON returns the original JSON Envoy config dump data which was used to create // the Config object. func (c *EnvoyConfig) JSON() []byte { - return c.RawCfg + return c.rawCfg } // UnmarshalJSON implements the json.Unmarshaler interface to unmarshal the raw @@ -178,7 +126,7 @@ func (c *EnvoyConfig) JSON() []byte { func (c *EnvoyConfig) UnmarshalJSON(b []byte) error { // Save the original config dump bytes for marshalling. We should treat this // struct as immutable so this should be safe. - c.RawCfg = b + c.rawCfg = b var root root err := json.Unmarshal(b, &root) diff --git a/cli/common/envoy/http_test.go b/cli/cmd/proxy/read/config_test.go similarity index 93% rename from cli/common/envoy/http_test.go rename to cli/cmd/proxy/read/config_test.go index 291eb2c22b..6b0e425794 100644 --- a/cli/common/envoy/http_test.go +++ b/cli/cmd/proxy/read/config_test.go @@ -1,38 +1,21 @@ -package envoy +package read import ( "bytes" "context" + "embed" "encoding/json" "fmt" "net/http" "net/http/httptest" - "os" "strings" "testing" "github.com/stretchr/testify/require" ) -func TestCallLoggingEndpoint(t *testing.T) { - t.Parallel() - rawLogLevels, err := os.ReadFile("testdata/fetch_debug_levels.txt") - require.NoError(t, err) - mockServer := httptest.NewServer(http.HandlerFunc(func(w http.ResponseWriter, r *http.Request) { - w.Write(rawLogLevels) - })) - - defer mockServer.Close() - - mpf := &mockPortForwarder{ - openBehavior: func(ctx context.Context) (string, error) { - return strings.Replace(mockServer.URL, "http://", "", 1), nil - }, - } - logLevels, err := CallLoggingEndpoint(context.Background(), mpf, NewLoggerParams()) - require.NoError(t, err) - require.Equal(t, testLogConfig(), logLevels) -} +//go:embed test_config_dump.json test_clusters.json +var fs embed.FS const ( testConfigDump = "test_config_dump.json" @@ -52,7 +35,7 @@ func TestUnmarshaling(t *testing.T) { } func TestJSON(t *testing.T) { - raw, err := os.ReadFile(fmt.Sprintf("testdata/%s", testConfigDump)) + raw, err := fs.ReadFile(testConfigDump) require.NoError(t, err) expected := bytes.TrimSpace(raw) @@ -66,10 +49,10 @@ func TestJSON(t *testing.T) { } func TestFetchConfig(t *testing.T) { - configDump, err := os.ReadFile(fmt.Sprintf("testdata/%s", testConfigDump)) + configDump, err := fs.ReadFile(testConfigDump) require.NoError(t, err) - clusters, err := os.ReadFile(fmt.Sprintf("testdata/%s", testClusters)) + clusters, err := fs.ReadFile(testClusters) require.NoError(t, err) mockServer := httptest.NewServer(http.HandlerFunc(func(w http.ResponseWriter, r *http.Request) { @@ -463,11 +446,18 @@ func TestClusterParsingEndpoints(t *testing.T) { require.Equal(t, expected, actual) } +type mockPortForwarder struct { + openBehavior func(context.Context) (string, error) +} + +func (m *mockPortForwarder) Open(ctx context.Context) (string, error) { return m.openBehavior(ctx) } +func (m *mockPortForwarder) Close() {} + func rawEnvoyConfig(t *testing.T) []byte { - configDump, err := os.ReadFile(fmt.Sprintf("testdata/%s", testConfigDump)) + configDump, err := fs.ReadFile(testConfigDump) require.NoError(t, err) - clusters, err := os.ReadFile(fmt.Sprintf("testdata/%s", testClusters)) + clusters, err := fs.ReadFile(testClusters) require.NoError(t, err) return []byte(fmt.Sprintf("{\n\"config_dump\":%s,\n\"clusters\":%s}", string(configDump), string(clusters))) @@ -518,18 +508,3 @@ var testEnvoyConfig = &EnvoyConfig{ }, }, } - -type mockPortForwarder struct { - openBehavior func(context.Context) (string, error) -} - -func (m *mockPortForwarder) Open(ctx context.Context) (string, error) { return m.openBehavior(ctx) } -func (m *mockPortForwarder) Close() {} - -func testLogConfig() map[string]string { - cfg := make(map[string]string, len(EnvoyLoggers)) - for k := range EnvoyLoggers { - cfg[k] = "debug" - } - return cfg -} diff --git a/cli/common/envoy/types.go b/cli/cmd/proxy/read/envoy_types.go similarity index 99% rename from cli/common/envoy/types.go rename to cli/cmd/proxy/read/envoy_types.go index 505248e983..cc1ffcf7e2 100644 --- a/cli/common/envoy/types.go +++ b/cli/cmd/proxy/read/envoy_types.go @@ -1,4 +1,4 @@ -package envoy +package read /* Envoy Types These types are based on the JSON returned from the Envoy Config Dump API on the diff --git a/cli/cmd/proxy/read/filters.go b/cli/cmd/proxy/read/filters.go index ab3e21b4d8..dc65172f32 100644 --- a/cli/cmd/proxy/read/filters.go +++ b/cli/cmd/proxy/read/filters.go @@ -3,8 +3,6 @@ package read import ( "strconv" "strings" - - "github.com/hashicorp/consul-k8s/cli/common/envoy" ) // FilterClusters takes a slice of clusters along with parameters for filtering @@ -19,7 +17,7 @@ import ( // // The filters are applied in combination such that a cluster must adhere to // all of the filtering values which are passed in. -func FilterClusters(clusters []envoy.Cluster, fqdn, address string, port int) []envoy.Cluster { +func FilterClusters(clusters []Cluster, fqdn, address string, port int) []Cluster { // No filtering no-op. if fqdn == "" && address == "" && port == -1 { return clusters @@ -27,7 +25,7 @@ func FilterClusters(clusters []envoy.Cluster, fqdn, address string, port int) [] portStr := ":" + strconv.Itoa(port) - filtered := make([]envoy.Cluster, 0) + filtered := make([]Cluster, 0) for _, cluster := range clusters { if !strings.Contains(cluster.FullyQualifiedDomainName, fqdn) { continue @@ -60,14 +58,14 @@ func FilterClusters(clusters []envoy.Cluster, fqdn, address string, port int) [] // // The filters are applied in combination such that an endpoint must adhere to // all of the filtering values which are passed in. -func FilterEndpoints(endpoints []envoy.Endpoint, address string, port int) []envoy.Endpoint { +func FilterEndpoints(endpoints []Endpoint, address string, port int) []Endpoint { if address == "" && port == -1 { return endpoints } portStr := ":" + strconv.Itoa(port) - filtered := make([]envoy.Endpoint, 0) + filtered := make([]Endpoint, 0) for _, endpoint := range endpoints { if strings.Contains(endpoint.Address, address) && (port == -1 || strings.Contains(endpoint.Address, portStr)) { filtered = append(filtered, endpoint) @@ -87,14 +85,14 @@ func FilterEndpoints(endpoints []envoy.Endpoint, address string, port int) []env // // The filters are applied in combination such that an listener must adhere to // all of the filtering values which are passed in. -func FilterListeners(listeners []envoy.Listener, address string, port int) []envoy.Listener { +func FilterListeners(listeners []Listener, address string, port int) []Listener { if address == "" && port == -1 { return listeners } portStr := ":" + strconv.Itoa(port) - filtered := make([]envoy.Listener, 0) + filtered := make([]Listener, 0) for _, listener := range listeners { if strings.Contains(listener.Address, address) && (port == -1 || strings.Contains(listener.Address, portStr)) { filtered = append(filtered, listener) diff --git a/cli/cmd/proxy/read/filters_test.go b/cli/cmd/proxy/read/filters_test.go index 7340b6ae0d..48ff3a97da 100644 --- a/cli/cmd/proxy/read/filters_test.go +++ b/cli/cmd/proxy/read/filters_test.go @@ -4,12 +4,10 @@ import ( "testing" "github.com/stretchr/testify/require" - - "github.com/hashicorp/consul-k8s/cli/common/envoy" ) func TestFilterClusters(t *testing.T) { - given := []envoy.Cluster{ + given := []Cluster{ { FullyQualifiedDomainName: "local_agent", Endpoints: []string{"192.168.79.187:8502"}, @@ -44,13 +42,13 @@ func TestFilterClusters(t *testing.T) { fqdn string address string port int - expected []envoy.Cluster + expected []Cluster }{ "No filter": { fqdn: "", address: "", port: -1, - expected: []envoy.Cluster{ + expected: []Cluster{ { FullyQualifiedDomainName: "local_agent", Endpoints: []string{"192.168.79.187:8502"}, @@ -85,7 +83,7 @@ func TestFilterClusters(t *testing.T) { fqdn: "default", address: "", port: -1, - expected: []envoy.Cluster{ + expected: []Cluster{ { FullyQualifiedDomainName: "client.default.dc1.internal.bc3815c2-1a0f-f3ff-a2e9-20d791f08d00.consul", Endpoints: []string{}, @@ -104,7 +102,7 @@ func TestFilterClusters(t *testing.T) { fqdn: "", address: "127.0.", port: -1, - expected: []envoy.Cluster{ + expected: []Cluster{ { FullyQualifiedDomainName: "local_app", Endpoints: []string{"127.0.0.1:8080"}, @@ -119,7 +117,7 @@ func TestFilterClusters(t *testing.T) { fqdn: "", address: "", port: 8080, - expected: []envoy.Cluster{ + expected: []Cluster{ { FullyQualifiedDomainName: "local_app", Endpoints: []string{"127.0.0.1:8080"}, @@ -134,7 +132,7 @@ func TestFilterClusters(t *testing.T) { fqdn: "local", address: "127.0.0.1", port: -1, - expected: []envoy.Cluster{ + expected: []Cluster{ { FullyQualifiedDomainName: "local_app", Endpoints: []string{"127.0.0.1:8080"}, @@ -149,7 +147,7 @@ func TestFilterClusters(t *testing.T) { fqdn: "local", address: "", port: 8080, - expected: []envoy.Cluster{ + expected: []Cluster{ { FullyQualifiedDomainName: "local_app", Endpoints: []string{"127.0.0.1:8080"}, @@ -160,7 +158,7 @@ func TestFilterClusters(t *testing.T) { fqdn: "", address: "127.0.0.1", port: 8080, - expected: []envoy.Cluster{ + expected: []Cluster{ { FullyQualifiedDomainName: "local_app", Endpoints: []string{"127.0.0.1:8080"}, @@ -171,7 +169,7 @@ func TestFilterClusters(t *testing.T) { fqdn: "local", address: "192.168.79.187", port: 8502, - expected: []envoy.Cluster{ + expected: []Cluster{ { FullyQualifiedDomainName: "local_agent", Endpoints: []string{"192.168.79.187:8502"}, @@ -189,7 +187,7 @@ func TestFilterClusters(t *testing.T) { } func TestFilterEndpoints(t *testing.T) { - given := []envoy.Endpoint{ + given := []Endpoint{ { Address: "192.168.79.187:8502", }, @@ -210,12 +208,12 @@ func TestFilterEndpoints(t *testing.T) { cases := map[string]struct { address string port int - expected []envoy.Endpoint + expected []Endpoint }{ "No filter": { address: "", port: -1, - expected: []envoy.Endpoint{ + expected: []Endpoint{ { Address: "192.168.79.187:8502", }, @@ -236,7 +234,7 @@ func TestFilterEndpoints(t *testing.T) { "Filter address": { address: "127.0.0.1", port: -1, - expected: []envoy.Endpoint{ + expected: []Endpoint{ { Address: "127.0.0.1:8080", }, @@ -245,7 +243,7 @@ func TestFilterEndpoints(t *testing.T) { "Filter port": { address: "", port: 20000, - expected: []envoy.Endpoint{ + expected: []Endpoint{ { Address: "192.168.31.201:20000", }, @@ -260,7 +258,7 @@ func TestFilterEndpoints(t *testing.T) { "Filter address and port": { address: "235", port: 20000, - expected: []envoy.Endpoint{ + expected: []Endpoint{ { Address: "192.168.47.235:20000", }, @@ -277,7 +275,7 @@ func TestFilterEndpoints(t *testing.T) { } func TestFilterListeners(t *testing.T) { - given := []envoy.Listener{ + given := []Listener{ { Address: "192.168.69.179:20000", }, @@ -289,12 +287,12 @@ func TestFilterListeners(t *testing.T) { cases := map[string]struct { address string port int - expected []envoy.Listener + expected []Listener }{ "No filter": { address: "", port: -1, - expected: []envoy.Listener{ + expected: []Listener{ { Address: "192.168.69.179:20000", }, @@ -306,7 +304,7 @@ func TestFilterListeners(t *testing.T) { "Filter address": { address: "127.0.0.1", port: -1, - expected: []envoy.Listener{ + expected: []Listener{ { Address: "127.0.0.1:15001", }, @@ -315,7 +313,7 @@ func TestFilterListeners(t *testing.T) { "Filter port": { address: "", port: 20000, - expected: []envoy.Listener{ + expected: []Listener{ { Address: "192.168.69.179:20000", }, @@ -324,7 +322,7 @@ func TestFilterListeners(t *testing.T) { "Filter address and port": { address: "192.168.69.179", port: 20000, - expected: []envoy.Listener{ + expected: []Listener{ { Address: "192.168.69.179:20000", }, diff --git a/cli/cmd/proxy/read/format.go b/cli/cmd/proxy/read/format.go index 90137db6a5..97d5ada86a 100644 --- a/cli/cmd/proxy/read/format.go +++ b/cli/cmd/proxy/read/format.go @@ -4,23 +4,20 @@ import ( "fmt" "strings" - "github.com/hashicorp/consul-k8s/cli/common/envoy" "github.com/hashicorp/consul-k8s/cli/common/terminal" ) -func formatClusters(clusters []envoy.Cluster) *terminal.Table { +func formatClusters(clusters []Cluster) *terminal.Table { table := terminal.NewTable("Name", "FQDN", "Endpoints", "Type", "Last Updated") for _, cluster := range clusters { - table.AddRow([]string{ - cluster.Name, cluster.FullyQualifiedDomainName, strings.Join(cluster.Endpoints, ", "), - cluster.Type, cluster.LastUpdated, - }, []string{}) + table.AddRow([]string{cluster.Name, cluster.FullyQualifiedDomainName, strings.Join(cluster.Endpoints, ", "), + cluster.Type, cluster.LastUpdated}, []string{}) } return table } -func formatEndpoints(endpoints []envoy.Endpoint) *terminal.Table { +func formatEndpoints(endpoints []Endpoint) *terminal.Table { table := terminal.NewTable("Address:Port", "Cluster", "Weight", "Status") for _, endpoint := range endpoints { var statusColor string @@ -38,7 +35,7 @@ func formatEndpoints(endpoints []envoy.Endpoint) *terminal.Table { return table } -func formatListeners(listeners []envoy.Listener) *terminal.Table { +func formatListeners(listeners []Listener) *terminal.Table { table := terminal.NewTable("Name", "Address:Port", "Direction", "Filter Chain Match", "Filters", "Last Updated") for _, listener := range listeners { for index, filter := range listener.FilterChain { @@ -60,7 +57,7 @@ func formatListeners(listeners []envoy.Listener) *terminal.Table { return table } -func formatRoutes(routes []envoy.Route) *terminal.Table { +func formatRoutes(routes []Route) *terminal.Table { table := terminal.NewTable("Name", "Destination Cluster", "Last Updated") for _, route := range routes { table.AddRow([]string{route.Name, route.DestinationCluster, route.LastUpdated}, []string{}) @@ -69,7 +66,7 @@ func formatRoutes(routes []envoy.Route) *terminal.Table { return table } -func formatSecrets(secrets []envoy.Secret) *terminal.Table { +func formatSecrets(secrets []Secret) *terminal.Table { table := terminal.NewTable("Name", "Type", "Last Updated") for _, secret := range secrets { table.AddRow([]string{secret.Name, secret.Type, secret.LastUpdated}, []string{}) diff --git a/cli/cmd/proxy/read/format_test.go b/cli/cmd/proxy/read/format_test.go index 95c562a0dd..7d6f975d39 100644 --- a/cli/cmd/proxy/read/format_test.go +++ b/cli/cmd/proxy/read/format_test.go @@ -5,10 +5,8 @@ import ( "context" "testing" - "github.com/stretchr/testify/require" - - "github.com/hashicorp/consul-k8s/cli/common/envoy" "github.com/hashicorp/consul-k8s/cli/common/terminal" + "github.com/stretchr/testify/require" ) func TestFormatClusters(t *testing.T) { @@ -23,7 +21,7 @@ func TestFormatClusters(t *testing.T) { "server.*server.default.dc1.internal.bc3815c2-1a0f-f3ff-a2e9-20d791f08d00.consul.*EDS.*2022-06-09T00:39:12\\.754Z", } - given := []envoy.Cluster{ + given := []Cluster{ { Name: "local_agent", FullyQualifiedDomainName: "local_agent", @@ -99,7 +97,7 @@ func TestFormatEndpoints(t *testing.T) { "192.168.65.131:20000.*1.00.*HEALTHY", } - given := []envoy.Endpoint{ + given := []Endpoint{ { Address: "192.168.79.187:8502", Cluster: "local_agent", @@ -176,11 +174,11 @@ func TestFormatListeners(t *testing.T) { "Any.*-> original-destination", } - given := []envoy.Listener{ + given := []Listener{ { Name: "public_listener", Address: "192.168.69.179:20000", - FilterChain: []envoy.FilterChain{ + FilterChain: []FilterChain{ { FilterChainMatch: "Any", Filters: []string{"* -> local_app/"}, @@ -192,7 +190,7 @@ func TestFormatListeners(t *testing.T) { { Name: "outbound_listener", Address: "127.0.0.1:15001", - FilterChain: []envoy.FilterChain{ + FilterChain: []FilterChain{ { FilterChainMatch: "10.100.134.173/32, 240.0.0.3/32", Filters: []string{"-> client.default.dc1.internal.bc3815c2-1a0f-f3ff-a2e9-20d791f08d00.consul"}, @@ -247,7 +245,7 @@ func TestFormatRoutes(t *testing.T) { "server.*server\\.default\\.dc1\\.internal\\.bc3815c2-1a0f-f3ff-a2e9-20d791f08d00\\.consul/.*2022-05-24T17:41:59\\.078Z", } - given := []envoy.Route{ + given := []Route{ { Name: "public_listener", DestinationCluster: "local_app/", @@ -284,7 +282,7 @@ func TestFormatSecrets(t *testing.T) { "ROOTCA.*Dynamic Warming.*2022-03-15T05:14:22.868Z", } - given := []envoy.Secret{ + given := []Secret{ { Name: "default", Type: "Dynamic Active", diff --git a/cli/common/envoy/testdata/test_clusters.json b/cli/cmd/proxy/read/test_clusters.json similarity index 100% rename from cli/common/envoy/testdata/test_clusters.json rename to cli/cmd/proxy/read/test_clusters.json diff --git a/cli/common/envoy/testdata/test_config_dump.json b/cli/cmd/proxy/read/test_config_dump.json similarity index 100% rename from cli/common/envoy/testdata/test_config_dump.json rename to cli/cmd/proxy/read/test_config_dump.json diff --git a/cli/cmd/troubleshoot/command.go b/cli/cmd/troubleshoot/command.go deleted file mode 100644 index d37c66e998..0000000000 --- a/cli/cmd/troubleshoot/command.go +++ /dev/null @@ -1,26 +0,0 @@ -package troubleshoot - -import ( - "fmt" - - "github.com/hashicorp/consul-k8s/cli/common" - "github.com/mitchellh/cli" -) - -// TroubleshootCommand provides a synopsis for the troubleshoot subcommands (e.g. proxy, upstreams). -type TroubleshootCommand struct { - *common.BaseCommand -} - -// Run prints out information about the subcommands. -func (c *TroubleshootCommand) Run([]string) int { - return cli.RunResultHelp -} - -func (c *TroubleshootCommand) Help() string { - return fmt.Sprintf("%s\n\nUsage: consul-k8s troubleshoot ", c.Synopsis()) -} - -func (c *TroubleshootCommand) Synopsis() string { - return "Troubleshoot network and security configurations." -} diff --git a/cli/cmd/troubleshoot/proxy/proxy.go b/cli/cmd/troubleshoot/proxy/proxy.go deleted file mode 100644 index 624757fad3..0000000000 --- a/cli/cmd/troubleshoot/proxy/proxy.go +++ /dev/null @@ -1,282 +0,0 @@ -package proxy - -import ( - "fmt" - "net" - "strings" - "sync" - - "github.com/hashicorp/consul-k8s/cli/common" - "github.com/hashicorp/consul-k8s/cli/common/flag" - "github.com/hashicorp/consul-k8s/cli/common/terminal" - troubleshoot "github.com/hashicorp/consul/troubleshoot/proxy" - "github.com/posener/complete" - helmCLI "helm.sh/helm/v3/pkg/cli" - "k8s.io/apimachinery/pkg/api/validation" - "k8s.io/client-go/kubernetes" - "k8s.io/client-go/rest" -) - -const ( - defaultAdminPort int = 19000 - flagNameKubeConfig = "kubeconfig" - flagNameKubeContext = "context" - flagNameNamespace = "namespace" - flagNamePod = "pod" - flagNameUpstreamEnvoyID = "upstream-envoy-id" - flagNameUpstreamIP = "upstream-ip" - DebugColor = "\033[0;36m%s\033[0m" -) - -type ProxyCommand struct { - *common.BaseCommand - - kubernetes kubernetes.Interface - - set *flag.Sets - - flagKubeConfig string - flagKubeContext string - flagNamespace string - - flagPod string - flagUpstreamEnvoyID string - flagUpstreamIP string - - restConfig *rest.Config - - once sync.Once - help string -} - -// init sets up flags and help text for the command. -func (c *ProxyCommand) init() { - c.set = flag.NewSets() - f := c.set.NewSet("Command Options") - - f.StringVar(&flag.StringVar{ - Name: flagNamePod, - Target: &c.flagPod, - Usage: "The pod to port-forward to.", - Aliases: []string{"p"}, - }) - - f.StringVar(&flag.StringVar{ - Name: flagNameUpstreamEnvoyID, - Target: &c.flagUpstreamEnvoyID, - Usage: "The envoy identifier of the upstream service that receives the communication. (explicit upstreams only)", - Aliases: []string{"id"}, - }) - - f.StringVar(&flag.StringVar{ - Name: flagNameUpstreamIP, - Target: &c.flagUpstreamIP, - Usage: "The IP address of the upstream service that receives the communication. (transparent proxy only)", - Aliases: []string{"ip"}, - }) - - f = c.set.NewSet("Global Options") - f.StringVar(&flag.StringVar{ - Name: flagNameKubeConfig, - Aliases: []string{"c"}, - Target: &c.flagKubeConfig, - Default: "", - Usage: "Set the path to kubeconfig file.", - }) - f.StringVar(&flag.StringVar{ - Name: flagNameKubeContext, - Target: &c.flagKubeContext, - Default: "", - Usage: "Set the Kubernetes context to use.", - }) - - f.StringVar(&flag.StringVar{ - Name: flagNameNamespace, - Target: &c.flagNamespace, - Usage: "The namespace the pod is in.", - Aliases: []string{"n"}, - }) - - c.help = c.set.Help() -} - -// Run executes the list command. -func (c *ProxyCommand) Run(args []string) int { - c.once.Do(c.init) - c.Log.ResetNamed("list") - defer common.CloseWithError(c.BaseCommand) - - // Parse the command line flags. - if err := c.set.Parse(args); err != nil { - c.UI.Output("Error parsing arguments: %v", err.Error(), terminal.WithErrorStyle()) - return 1 - } - - // Validate the command line flags. - if err := c.validateFlags(); err != nil { - c.UI.Output("Invalid argument: %v", err.Error(), terminal.WithErrorStyle()) - return 1 - } - - if c.kubernetes == nil { - if err := c.initKubernetes(); err != nil { - c.UI.Output("Error initializing Kubernetes client: %v", err.Error(), terminal.WithErrorStyle()) - return 1 - } - } - - if err := c.Troubleshoot(); err != nil { - c.UI.Output("Error running troubleshoot: %v", err.Error(), terminal.WithErrorStyle()) - return 1 - } - - return 0 -} - -// validateFlags ensures that the flags passed in by the can be used. -func (c *ProxyCommand) validateFlags() error { - - if (c.flagUpstreamEnvoyID == "" && c.flagUpstreamIP == "") || (c.flagUpstreamEnvoyID != "" && c.flagUpstreamIP != "") { - return fmt.Errorf("-upstream-envoy-id OR -upstream-ip is required.\n Please run `consul troubleshoot upstreams` to find the corresponding upstream.") - } - - if c.flagPod == "" { - return fmt.Errorf("-pod flag is required") - } - - if errs := validation.ValidateNamespaceName(c.flagNamespace, false); c.flagNamespace != "" && len(errs) > 0 { - return fmt.Errorf("invalid namespace name passed for -namespace/-n: %v", strings.Join(errs, "; ")) - } - - return nil -} - -// initKubernetes initializes the Kubernetes client. -func (c *ProxyCommand) initKubernetes() (err error) { - settings := helmCLI.New() - - if c.flagKubeConfig != "" { - settings.KubeConfig = c.flagKubeConfig - } - - if c.flagKubeContext != "" { - settings.KubeContext = c.flagKubeContext - } - - if c.restConfig == nil { - if c.restConfig, err = settings.RESTClientGetter().ToRESTConfig(); err != nil { - return fmt.Errorf("error creating Kubernetes REST config %v", err) - } - } - - if c.kubernetes == nil { - if c.kubernetes, err = kubernetes.NewForConfig(c.restConfig); err != nil { - return fmt.Errorf("error creating Kubernetes client %v", err) - } - } - - if c.flagNamespace == "" { - c.flagNamespace = settings.Namespace() - } - - return nil -} - -func (c *ProxyCommand) Troubleshoot() error { - pf := common.PortForward{ - Namespace: c.flagNamespace, - PodName: c.flagPod, - RemotePort: defaultAdminPort, - KubeClient: c.kubernetes, - RestConfig: c.restConfig, - } - - endpoint, err := pf.Open(c.Ctx) - if err != nil { - return err - } - defer pf.Close() - - adminAddr, adminPort, err := net.SplitHostPort(endpoint) - if err != nil { - return err - } - - adminAddrIP, err := net.ResolveIPAddr("ip", adminAddr) - if err != nil { - return err - } - - t, err := troubleshoot.NewTroubleshoot(adminAddrIP, adminPort) - if err != nil { - return err - } - - // err = t.GetEnvoyConfigDump() - // if err != nil { - // return err - // } - - messages, err := t.RunAllTests(c.flagUpstreamEnvoyID, c.flagUpstreamIP) - if err != nil { - return err - } - - c.UI.Output("Validation", terminal.WithHeaderStyle()) - for _, o := range messages { - if o.Success { - c.UI.Output(o.Message, terminal.WithSuccessStyle()) - } else { - c.UI.Output(o.Message, terminal.WithErrorStyle()) - for _, action := range o.PossibleActions { - c.UI.Output(fmt.Sprintf("-> %s", action), terminal.WithInfoStyle()) - } - } - } - - return nil -} - -// AutocompleteFlags returns a mapping of supported flags and autocomplete -// options for this command. The map key for the Flags map should be the -// complete flag such as "-foo" or "--foo". -func (c *ProxyCommand) AutocompleteFlags() complete.Flags { - return complete.Flags{ - fmt.Sprintf("-%s", flagNameNamespace): complete.PredictNothing, - fmt.Sprintf("-%s", flagNameKubeConfig): complete.PredictFiles("*"), - fmt.Sprintf("-%s", flagNameKubeContext): complete.PredictNothing, - } -} - -// AutocompleteArgs returns the argument predictor for this command. -// Since argument completion is not supported, this will return -// complete.PredictNothing. -func (c *ProxyCommand) AutocompleteArgs() complete.Predictor { - return complete.PredictNothing -} - -func (c *ProxyCommand) Synopsis() string { - return synopsis -} - -func (c *ProxyCommand) Help() string { - return help -} - -const ( - synopsis = "Troubleshoots service mesh issues." - help = ` -Usage: consul-k8s troubleshoot proxy [options] - - Connect to a pod with a proxy and troubleshoots service mesh communication issues. - - Requires a pod and upstream service SNI. - - Examples: - $ consul-k8s troubleshoot proxy -pod pod1 -upstream foo - - where 'pod1' is the pod running a consul proxy and 'foo' is the upstream envoy ID which - can be obtained by running: - $ consul-k8s troubleshoot upstreams [options] -` -) diff --git a/cli/cmd/troubleshoot/proxy/proxy_test.go b/cli/cmd/troubleshoot/proxy/proxy_test.go deleted file mode 100644 index 784cc7a136..0000000000 --- a/cli/cmd/troubleshoot/proxy/proxy_test.go +++ /dev/null @@ -1,72 +0,0 @@ -package proxy - -import ( - "bytes" - "context" - "io" - "os" - "testing" - - "github.com/hashicorp/consul-k8s/cli/common" - "github.com/hashicorp/consul-k8s/cli/common/terminal" - "github.com/hashicorp/go-hclog" - "github.com/stretchr/testify/require" - "k8s.io/client-go/kubernetes/fake" -) - -func TestFlagParsing(t *testing.T) { - cases := map[string]struct { - args []string - out int - }{ - "No args, should fail": { - args: []string{}, - out: 1, - }, - "Nonexistent flag passed, -foo bar, should fail": { - args: []string{"-foo", "bar"}, - out: 1, - }, - "Invalid argument passed, -namespace notaname, should fail": { - args: []string{"-namespace", "notaname"}, - out: 1, - }, - "Cannot pass both -upstream-envoy-id and -upstream-ip flags, should fail": { - args: []string{"-upstream-envoy-id", "1234", "-upstream-ip", "127.0.0.1"}, - out: 1, - }, - "Cannot pass empty -upstream-envoy-id and -upstream-ip flags, should fail": { - args: []string{"-upstream-envoy-id", "-upstream-ip"}, - out: 1, - }, - } - - for name, tc := range cases { - t.Run(name, func(t *testing.T) { - c := setupCommand(new(bytes.Buffer)) - c.kubernetes = fake.NewSimpleClientset() - out := c.Run(tc.args) - require.Equal(t, tc.out, out) - }) - } -} - -func setupCommand(buf io.Writer) *ProxyCommand { - // Log at a test level to standard out. - log := hclog.New(&hclog.LoggerOptions{ - Name: "test", - Level: hclog.Debug, - Output: os.Stdout, - }) - - // Setup and initialize the command struct - command := &ProxyCommand{ - BaseCommand: &common.BaseCommand{ - Log: log, - UI: terminal.NewUI(context.Background(), buf), - }, - } - command.init() - - return command -} diff --git a/cli/cmd/troubleshoot/upstreams/upstreams.go b/cli/cmd/troubleshoot/upstreams/upstreams.go deleted file mode 100644 index 7765b170a7..0000000000 --- a/cli/cmd/troubleshoot/upstreams/upstreams.go +++ /dev/null @@ -1,274 +0,0 @@ -package upstreams - -import ( - "fmt" - "net" - "sort" - "strconv" - "strings" - "sync" - - "github.com/hashicorp/consul-k8s/cli/common" - "github.com/hashicorp/consul-k8s/cli/common/flag" - "github.com/hashicorp/consul-k8s/cli/common/terminal" - troubleshoot "github.com/hashicorp/consul/troubleshoot/proxy" - "github.com/posener/complete" - helmCLI "helm.sh/helm/v3/pkg/cli" - "k8s.io/apimachinery/pkg/api/validation" - "k8s.io/client-go/kubernetes" - "k8s.io/client-go/rest" -) - -const ( - defaultAdminPort int = 19000 - flagNameKubeConfig = "kubeconfig" - flagNameKubeContext = "context" - flagNameNamespace = "namespace" - flagNamePod = "pod" -) - -type UpstreamsCommand struct { - *common.BaseCommand - - kubernetes kubernetes.Interface - - set *flag.Sets - - flagKubeConfig string - flagKubeContext string - flagNamespace string - - flagPod string - - restConfig *rest.Config - - once sync.Once - help string -} - -// init sets up flags and help text for the command. -func (c *UpstreamsCommand) init() { - c.set = flag.NewSets() - f := c.set.NewSet("Command Options") - - f.StringVar(&flag.StringVar{ - Name: flagNamePod, - Target: &c.flagPod, - Usage: "The pod to port-forward to.", - Aliases: []string{"p"}, - }) - - f = c.set.NewSet("Global Options") - f.StringVar(&flag.StringVar{ - Name: flagNameKubeConfig, - Aliases: []string{"c"}, - Target: &c.flagKubeConfig, - Default: "", - Usage: "Set the path to kubeconfig file.", - }) - f.StringVar(&flag.StringVar{ - Name: flagNameKubeContext, - Target: &c.flagKubeContext, - Default: "", - Usage: "Set the Kubernetes context to use.", - }) - - f.StringVar(&flag.StringVar{ - Name: flagNameNamespace, - Target: &c.flagNamespace, - Usage: "The namespace the pod is in.", - Aliases: []string{"n"}, - }) - - c.help = c.set.Help() -} - -// Run executes the list command. -func (c *UpstreamsCommand) Run(args []string) int { - c.once.Do(c.init) - c.Log.ResetNamed("list") - defer common.CloseWithError(c.BaseCommand) - - // Parse the command line flags. - if err := c.set.Parse(args); err != nil { - c.UI.Output("Error parsing arguments: %v", err.Error(), terminal.WithErrorStyle()) - return 1 - } - - // Validate the command line flags. - if err := c.validateFlags(); err != nil { - c.UI.Output("Invalid argument: %v", err.Error(), terminal.WithErrorStyle()) - return 1 - } - - if c.kubernetes == nil { - if err := c.initKubernetes(); err != nil { - c.UI.Output("Error initializing Kubernetes client: %v", err.Error(), terminal.WithErrorStyle()) - return 1 - } - } - - if err := c.Troubleshoot(); err != nil { - c.UI.Output("Error running troubleshoot: %v", err.Error(), terminal.WithErrorStyle()) - return 1 - } - - return 0 -} - -// validateFlags ensures that the flags passed in by the can be used. -func (c *UpstreamsCommand) validateFlags() error { - - if c.flagPod == "" { - return fmt.Errorf("-pod flag is required") - } - - if errs := validation.ValidateNamespaceName(c.flagNamespace, false); c.flagNamespace != "" && len(errs) > 0 { - return fmt.Errorf("invalid namespace name passed for -namespace/-n: %v", strings.Join(errs, "; ")) - } - - return nil -} - -// initKubernetes initializes the Kubernetes client. -func (c *UpstreamsCommand) initKubernetes() (err error) { - settings := helmCLI.New() - - if c.flagKubeConfig != "" { - settings.KubeConfig = c.flagKubeConfig - } - - if c.flagKubeContext != "" { - settings.KubeContext = c.flagKubeContext - } - - if c.restConfig == nil { - if c.restConfig, err = settings.RESTClientGetter().ToRESTConfig(); err != nil { - return fmt.Errorf("error creating Kubernetes REST config %v", err) - } - } - - if c.kubernetes == nil { - if c.kubernetes, err = kubernetes.NewForConfig(c.restConfig); err != nil { - return fmt.Errorf("error creating Kubernetes client %v", err) - } - } - - if c.flagNamespace == "" { - c.flagNamespace = settings.Namespace() - } - - return nil -} - -func (c *UpstreamsCommand) Troubleshoot() error { - pf := common.PortForward{ - Namespace: c.flagNamespace, - PodName: c.flagPod, - RemotePort: defaultAdminPort, - KubeClient: c.kubernetes, - RestConfig: c.restConfig, - } - - endpoint, err := pf.Open(c.Ctx) - if err != nil { - return fmt.Errorf("error opening endpoint: %v", err) - } - defer pf.Close() - - adminAddr, adminPort, err := net.SplitHostPort(endpoint) - if err != nil { - return fmt.Errorf("error splitting hostport: %v", err) - } - - adminAddrIP, err := net.ResolveIPAddr("ip", adminAddr) - if err != nil { - return fmt.Errorf("error resolving ip address: %v", err) - } - - t, err := troubleshoot.NewTroubleshoot(adminAddrIP, adminPort) - if err != nil { - return fmt.Errorf("error creating new troubleshoot: %v", err) - } - - envoyIDs, upstreamIPs, err := t.GetUpstreams() - if err != nil { - return fmt.Errorf("error getting upstreams: %v", err) - } - - c.UI.Output(fmt.Sprintf("Upstreams (explicit upstreams only) (%v)", len(envoyIDs)), terminal.WithHeaderStyle()) - for _, e := range envoyIDs { - c.UI.Output(e) - } - - c.UI.Output(fmt.Sprintf("Upstream IPs (transparent proxy only) (%v)", len(upstreamIPs)), terminal.WithHeaderStyle()) - table := terminal.NewTable("IPs ", "Virtual ", "Cluster Names") - for _, u := range upstreamIPs { - table.AddRow([]string{formatIPs(u.IPs), strconv.FormatBool(u.IsVirtual), formatClusterNames(u.ClusterNames)}, []string{}) - } - c.UI.Table(table) - - c.UI.Output("\nIf you cannot find the upstream address or cluster for a transparent proxy upstream:", terminal.WithInfoStyle()) - c.UI.Output("-> Check intentions: Transparent proxy upstreams are configured based on intentions. Make sure you "+ - "have configured intentions to allow traffic to your upstream.", terminal.WithInfoStyle()) - c.UI.Output("-> To check that the right cluster is being dialed, run a DNS lookup "+ - "for the upstream you are dialing. For example, run `dig backend.svc.consul` to return the IP address for the `backend` service. If the address you get from that is missing "+ - "from the upstream IPs, it means that your proxy may be misconfigured.", terminal.WithInfoStyle()) - - return nil -} - -// AutocompleteFlags returns a mapping of supported flags and autocomplete -// options for this command. The map key for the Flags map should be the -// complete flag such as "-foo" or "--foo". -func (c *UpstreamsCommand) AutocompleteFlags() complete.Flags { - return complete.Flags{ - fmt.Sprintf("-%s", flagNameNamespace): complete.PredictNothing, - fmt.Sprintf("-%s", flagNameKubeConfig): complete.PredictFiles("*"), - fmt.Sprintf("-%s", flagNameKubeContext): complete.PredictNothing, - } -} - -// AutocompleteArgs returns the argument predictor for this command. -// Since argument completion is not supported, this will return -// complete.PredictNothing. -func (c *UpstreamsCommand) AutocompleteArgs() complete.Predictor { - return complete.PredictNothing -} - -func (c *UpstreamsCommand) Synopsis() string { - return synopsis -} - -func (c *UpstreamsCommand) Help() string { - return help -} - -func formatIPs(ips []string) string { - return strings.Join(ips, ", ") -} - -func formatClusterNames(names map[string]struct{}) string { - var out []string - for k := range names { - out = append(out, k) - } - sort.Strings(out) - return strings.Join(out, ", ") -} - -const ( - synopsis = "Connect to a pod with a proxy and gather upstream services." - help = ` -Usage: consul-k8s troubleshoot upstreams [options] - - Connect to a pod with a proxy and gather upstream services. - - Requires a pod. - - Examples: - $ consul-k8s troubleshoot upstreams -pod pod1 - - where 'pod1' is the pod running a consul proxy -` -) diff --git a/cli/cmd/troubleshoot/upstreams/upstreams_test.go b/cli/cmd/troubleshoot/upstreams/upstreams_test.go deleted file mode 100644 index f5ddefbd28..0000000000 --- a/cli/cmd/troubleshoot/upstreams/upstreams_test.go +++ /dev/null @@ -1,127 +0,0 @@ -package upstreams - -import ( - "bytes" - "context" - "io" - "os" - "testing" - - "github.com/hashicorp/consul-k8s/cli/common" - "github.com/hashicorp/consul-k8s/cli/common/terminal" - "github.com/hashicorp/go-hclog" - "github.com/stretchr/testify/require" - "k8s.io/client-go/kubernetes/fake" -) - -func TestFlagParsing(t *testing.T) { - cases := map[string]struct { - args []string - out int - }{ - "No args, should fail": { - args: []string{}, - out: 1, - }, - "Nonexistent flag passed, -foo bar, should fail": { - args: []string{"-foo", "bar"}, - out: 1, - }, - "Invalid argument passed, -namespace notaname, should fail": { - args: []string{"-namespace", "notaname"}, - out: 1, - }, - } - - for name, tc := range cases { - t.Run(name, func(t *testing.T) { - c := setupCommand(new(bytes.Buffer)) - c.kubernetes = fake.NewSimpleClientset() - out := c.Run(tc.args) - require.Equal(t, tc.out, out) - }) - } -} - -func TestFormatIPs(t *testing.T) { - t.Parallel() - - cases := []struct { - name string - actual []string - expected string - }{ - { - name: "single IPs", - actual: []string{"1.1.1.1"}, - expected: "1.1.1.1", - }, - - { - name: "several IPs", - actual: []string{"1.1.1.1", "2.2.2.2"}, - expected: "1.1.1.1, 2.2.2.2", - }, - } - for _, c := range cases { - t.Run(c.name, func(t *testing.T) { - got := formatIPs(c.actual) - if c.expected != got { - t.Errorf("expected %v, got %v", c.expected, got) - } - }) - } -} - -func TestFormatClusterNames(t *testing.T) { - cases := []struct { - name string - actual map[string]struct{} - expected string - }{ - { - name: "single cluster", - actual: map[string]struct{}{ - "cluster1": {}, - }, - expected: "cluster1", - }, - { - name: "several clusters", - actual: map[string]struct{}{ - "cluster1": {}, - "cluster2": {}, - "cluster3": {}, - }, - expected: "cluster1, cluster2, cluster3", - }, - } - for _, c := range cases { - t.Run(c.name, func(t *testing.T) { - got := formatClusterNames(c.actual) - if c.expected != got { - t.Errorf("expected %v, got %v", c.expected, got) - } - }) - } -} - -func setupCommand(buf io.Writer) *UpstreamsCommand { - // Log at a test level to standard out. - log := hclog.New(&hclog.LoggerOptions{ - Name: "test", - Level: hclog.Debug, - Output: os.Stdout, - }) - - // Setup and initialize the command struct - command := &UpstreamsCommand{ - BaseCommand: &common.BaseCommand{ - Log: log, - UI: terminal.NewUI(context.Background(), buf), - }, - } - command.init() - - return command -} diff --git a/cli/cmd/upgrade/upgrade.go b/cli/cmd/upgrade/upgrade.go index 2672a9f989..4c962c47b5 100644 --- a/cli/cmd/upgrade/upgrade.go +++ b/cli/cmd/upgrade/upgrade.go @@ -17,6 +17,7 @@ import ( "github.com/hashicorp/consul-k8s/cli/helm" "github.com/hashicorp/consul-k8s/cli/preset" "github.com/posener/complete" + helmCLI "helm.sh/helm/v3/pkg/cli" "helm.sh/helm/v3/pkg/cli/values" "helm.sh/helm/v3/pkg/getter" @@ -424,7 +425,7 @@ func (c *Command) validateFlags(args []string) error { return fmt.Errorf("cannot set both -%s and -%s", flagNameConfigFile, flagNamePreset) } if ok := slices.Contains(preset.Presets, c.flagPreset); c.flagPreset != defaultPreset && !ok { - return fmt.Errorf("'%s' is not a valid preset (valid presets: %s)", c.flagPreset, strings.Join(preset.Presets, ", ")) + return fmt.Errorf("'%s' is not a valid preset", c.flagPreset) } if _, err := time.ParseDuration(c.flagTimeout); err != nil { return fmt.Errorf("unable to parse -%s: %s", flagNameTimeout, err) diff --git a/cli/cmd/upgrade/upgrade_test.go b/cli/cmd/upgrade/upgrade_test.go index d21b17febf..809cac1034 100644 --- a/cli/cmd/upgrade/upgrade_test.go +++ b/cli/cmd/upgrade/upgrade_test.go @@ -452,7 +452,7 @@ func TestUpgrade(t *testing.T) { messages: []string{ "\n==> Checking if Consul can be upgraded\n ✓ Existing Consul installation found to be upgraded.\n Name: consul\n Namespace: consul\n", "\n==> Checking if Consul demo application can be upgraded\n No existing Consul demo application installation found.\n", - "\n==> Consul Upgrade Summary\n ✓ Downloaded charts.\n \n Difference between user overrides for current and upgraded charts\n -----------------------------------------------------------------\n + connectInject:\n + enabled: true\n + metrics:\n + defaultEnableMerging: true\n + defaultEnabled: true\n + enableGatewayMetrics: true\n + global:\n + metrics:\n + enableAgentMetrics: true\n + enabled: true\n + name: consul\n + prometheus:\n + enabled: true\n + server:\n + replicas: 1\n + ui:\n + enabled: true\n + service:\n + enabled: true\n \n", + "\n==> Consul Upgrade Summary\n ✓ Downloaded charts.\n \n Difference between user overrides for current and upgraded charts\n -----------------------------------------------------------------\n + connectInject:\n + enabled: true\n + metrics:\n + defaultEnableMerging: true\n + defaultEnabled: true\n + enableGatewayMetrics: true\n + controller:\n + enabled: true\n + global:\n + metrics:\n + enableAgentMetrics: true\n + enabled: true\n + name: consul\n + prometheus:\n + enabled: true\n + server:\n + replicas: 1\n + ui:\n + enabled: true\n + service:\n + enabled: true\n \n", "\n==> Upgrading Consul\n ✓ Consul upgraded in namespace \"consul\".\n", }, helmActionsRunner: &helm.MockActionRunner{ @@ -477,7 +477,7 @@ func TestUpgrade(t *testing.T) { messages: []string{ "\n==> Checking if Consul can be upgraded\n ✓ Existing Consul installation found to be upgraded.\n Name: consul\n Namespace: consul\n", "\n==> Checking if Consul demo application can be upgraded\n No existing Consul demo application installation found.\n", - "\n==> Consul Upgrade Summary\n ✓ Downloaded charts.\n \n Difference between user overrides for current and upgraded charts\n -----------------------------------------------------------------\n + connectInject:\n + enabled: true\n + global:\n + acls:\n + manageSystemACLs: true\n + gossipEncryption:\n + autoGenerate: true\n + name: consul\n + tls:\n + enableAutoEncrypt: true\n + enabled: true\n + server:\n + replicas: 1\n \n", + "\n==> Consul Upgrade Summary\n ✓ Downloaded charts.\n \n Difference between user overrides for current and upgraded charts\n -----------------------------------------------------------------\n + connectInject:\n + enabled: true\n + controller:\n + enabled: true\n + global:\n + acls:\n + manageSystemACLs: true\n + gossipEncryption:\n + autoGenerate: true\n + name: consul\n + tls:\n + enableAutoEncrypt: true\n + enabled: true\n + server:\n + replicas: 1\n \n", "\n==> Upgrading Consul\n ✓ Consul upgraded in namespace \"consul\".\n", }, helmActionsRunner: &helm.MockActionRunner{ diff --git a/cli/commands.go b/cli/commands.go index fe4c47400e..d29b4a8ad7 100644 --- a/cli/commands.go +++ b/cli/commands.go @@ -6,12 +6,8 @@ import ( "github.com/hashicorp/consul-k8s/cli/cmd/install" "github.com/hashicorp/consul-k8s/cli/cmd/proxy" "github.com/hashicorp/consul-k8s/cli/cmd/proxy/list" - "github.com/hashicorp/consul-k8s/cli/cmd/proxy/loglevel" "github.com/hashicorp/consul-k8s/cli/cmd/proxy/read" "github.com/hashicorp/consul-k8s/cli/cmd/status" - "github.com/hashicorp/consul-k8s/cli/cmd/troubleshoot" - troubleshoot_proxy "github.com/hashicorp/consul-k8s/cli/cmd/troubleshoot/proxy" - "github.com/hashicorp/consul-k8s/cli/cmd/troubleshoot/upstreams" "github.com/hashicorp/consul-k8s/cli/cmd/uninstall" "github.com/hashicorp/consul-k8s/cli/cmd/upgrade" cmdversion "github.com/hashicorp/consul-k8s/cli/cmd/version" @@ -23,6 +19,7 @@ import ( ) func initializeCommands(ctx context.Context, log hclog.Logger) (*common.BaseCommand, map[string]cli.CommandFactory) { + baseCommand := &common.BaseCommand{ Ctx: ctx, Log: log, @@ -66,31 +63,11 @@ func initializeCommands(ctx context.Context, log hclog.Logger) (*common.BaseComm BaseCommand: baseCommand, }, nil }, - "proxy log": func() (cli.Command, error) { - return &loglevel.LogLevelCommand{ - BaseCommand: baseCommand, - }, nil - }, "proxy read": func() (cli.Command, error) { return &read.ReadCommand{ BaseCommand: baseCommand, }, nil }, - "troubleshoot": func() (cli.Command, error) { - return &troubleshoot.TroubleshootCommand{ - BaseCommand: baseCommand, - }, nil - }, - "troubleshoot proxy": func() (cli.Command, error) { - return &troubleshoot_proxy.ProxyCommand{ - BaseCommand: baseCommand, - }, nil - }, - "troubleshoot upstreams": func() (cli.Command, error) { - return &upstreams.UpstreamsCommand{ - BaseCommand: baseCommand, - }, nil - }, } return baseCommand, commands diff --git a/cli/common/envoy/logger_params.go b/cli/common/envoy/logger_params.go deleted file mode 100644 index b2eff623c0..0000000000 --- a/cli/common/envoy/logger_params.go +++ /dev/null @@ -1,166 +0,0 @@ -package envoy - -import ( - "fmt" - "strings" -) - -type logLevel struct { - name string - level string -} - -type LoggerParams struct { - globalLevel string - individualLevels []logLevel -} - -func NewLoggerParams() *LoggerParams { - return &LoggerParams{ - individualLevels: make([]logLevel, 0), - } -} - -func (l *LoggerParams) SetLoggerLevel(name, level string) error { - err := validateLoggerName(name) - if err != nil { - return err - } - err = validateLogLevel(level) - if err != nil { - return err - } - - l.individualLevels = append(l.individualLevels, logLevel{name: name, level: level}) - return nil -} - -func (l *LoggerParams) SetGlobalLoggerLevel(level string) error { - err := validateLogLevel(level) - if err != nil { - return err - } - l.globalLevel = level - return nil -} - -func validateLogLevel(level string) error { - if _, ok := envoyLevels[level]; !ok { - logLevels := []string{} - for levelName := range envoyLevels { - logLevels = append(logLevels, levelName) - } - return fmt.Errorf("Unknown log level %s, available log levels are %q", level, strings.Join(logLevels, ", ")) - } - return nil -} - -func validateLoggerName(name string) error { - if _, ok := EnvoyLoggers[name]; !ok { - loggers := []string{} - for loggerName := range envoyLevels { - loggers = append(loggers, loggerName) - } - return fmt.Errorf("Unknown logger %s, available loggers are %q", name, strings.Join(loggers, ", ")) - - } - return nil -} - -func (l *LoggerParams) String() string { - switch { - // Global log level change is set - case l.globalLevel != "": - return fmt.Sprintf("?level=%s", l.globalLevel) - - // only one specific logger is changed - case len(l.individualLevels) == 1: - params := fmt.Sprintf("?%s=%s", l.individualLevels[0].name, l.individualLevels[0].level) - return params - - // multiple specific loggers are changed - case len(l.individualLevels) > 1: - logParams := make([]string, 0, len(l.individualLevels)) - for _, logger := range l.individualLevels { - logParams = append(logParams, fmt.Sprintf("%s:%s", logger.name, logger.level)) - } - - params := fmt.Sprintf("?paths=%s", strings.Join(logParams, ",")) - return params - default: - - // default path, this is hit if there are no params - return "" - } -} - -// trace debug info warning error critical off. -var envoyLevels = map[string]struct{}{ - "trace": {}, - "debug": {}, - "info": {}, - "warning": {}, - "error": {}, - "critical": {}, - "off": {}, -} - -var EnvoyLoggers = map[string]struct{}{ - "admin": {}, - "alternate_protocols_cache": {}, - "aws": {}, - "assert": {}, - "backtrace": {}, - "cache_filter": {}, - "client": {}, - "config": {}, - "connection": {}, - "conn_handler": {}, - "decompression": {}, - "dns": {}, - "dubbo": {}, - "envoy_bug": {}, - "ext_authz": {}, - "ext_proc": {}, - "rocketmq": {}, - "file": {}, - "filter": {}, - "forward_proxy": {}, - "grpc": {}, - "happy_eyeballs": {}, - "hc": {}, - "health_checker": {}, - "http": {}, - "http2": {}, - "hystrix": {}, - "init": {}, - "io": {}, - "jwt": {}, - "kafka": {}, - "key_value_store": {}, - "lua": {}, - "main": {}, - "matcher": {}, - "misc": {}, - "mongo": {}, - "multi_connection": {}, - "oauth2": {}, - "quic": {}, - "quic_stream": {}, - "pool": {}, - "rbac": {}, - "rds": {}, - "redis": {}, - "router": {}, - "runtime": {}, - "stats": {}, - "secret": {}, - "tap": {}, - "testing": {}, - "thrift": {}, - "tracing": {}, - "upstream": {}, - "udp": {}, - "wasm": {}, - "websocket": {}, -} diff --git a/cli/common/envoy/logger_params_test.go b/cli/common/envoy/logger_params_test.go deleted file mode 100644 index 26be9f69a6..0000000000 --- a/cli/common/envoy/logger_params_test.go +++ /dev/null @@ -1,172 +0,0 @@ -package envoy - -import ( - "testing" - - "github.com/stretchr/testify/require" -) - -func TestSetLoggerLevelSucceeds(t *testing.T) { - t.Parallel() - testCases := map[string]struct { - levelsToSet [][]string - expectedIndividualLevels []logLevel - }{ - "single log level change trace": { - levelsToSet: [][]string{ - {"admin", "trace"}, - }, - expectedIndividualLevels: []logLevel{ - {name: "admin", level: "trace"}, - }, - }, - "single log level change debug": { - levelsToSet: [][]string{ - {"admin", "debug"}, - }, - expectedIndividualLevels: []logLevel{ - {name: "admin", level: "debug"}, - }, - }, - "single log level change info": { - levelsToSet: [][]string{ - {"admin", "info"}, - }, - expectedIndividualLevels: []logLevel{ - {name: "admin", level: "info"}, - }, - }, - "single log level change warning": { - levelsToSet: [][]string{ - {"admin", "warning"}, - }, - expectedIndividualLevels: []logLevel{ - {name: "admin", level: "warning"}, - }, - }, - "single log level change error": { - levelsToSet: [][]string{ - {"admin", "error"}, - }, - expectedIndividualLevels: []logLevel{ - {name: "admin", level: "error"}, - }, - }, - "single log level change critical": { - levelsToSet: [][]string{ - {"admin", "critical"}, - }, - expectedIndividualLevels: []logLevel{ - {name: "admin", level: "critical"}, - }, - }, - "single log level change off": { - levelsToSet: [][]string{ - {"admin", "off"}, - }, - expectedIndividualLevels: []logLevel{ - {name: "admin", level: "off"}, - }, - }, - "multiple log level change": { - levelsToSet: [][]string{ - {"admin", "info"}, - {"grpc", "debug"}, - }, - expectedIndividualLevels: []logLevel{ - {name: "admin", level: "info"}, - {name: "grpc", level: "debug"}, - }, - }, - } - - for name, tc := range testCases { - t.Run(name, func(t *testing.T) { - loggerParams := NewLoggerParams() - for _, loggerLevel := range tc.levelsToSet { - logger, level := loggerLevel[0], loggerLevel[1] - err := loggerParams.SetLoggerLevel(logger, level) - require.NoError(t, err) - } - require.Equal(t, loggerParams.individualLevels, tc.expectedIndividualLevels) - }) - } -} - -func TestSetLoggerLevelFails(t *testing.T) { - t.Parallel() - testCases := map[string]struct { - loggerName string - loggerLevel string - }{ - "invalid logger name": { - loggerName: "this is not the logger you're looking for", - loggerLevel: "info", - }, - "invalid logger level": { - loggerName: "grpc", - loggerLevel: "this is also incorrect", - }, - } - - for name, tc := range testCases { - t.Run(name, func(t *testing.T) { - loggerParams := NewLoggerParams() - err := loggerParams.SetLoggerLevel(tc.loggerName, tc.loggerLevel) - require.Error(t, err) - }) - } -} - -func TestSetGlobalLoggerLevel(t *testing.T) { - t.Parallel() - for level := range envoyLevels { - loggerParams := NewLoggerParams() - err := loggerParams.SetGlobalLoggerLevel(level) - require.NoError(t, err) - } -} - -func TestSetGlobalLoggerLevelFails(t *testing.T) { - t.Parallel() - loggerParams := NewLoggerParams() - err := loggerParams.SetGlobalLoggerLevel("not a valid level") - require.Error(t, err) -} - -func TestString(t *testing.T) { - t.Parallel() - testCases := map[string]struct { - subject *LoggerParams - expectedOutput string - }{ - "when global level is set": { - subject: &LoggerParams{globalLevel: "warn"}, - expectedOutput: "?level=warn", - }, - "when one specific log level is set": { - subject: &LoggerParams{ - individualLevels: []logLevel{ - {name: "grpc", level: "warn"}, - }, - }, - expectedOutput: "?grpc=warn", - }, - "when multiple specific log levels are set": { - subject: &LoggerParams{ - individualLevels: []logLevel{ - {name: "grpc", level: "warn"}, - {name: "http", level: "info"}, - }, - }, - expectedOutput: "?paths=grpc:warn,http:info", - }, - } - - for name, tc := range testCases { - t.Run(name, func(t *testing.T) { - actual := tc.subject.String() - require.Equal(t, actual, tc.expectedOutput) - }) - } -} diff --git a/cli/common/envoy/testdata/fetch_debug_levels.txt b/cli/common/envoy/testdata/fetch_debug_levels.txt deleted file mode 100644 index 6b059dc1aa..0000000000 --- a/cli/common/envoy/testdata/fetch_debug_levels.txt +++ /dev/null @@ -1,59 +0,0 @@ -active loggers: - admin: debug - alternate_protocols_cache: debug - aws: debug - assert: debug - backtrace: debug - cache_filter: debug - client: debug - config: debug - connection: debug - conn_handler: debug - decompression: debug - dns: debug - dubbo: debug - envoy_bug: debug - ext_authz: debug - ext_proc: debug - rocketmq: debug - file: debug - filter: debug - forward_proxy: debug - grpc: debug - happy_eyeballs: debug - hc: debug - health_checker: debug - http: debug - http2: debug - hystrix: debug - init: debug - io: debug - jwt: debug - kafka: debug - key_value_store: debug - lua: debug - main: debug - matcher: debug - misc: debug - mongo: debug - multi_connection: debug - oauth2: debug - quic: debug - quic_stream: debug - pool: debug - rbac: debug - rds: debug - redis: debug - router: debug - runtime: debug - stats: debug - secret: debug - tap: debug - testing: debug - thrift: debug - tracing: debug - upstream: debug - udp: debug - wasm: debug - websocket: debug - diff --git a/cli/common/terminal/table.go b/cli/common/terminal/table.go index ac9a762609..67278931a4 100644 --- a/cli/common/terminal/table.go +++ b/cli/common/terminal/table.go @@ -5,21 +5,15 @@ import ( ) const ( - Yellow = "yellow" - Green = "green" - Red = "red" - Blue = "blue" - Magenta = "magenta" - HiWhite = "hiwhite" + Yellow = "yellow" + Green = "green" + Red = "red" ) var colorMapping = map[string]int{ - Green: tablewriter.FgGreenColor, - Yellow: tablewriter.FgYellowColor, - Red: tablewriter.FgRedColor, - Blue: tablewriter.FgBlueColor, - Magenta: tablewriter.FgMagentaColor, - HiWhite: tablewriter.FgHiWhiteColor, + Green: tablewriter.FgGreenColor, + Yellow: tablewriter.FgYellowColor, + Red: tablewriter.FgRedColor, } // Passed to UI.Table to provide a nicely formatted table. diff --git a/cli/go.mod b/cli/go.mod index adc0309466..7a05de4ef2 100644 --- a/cli/go.mod +++ b/cli/go.mod @@ -1,6 +1,6 @@ module github.com/hashicorp/consul-k8s/cli -go 1.20 +go 1.19 require ( github.com/bgentry/speakeasy v0.1.0 @@ -8,16 +8,15 @@ require ( github.com/fatih/color v1.13.0 github.com/google/go-cmp v0.5.8 github.com/hashicorp/consul-k8s/charts v0.0.0-00010101000000-000000000000 - github.com/hashicorp/consul/troubleshoot v0.1.2 - github.com/hashicorp/go-hclog v1.2.1 + github.com/hashicorp/go-hclog v0.16.2 github.com/hashicorp/hcp-sdk-go v0.23.1-0.20220921131124-49168300a7dc github.com/kr/text v0.2.0 - github.com/mattn/go-isatty v0.0.16 + github.com/mattn/go-isatty v0.0.14 github.com/mitchellh/cli v1.1.2 github.com/olekukonko/tablewriter v0.0.5 github.com/posener/complete v1.2.3 - github.com/stretchr/testify v1.8.0 - golang.org/x/text v0.5.0 + github.com/stretchr/testify v1.7.2 + golang.org/x/text v0.7.0 helm.sh/helm/v3 v3.9.4 k8s.io/api v0.25.0 k8s.io/apiextensions-apiserver v0.25.0 @@ -28,8 +27,6 @@ require ( sigs.k8s.io/yaml v1.3.0 ) -require go.opentelemetry.io/proto/otlp v0.11.0 // indirect - require ( cloud.google.com/go v0.99.0 // indirect github.com/Azure/go-ansiterm v0.0.0-20210617225240-d185dfc1b5a1 // indirect @@ -49,17 +46,14 @@ require ( github.com/Masterminds/squirrel v1.5.3 // indirect github.com/PuerkitoBio/purell v1.1.1 // indirect github.com/PuerkitoBio/urlesc v0.0.0-20170810143723-de5bf2ad4578 // indirect - github.com/armon/go-metrics v0.3.10 // indirect github.com/armon/go-radix v1.0.0 // indirect - github.com/asaskevich/govalidator v0.0.0-20210307081110-f21760c49a8d // indirect + github.com/asaskevich/govalidator v0.0.0-20200907205600-7a23bdc65eef // indirect github.com/beorn7/perks v1.0.1 // indirect - github.com/census-instrumentation/opencensus-proto v0.3.0 // indirect github.com/cespare/xxhash/v2 v2.1.2 // indirect github.com/chai2010/gettext-go v0.0.0-20160711120539-c6fed771bfd5 // indirect - github.com/cncf/xds/go v0.0.0-20220314180256-7f1daf1720fc // indirect github.com/containerd/containerd v1.6.6 // indirect github.com/cyphar/filepath-securejoin v0.2.3 // indirect - github.com/davecgh/go-spew v1.1.2-0.20180830191138-d8f796af33cc // indirect + github.com/davecgh/go-spew v1.1.1 // indirect github.com/docker/cli v20.10.17+incompatible // indirect github.com/docker/distribution v2.8.1+incompatible // indirect github.com/docker/docker v20.10.17+incompatible // indirect @@ -68,25 +62,24 @@ require ( github.com/docker/go-metrics v0.0.1 // indirect github.com/docker/go-units v0.4.0 // indirect github.com/emicklei/go-restful/v3 v3.8.0 // indirect - github.com/envoyproxy/go-control-plane v0.10.2-0.20220325020618-49ff273808a1 // indirect - github.com/envoyproxy/protoc-gen-validate v0.9.1 // indirect github.com/evanphx/json-patch v4.12.0+incompatible // indirect github.com/exponent-io/jsonpath v0.0.0-20151013193312-d6023ce2651d // indirect github.com/fsnotify/fsnotify v1.5.4 // indirect github.com/go-errors/errors v1.0.1 // indirect - github.com/go-gorp/gorp/v3 v3.1.0 // indirect + github.com/go-gorp/gorp/v3 v3.0.2 // indirect github.com/go-logr/logr v1.2.3 // indirect - github.com/go-openapi/analysis v0.21.2 // indirect + github.com/go-openapi/analysis v0.20.0 // indirect github.com/go-openapi/errors v0.20.2 // indirect github.com/go-openapi/jsonpointer v0.19.5 // indirect - github.com/go-openapi/jsonreference v0.19.6 // indirect - github.com/go-openapi/loads v0.21.1 // indirect - github.com/go-openapi/runtime v0.24.1 // indirect - github.com/go-openapi/spec v0.20.4 // indirect - github.com/go-openapi/strfmt v0.21.3 // indirect - github.com/go-openapi/swag v0.21.1 // indirect - github.com/go-openapi/validate v0.21.0 // indirect + github.com/go-openapi/jsonreference v0.19.5 // indirect + github.com/go-openapi/loads v0.20.2 // indirect + github.com/go-openapi/runtime v0.19.24 // indirect + github.com/go-openapi/spec v0.20.3 // indirect + github.com/go-openapi/strfmt v0.20.0 // indirect + github.com/go-openapi/swag v0.19.14 // indirect + github.com/go-openapi/validate v0.20.2 // indirect github.com/go-ozzo/ozzo-validation v3.6.0+incompatible // indirect + github.com/go-stack/stack v1.8.0 // indirect github.com/gobwas/glob v0.2.3 // indirect github.com/gogo/protobuf v1.3.2 // indirect github.com/golang-jwt/jwt/v4 v4.2.0 // indirect @@ -95,22 +88,15 @@ require ( github.com/google/gnostic v0.5.7-v3refs // indirect github.com/google/gofuzz v1.2.0 // indirect github.com/google/shlex v0.0.0-20191202100458-e7afc7fbc510 // indirect - github.com/google/uuid v1.3.0 // indirect + github.com/google/uuid v1.2.0 // indirect github.com/gorilla/mux v1.8.0 // indirect github.com/gosuri/uitable v0.0.4 // indirect github.com/gregjones/httpcache v0.0.0-20180305231024-9cad4c3443a7 // indirect - github.com/hashicorp/consul/api v1.20.0 // indirect - github.com/hashicorp/consul/envoyextensions v0.1.2 // indirect github.com/hashicorp/errwrap v1.1.0 // indirect - github.com/hashicorp/go-cleanhttp v0.5.2 // indirect - github.com/hashicorp/go-immutable-radix v1.3.1 // indirect + github.com/hashicorp/go-cleanhttp v0.5.1 // indirect github.com/hashicorp/go-multierror v1.1.1 // indirect - github.com/hashicorp/go-rootcerts v1.0.2 // indirect - github.com/hashicorp/go-version v1.2.1 // indirect - github.com/hashicorp/golang-lru v0.5.4 // indirect - github.com/hashicorp/serf v0.10.1 // indirect github.com/huandu/xstrings v1.3.2 // indirect - github.com/imdario/mergo v0.3.13 // indirect + github.com/imdario/mergo v0.3.12 // indirect github.com/inconshreveable/mousetrap v1.0.0 // indirect github.com/jmoiron/sqlx v1.3.5 // indirect github.com/josharian/intern v1.0.0 // indirect @@ -118,17 +104,16 @@ require ( github.com/klauspost/compress v1.13.6 // indirect github.com/lann/builder v0.0.0-20180802200727-47ae307949d0 // indirect github.com/lann/ps v0.0.0-20150810152359-62de8c46ede0 // indirect - github.com/lib/pq v1.10.7 // indirect + github.com/lib/pq v1.10.6 // indirect github.com/liggitt/tabwriter v0.0.0-20181228230101-89fcab3d43de // indirect - github.com/mailru/easyjson v0.7.7 // indirect - github.com/mattn/go-colorable v0.1.13 // indirect + github.com/mailru/easyjson v0.7.6 // indirect + github.com/mattn/go-colorable v0.1.12 // indirect github.com/mattn/go-runewidth v0.0.9 // indirect github.com/matttproud/golang_protobuf_extensions v1.0.2-0.20181231171920-c182affec369 // indirect github.com/mitchellh/colorstring v0.0.0-20190213212951-d06e56a500db // indirect github.com/mitchellh/copystructure v1.2.0 // indirect - github.com/mitchellh/go-homedir v1.1.0 // indirect github.com/mitchellh/go-wordwrap v1.0.1 // indirect - github.com/mitchellh/mapstructure v1.5.0 // indirect + github.com/mitchellh/mapstructure v1.4.1 // indirect github.com/mitchellh/reflectwalk v1.0.2 // indirect github.com/moby/locker v1.0.1 // indirect github.com/moby/spdystream v0.2.0 // indirect @@ -138,14 +123,12 @@ require ( github.com/monochromegane/go-gitignore v0.0.0-20200626010858-205db1a8cc00 // indirect github.com/morikuni/aec v1.0.0 // indirect github.com/munnerz/goautoneg v0.0.0-20191010083416-a7dc8b61c822 // indirect - github.com/oklog/ulid v1.3.1 // indirect github.com/onsi/ginkgo v1.16.5 // indirect github.com/opencontainers/go-digest v1.0.0 // indirect github.com/opencontainers/image-spec v1.0.3-0.20211202183452-c5a74bcca799 // indirect - github.com/opentracing/opentracing-go v1.2.0 // indirect github.com/peterbourgon/diskv v2.0.1+incompatible // indirect github.com/pkg/errors v0.9.1 // indirect - github.com/pmezard/go-difflib v1.0.1-0.20181226105442-5d4384ee4fb2 // indirect + github.com/pmezard/go-difflib v1.0.0 // indirect github.com/prometheus/client_golang v1.12.2 // indirect github.com/prometheus/client_model v0.2.0 // indirect github.com/prometheus/common v0.32.1 // indirect @@ -162,19 +145,19 @@ require ( github.com/xeipuuv/gojsonreference v0.0.0-20180127040603-bd5ef7bd5415 // indirect github.com/xeipuuv/gojsonschema v1.2.0 // indirect github.com/xlab/treeprint v0.0.0-20181112141820-a009c3971eca // indirect - go.mongodb.org/mongo-driver v1.11.1 // indirect - go.starlark.net v0.0.0-20230128213706-3f75dec8e403 // indirect - golang.org/x/crypto v0.0.0-20220622213112-05595931fe9d // indirect - golang.org/x/net v0.4.0 // indirect - golang.org/x/oauth2 v0.0.0-20220909003341-f21342109be1 // indirect + go.mongodb.org/mongo-driver v1.4.6 // indirect + go.starlark.net v0.0.0-20200707032745-474f21a9602d // indirect + golang.org/x/crypto v0.0.0-20220525230936-793ad666bf5e // indirect + golang.org/x/net v0.7.0 // indirect + golang.org/x/oauth2 v0.0.0-20211104180415-d3ed0bb246c8 // indirect golang.org/x/sync v0.0.0-20220722155255-886fb9371eb4 // indirect - golang.org/x/sys v0.3.0 // indirect - golang.org/x/term v0.3.0 // indirect + golang.org/x/sys v0.5.0 // indirect + golang.org/x/term v0.5.0 // indirect golang.org/x/time v0.0.0-20220609170525-579cf78fd858 // indirect google.golang.org/appengine v1.6.7 // indirect - google.golang.org/genproto v0.0.0-20220921223823-23cae91e6737 // indirect - google.golang.org/grpc v1.49.0 // indirect - google.golang.org/protobuf v1.28.1 // indirect + google.golang.org/genproto v0.0.0-20220502173005-c8bf987b8c21 // indirect + google.golang.org/grpc v1.47.0 // indirect + google.golang.org/protobuf v1.28.0 // indirect gopkg.in/inf.v0 v0.9.1 // indirect gopkg.in/yaml.v2 v2.4.0 // indirect gopkg.in/yaml.v3 v3.0.1 // indirect diff --git a/cli/go.sum b/cli/go.sum index 6ba77d4281..2dea354c17 100644 --- a/cli/go.sum +++ b/cli/go.sum @@ -71,7 +71,6 @@ github.com/BurntSushi/toml v1.0.0 h1:dtDWrepsVPfW9H/4y7dDgFc2MBUSeJhlaDtK13CxFlU github.com/BurntSushi/toml v1.0.0/go.mod h1:CxXYINrC8qIiEnFrOxCa7Jy5BFHlXnUU2pbicEuybxQ= github.com/BurntSushi/xgb v0.0.0-20160522181843-27f122750802/go.mod h1:IVnqGOEym/WlBOVXweHU+Q+/VP0lqqI8lqeDx9IjBqo= github.com/DATA-DOG/go-sqlmock v1.5.0 h1:Shsta01QNfFxHCfpW6YH2STWB0MudeXXEWMr20OEh60= -github.com/DataDog/datadog-go v3.2.0+incompatible/go.mod h1:LButxg5PwREeZtORoXG3tL4fMGNddJ+vMq1mwgfaqoQ= github.com/MakeNowJust/heredoc v0.0.0-20170808103936-bb23615498cd h1:sjQovDkwrZp8u+gxLtPgKGjk5hCxuy2hrRejBTA9xFU= github.com/MakeNowJust/heredoc v0.0.0-20170808103936-bb23615498cd/go.mod h1:64YHyfSL2R96J44Nlwm39UHepQbyR5q10x7iYa1ks2E= github.com/Masterminds/goutils v1.1.0/go.mod h1:8cTjp+g8YejhMuvIA5y2vz3BpJxksy863GQaJW2MFNU= @@ -91,30 +90,34 @@ github.com/Microsoft/go-winio v0.5.1 h1:aPJp2QD7OOrhO5tQXqQoGSJc+DjDtWTGLOmNyAm6 github.com/Microsoft/hcsshim v0.9.3 h1:k371PzBuRrz2b+ebGuI2nVgVhgsVX60jMfSw80NECxo= github.com/NYTimes/gziphandler v0.0.0-20170623195520-56545f4a5d46/go.mod h1:3wb06e3pkSAbeQ52E9H9iFoQsEEwGN64994WTCIhntQ= github.com/OneOfOne/xxhash v1.2.2/go.mod h1:HSdplMjZKSmBqAxg5vPj2TmRDmfkzw+cTzAElWljhcU= +github.com/PuerkitoBio/purell v1.1.0/go.mod h1:c11w/QuzBsJSee3cPx9rAFu61PvFxuPbtSwDGJws/X0= github.com/PuerkitoBio/purell v1.1.1 h1:WEQqlqaGbrPkxLJWfBwQmfEAE1Z7ONdDLqrN38tNFfI= github.com/PuerkitoBio/purell v1.1.1/go.mod h1:c11w/QuzBsJSee3cPx9rAFu61PvFxuPbtSwDGJws/X0= github.com/PuerkitoBio/urlesc v0.0.0-20170810143723-de5bf2ad4578 h1:d+Bc7a5rLufV/sSk/8dngufqelfh6jnri85riMAaF/M= github.com/PuerkitoBio/urlesc v0.0.0-20170810143723-de5bf2ad4578/go.mod h1:uGdkoq3SwY9Y+13GIhn11/XLaGBb4BfwItxLd5jeuXE= github.com/Shopify/logrus-bugsnag v0.0.0-20171204204709-577dee27f20d h1:UrqY+r/OJnIp5u0s1SbQ8dVfLCZJsnvazdBP5hS4iRs= +github.com/agnivade/levenshtein v1.0.1/go.mod h1:CURSv5d9Uaml+FovSIICkLbAUZ9S4RqaHDIsdSBg7lM= github.com/alecthomas/template v0.0.0-20160405071501-a0175ee3bccc/go.mod h1:LOuyumcjzFXgccqObfd/Ljyb9UuFJ6TxHnclSeseNhc= github.com/alecthomas/template v0.0.0-20190718012654-fb15b899a751/go.mod h1:LOuyumcjzFXgccqObfd/Ljyb9UuFJ6TxHnclSeseNhc= github.com/alecthomas/units v0.0.0-20151022065526-2efee857e7cf/go.mod h1:ybxpYRFXyAe+OPACYpWeL0wqObRcbAqCMya13uyzqw0= github.com/alecthomas/units v0.0.0-20190717042225-c3de453c63f4/go.mod h1:ybxpYRFXyAe+OPACYpWeL0wqObRcbAqCMya13uyzqw0= github.com/alecthomas/units v0.0.0-20190924025748-f65c72e2690d/go.mod h1:rBZYJk541a8SKzHPHnH3zbiI+7dagKZ0cgpgrD7Fyho= +github.com/andreyvit/diff v0.0.0-20170406064948-c7f18ee00883/go.mod h1:rCTlJbsFo29Kk6CurOXKm700vrz8f0KW0JNfpkRJY/8= github.com/antihax/optional v1.0.0/go.mod h1:uupD/76wgC+ih3iEmQUL+0Ugr19nfwCT1kdvxnR2qWY= github.com/armon/circbuf v0.0.0-20150827004946-bbbad097214e/go.mod h1:3U/XgcO3hCbHZ8TKRvWD2dDTCfh9M9ya+I9JpbB7O8o= github.com/armon/go-metrics v0.0.0-20180917152333-f0300d1749da/go.mod h1:Q73ZrmVTwzkszR9V5SSuryQ31EELlFMUz1kKyl939pY= -github.com/armon/go-metrics v0.3.10 h1:FR+drcQStOe+32sYyJYyZ7FIdgoGGBnwLl+flodp8Uo= -github.com/armon/go-metrics v0.3.10/go.mod h1:4O98XIr/9W0sxpJ8UaYkvjk10Iff7SnFrb4QAOwNTFc= github.com/armon/go-radix v0.0.0-20180808171621-7fddfc383310/go.mod h1:ufUuZ+zHj4x4TnLV4JWEpy2hxWSpsRywHrMgIH9cCH8= github.com/armon/go-radix v1.0.0 h1:F4z6KzEeeQIMeLFa97iZU6vupzoecKdU5TX24SNppXI= github.com/armon/go-radix v1.0.0/go.mod h1:ufUuZ+zHj4x4TnLV4JWEpy2hxWSpsRywHrMgIH9cCH8= github.com/armon/go-socks5 v0.0.0-20160902184237-e75332964ef5 h1:0CwZNZbxp69SHPdPJAN/hZIm0C4OItdklCFmMRWYpio= github.com/armon/go-socks5 v0.0.0-20160902184237-e75332964ef5/go.mod h1:wHh0iHkYZB8zMSxRWpUBQtwG5a7fFgvEO+odwuTv2gs= +github.com/asaskevich/govalidator v0.0.0-20180720115003-f9ffefc3facf/go.mod h1:lB+ZfQJz7igIIfQNfa7Ml4HSf2uFQQRzpGGRXenZAgY= github.com/asaskevich/govalidator v0.0.0-20190424111038-f61b66f89f4a/go.mod h1:lB+ZfQJz7igIIfQNfa7Ml4HSf2uFQQRzpGGRXenZAgY= +github.com/asaskevich/govalidator v0.0.0-20200108200545-475eaeb16496/go.mod h1:oGkLhpf+kjZl6xBf758TQhh5XrAeiJv/7FRz/2spLIg= +github.com/asaskevich/govalidator v0.0.0-20200428143746-21a406dcc535/go.mod h1:oGkLhpf+kjZl6xBf758TQhh5XrAeiJv/7FRz/2spLIg= +github.com/asaskevich/govalidator v0.0.0-20200907205600-7a23bdc65eef h1:46PFijGLmAjMPwCCCo7Jf0W6f9slllCkkv7vyc1yOSg= github.com/asaskevich/govalidator v0.0.0-20200907205600-7a23bdc65eef/go.mod h1:WaHUgvxTVq04UNunO+XhnAqY/wQc+bxr74GqbsZ/Jqw= -github.com/asaskevich/govalidator v0.0.0-20210307081110-f21760c49a8d h1:Byv0BzEl3/e6D5CLfI0j/7hiIEtvGVFPCZ7Ei2oq8iQ= -github.com/asaskevich/govalidator v0.0.0-20210307081110-f21760c49a8d/go.mod h1:WaHUgvxTVq04UNunO+XhnAqY/wQc+bxr74GqbsZ/Jqw= +github.com/aws/aws-sdk-go v1.34.28/go.mod h1:H7NKnBqNVzoTJpGfLrQkkD+ytBA93eiDYi/+8rV9s48= github.com/benbjohnson/clock v1.0.3/go.mod h1:bGMdMPoPVvcYyt1gHDf4J2KE153Yf9BuiUKYMaxlTDM= github.com/benbjohnson/clock v1.1.0/go.mod h1:J11/hYXuz8f4ySSvYwY0FKfm+ezbsZBKZxNJlLklBHA= github.com/beorn7/perks v0.0.0-20180321164747-3a771d992973/go.mod h1:Dwedo/Wpr24TaqPxmxbtue+5NUziq4I4S80YR8gNf3Q= @@ -132,8 +135,6 @@ github.com/bugsnag/panicwrap v0.0.0-20151223152923-e2c28503fcd0 h1:nvj0OLI3YqYXe github.com/cenkalti/backoff v2.2.1+incompatible h1:tNowT99t7UNflLxfYYSlKYsBpXdEet03Pg2g16Swow4= github.com/cenkalti/backoff v2.2.1+incompatible/go.mod h1:90ReRw6GdpyfrHakVjL/QHaoyV4aDUVVkXQJJJ3NXXM= github.com/census-instrumentation/opencensus-proto v0.2.1/go.mod h1:f6KPmirojxKA12rnyqOA5BBL4O983OfeGPqjHWSTneU= -github.com/census-instrumentation/opencensus-proto v0.3.0 h1:t/LhUZLVitR1Ow2YOnduCsavhwFUklBMoGVYUCqmCqk= -github.com/census-instrumentation/opencensus-proto v0.3.0/go.mod h1:f6KPmirojxKA12rnyqOA5BBL4O983OfeGPqjHWSTneU= github.com/cespare/xxhash v1.1.0/go.mod h1:XrSqR1VqqWfGrhpAt58auRo0WTKS1nRRg3ghfAqPWnc= github.com/cespare/xxhash/v2 v2.1.1/go.mod h1:VGX0DQ3Q6kWi7AoAeZDth3/j3BFtOZR5XLFGgcrjCOs= github.com/cespare/xxhash/v2 v2.1.2 h1:YRXhKfTDauu4ajMg1TPgFO5jnlC2HCbmLXMcTG5cbYE= @@ -143,20 +144,15 @@ github.com/chai2010/gettext-go v0.0.0-20160711120539-c6fed771bfd5/go.mod h1:/iP1 github.com/chzyer/logex v1.1.10/go.mod h1:+Ywpsq7O8HXn0nuIou7OrIPyXbp3wmkHB+jjWRnGsAI= github.com/chzyer/readline v0.0.0-20180603132655-2972be24d48e/go.mod h1:nSuG5e5PlCu98SY8svDHJxuZscDgtXS6KTTbou5AhLI= github.com/chzyer/test v0.0.0-20180213035817-a1ea475d72b1/go.mod h1:Q3SI9o4m/ZMnBNeIyt5eFwwo7qiLfzFZmjNmxjkiQlU= -github.com/circonus-labs/circonus-gometrics v2.3.1+incompatible/go.mod h1:nmEj6Dob7S7YxXgwXpfOuvO54S+tGdZdw9fuRZt25Ag= -github.com/circonus-labs/circonusllhist v0.1.3/go.mod h1:kMXHVDlOchFAehlya5ePtbp5jckzBHf4XRpQvBOLI+I= github.com/client9/misspell v0.3.4/go.mod h1:qj6jICC3Q7zFZvVWo7KLAzC3yx5G7kyvSDkc90ppPyw= github.com/cncf/udpa/go v0.0.0-20191209042840-269d4d468f6f/go.mod h1:M8M6+tZqaGXZJjfX53e64911xZQV5JYwmTeXPW+k8Sc= github.com/cncf/udpa/go v0.0.0-20200629203442-efcf912fb354/go.mod h1:WmhPx2Nbnhtbo57+VJT5O0JRkEi1Wbu0z5j0R8u5Hbk= github.com/cncf/udpa/go v0.0.0-20201120205902-5459f2c99403/go.mod h1:WmhPx2Nbnhtbo57+VJT5O0JRkEi1Wbu0z5j0R8u5Hbk= github.com/cncf/udpa/go v0.0.0-20210930031921-04548b0d99d4/go.mod h1:6pvJx4me5XPnfI9Z40ddWsdw2W/uZgQLFXToKeRcDiI= github.com/cncf/xds/go v0.0.0-20210312221358-fbca930ec8ed/go.mod h1:eXthEFrGJvWHgFFCl3hGmgk+/aYT6PnTQLykKQRLhEs= -github.com/cncf/xds/go v0.0.0-20210805033703-aa0b78936158/go.mod h1:eXthEFrGJvWHgFFCl3hGmgk+/aYT6PnTQLykKQRLhEs= github.com/cncf/xds/go v0.0.0-20210922020428-25de7278fc84/go.mod h1:eXthEFrGJvWHgFFCl3hGmgk+/aYT6PnTQLykKQRLhEs= github.com/cncf/xds/go v0.0.0-20211001041855-01bcc9b48dfe/go.mod h1:eXthEFrGJvWHgFFCl3hGmgk+/aYT6PnTQLykKQRLhEs= github.com/cncf/xds/go v0.0.0-20211011173535-cb28da3451f1/go.mod h1:eXthEFrGJvWHgFFCl3hGmgk+/aYT6PnTQLykKQRLhEs= -github.com/cncf/xds/go v0.0.0-20220314180256-7f1daf1720fc h1:PYXxkRUBGUMa5xgMVMDl62vEklZvKpVaxQeN9ie7Hfk= -github.com/cncf/xds/go v0.0.0-20220314180256-7f1daf1720fc/go.mod h1:eXthEFrGJvWHgFFCl3hGmgk+/aYT6PnTQLykKQRLhEs= github.com/containerd/cgroups v1.0.3 h1:ADZftAkglvCiD44c77s5YmMqaP2pzVCFZvBmAlBdAP4= github.com/containerd/containerd v1.6.6 h1:xJNPhbrmz8xAMDNoVjHy9YHtWwEQNS+CDkcIRh7t8Y0= github.com/containerd/containerd v1.6.6/go.mod h1:ZoP1geJldzCVY3Tonoz7b1IXk8rIX0Nltt5QE4OMNk0= @@ -171,9 +167,8 @@ github.com/cyphar/filepath-securejoin v0.2.3 h1:YX6ebbZCZP7VkM3scTTokDgBL2TY741X github.com/cyphar/filepath-securejoin v0.2.3/go.mod h1:aPGpWjXOXUn2NCNjFvBE6aRxGGx79pTxQpKOJNYHHl4= github.com/danieljoos/wincred v1.1.0/go.mod h1:XYlo+eRTsVA9aHGp7NGjFkPla4m+DCL7hqDjlFjiygg= github.com/davecgh/go-spew v1.1.0/go.mod h1:J7Y8YcW2NihsgmVo/mv3lAwl/skON4iLHjSsI+c5H38= +github.com/davecgh/go-spew v1.1.1 h1:vj9j/u1bqnvCEfJOwUhtlOARqs3+rkHYY13jYWTU97c= github.com/davecgh/go-spew v1.1.1/go.mod h1:J7Y8YcW2NihsgmVo/mv3lAwl/skON4iLHjSsI+c5H38= -github.com/davecgh/go-spew v1.1.2-0.20180830191138-d8f796af33cc h1:U9qPSI2PIWSS1VwoXQT9A3Wy9MM3WgvqSxFWenqJduM= -github.com/davecgh/go-spew v1.1.2-0.20180830191138-d8f796af33cc/go.mod h1:J7Y8YcW2NihsgmVo/mv3lAwl/skON4iLHjSsI+c5H38= github.com/daviddengcn/go-colortext v0.0.0-20160507010035-511bcaf42ccd/go.mod h1:dv4zxwHi5C/8AeI+4gX4dCWOIvNi7I6JCSX0HvlKPgE= github.com/denisenkom/go-mssqldb v0.9.0/go.mod h1:xbL0rPBG9cCiLr28tMa8zpbdarY27NDyej4t/EjAShU= github.com/distribution/distribution/v3 v3.0.0-20220526142353-ffbd94cbe269 h1:hbCT8ZPPMqefiAWD2ZKjn7ypokIGViTvBBg/ExLSdCk= @@ -190,6 +185,7 @@ github.com/docker/go-connections v0.4.0/go.mod h1:Gbd7IOopHjR8Iph03tsViu4nIes5Xh github.com/docker/go-events v0.0.0-20190806004212-e31b211e4f1c h1:+pKlWGMw7gf6bQ+oDZB4KHQFypsfjYlq/C4rfL7D3g8= github.com/docker/go-metrics v0.0.1 h1:AgB/0SvBxihN0X8OR4SjsblXkbMvalQ8cjmtKQ2rQV8= github.com/docker/go-metrics v0.0.1/go.mod h1:cG1hvH2utMXtqgqqYE9plW6lDxS3/5ayHzueweSI3Vw= +github.com/docker/go-units v0.3.3/go.mod h1:fgPhTUdO+D/Jk86RDLlptpiXQzgHJF7gydDDbaIK4Dk= github.com/docker/go-units v0.4.0 h1:3uh0PgVws3nIA0Q+MwDC8yjEPf9zjRfZZWXZYDct3Tw= github.com/docker/go-units v0.4.0/go.mod h1:fgPhTUdO+D/Jk86RDLlptpiXQzgHJF7gydDDbaIK4Dk= github.com/docker/libtrust v0.0.0-20150114040149-fa567046d9b1 h1:ZClxb8laGDf5arXfYcAtECDFgAgHklGI8CxgjHnXKJ4= @@ -207,12 +203,8 @@ github.com/envoyproxy/go-control-plane v0.9.7/go.mod h1:cwu0lG7PUMfa9snN8LXBig5y github.com/envoyproxy/go-control-plane v0.9.9-0.20201210154907-fd9021fe5dad/go.mod h1:cXg6YxExXjJnVBQHBLXeUAgxn2UodCpnH306RInaBQk= github.com/envoyproxy/go-control-plane v0.9.9-0.20210217033140-668b12f5399d/go.mod h1:cXg6YxExXjJnVBQHBLXeUAgxn2UodCpnH306RInaBQk= github.com/envoyproxy/go-control-plane v0.9.9-0.20210512163311-63b5d3c536b0/go.mod h1:hliV/p42l8fGbc6Y9bQ70uLwIvmJyVE5k4iMKlh8wCQ= -github.com/envoyproxy/go-control-plane v0.9.10-0.20210907150352-cf90f659a021/go.mod h1:AFq3mo9L8Lqqiid3OhADV3RfLJnjiw63cSpi+fDTRC0= -github.com/envoyproxy/go-control-plane v0.10.2-0.20220325020618-49ff273808a1 h1:xvqufLtNVwAhN8NMyWklVgxnWohi+wtMGQMhtxexlm0= github.com/envoyproxy/go-control-plane v0.10.2-0.20220325020618-49ff273808a1/go.mod h1:KJwIaB5Mv44NWtYuAOFCVOjcI94vtpEz2JU/D2v6IjE= github.com/envoyproxy/protoc-gen-validate v0.1.0/go.mod h1:iSmxcyjqTsJpI2R4NaDN7+kN2VEUnK/pcBlmesArF7c= -github.com/envoyproxy/protoc-gen-validate v0.9.1 h1:PS7VIOgmSVhWUEeZwTe7z7zouA22Cr590PzXKbZHOVY= -github.com/envoyproxy/protoc-gen-validate v0.9.1/go.mod h1:OKNgG7TCp5pF4d6XftA0++PMirau2/yoOwVac3AbF2w= github.com/evanphx/json-patch v4.11.0+incompatible/go.mod h1:50XU6AFN0ol/bzJsmQLiYLvXMP4fmwYFNcr97nuDLSk= github.com/evanphx/json-patch v4.12.0+incompatible h1:4onqiflcdA9EOZ4RxV643DvftH5pOlLGNtQ5lPWQu84= github.com/evanphx/json-patch v4.12.0+incompatible/go.mod h1:50XU6AFN0ol/bzJsmQLiYLvXMP4fmwYFNcr97nuDLSk= @@ -220,7 +212,6 @@ github.com/exponent-io/jsonpath v0.0.0-20151013193312-d6023ce2651d h1:105gxyaGwC github.com/exponent-io/jsonpath v0.0.0-20151013193312-d6023ce2651d/go.mod h1:ZZMPRZwes7CROmyNKgQzC3XPs6L/G2EJLHddWejkmf4= github.com/fatih/camelcase v1.0.0/go.mod h1:yN2Sb0lFhZJUdVvtELVWefmrXpuZESvPmqwoZc+/fpc= github.com/fatih/color v1.7.0/go.mod h1:Zm6kSWBoL9eyXnKyktHP6abPY2pDugNf5KwzbycvMj4= -github.com/fatih/color v1.9.0/go.mod h1:eQcE1qtQxscV5RaZvpXrrb8Drkc3/DdQ+uUYCNjL+zU= github.com/fatih/color v1.13.0 h1:8LOYc1KYPPmyKMuN8QV2DNRWNbLo6LZ0iLs8+mlH53w= github.com/fatih/color v1.13.0/go.mod h1:kLAiJbzzSOZDVNGyDpeOxJ47H46qBXwg5ILebYFFOfk= github.com/felixge/httpsnoop v1.0.1 h1:lvB5Jl89CsZtGIWuTcDM1E/vkVs49/Ml7JJe07l8SPQ= @@ -234,14 +225,15 @@ github.com/fsnotify/fsnotify v1.5.4/go.mod h1:OVB6XrOHzAwXMpEM7uPOzcehqUV2UqJxmV github.com/fvbommel/sortorder v1.0.1/go.mod h1:uk88iVf1ovNn1iLfgUVU2F9o5eO30ui720w+kxuqRs0= github.com/getkin/kin-openapi v0.76.0/go.mod h1:660oXbgy5JFMKreazJaQTw7o+X00qeSyhcnluiMv+Xg= github.com/ghodss/yaml v1.0.0/go.mod h1:4dBDuWmgqj2HViK6kFavaiC9ZROes6MMH2rRYeMEF04= +github.com/globalsign/mgo v0.0.0-20180905125535-1ca0a4f7cbcb/go.mod h1:xkRDCp4j0OGD1HRkm4kmhM+pmpv3AKq5SU7GMg4oO/Q= +github.com/globalsign/mgo v0.0.0-20181015135952-eeefdecb41b8/go.mod h1:xkRDCp4j0OGD1HRkm4kmhM+pmpv3AKq5SU7GMg4oO/Q= github.com/go-errors/errors v1.0.1 h1:LUHzmkK3GUKUrL/1gfBUxAHzcev3apQlezX/+O7ma6w= github.com/go-errors/errors v1.0.1/go.mod h1:f4zRHt4oKfwPJE5k8C9vpYG+aDHdBFUsgrm6/TyX73Q= github.com/go-gl/glfw v0.0.0-20190409004039-e6da0acd62b1/go.mod h1:vR7hzQXu2zJy9AVAgeJqvqgH9Q5CA+iKCZ2gyEVpxRU= github.com/go-gl/glfw/v3.3/glfw v0.0.0-20191125211704-12ad95a8df72/go.mod h1:tQ2UAYgL5IevRw8kRxooKSPJfGvJ9fJQFa0TUsXzTg8= github.com/go-gl/glfw/v3.3/glfw v0.0.0-20200222043503-6f7a984d4dc4/go.mod h1:tQ2UAYgL5IevRw8kRxooKSPJfGvJ9fJQFa0TUsXzTg8= +github.com/go-gorp/gorp/v3 v3.0.2 h1:ULqJXIekoqMx29FI5ekXXFoH1dT2Vc8UhnRzBg+Emz4= github.com/go-gorp/gorp/v3 v3.0.2/go.mod h1:BJ3q1ejpV8cVALtcXvXaXyTOlMmJhWDxTmncaR6rwBY= -github.com/go-gorp/gorp/v3 v3.1.0 h1:ItKF/Vbuj31dmV4jxA1qblpSwkl9g1typ24xoe70IGs= -github.com/go-gorp/gorp/v3 v3.1.0/go.mod h1:dLEjIyyRNiXvNZ8PSmzpt1GsWAUK8kjVhEpjH8TixEw= github.com/go-kit/kit v0.8.0/go.mod h1:xBxKIO96dXMWWy0MnWVtmwkA9/13aqxPnvrjFYMA2as= github.com/go-kit/kit v0.9.0/go.mod h1:xBxKIO96dXMWWy0MnWVtmwkA9/13aqxPnvrjFYMA2as= github.com/go-kit/log v0.1.0/go.mod h1:zbhenjAZHb184qTLMA9ZjW7ThYL0H2mk7Q6pNt4vbaY= @@ -254,45 +246,104 @@ github.com/go-logr/logr v1.2.0/go.mod h1:jdQByPbusPIv2/zmleS9BjJVeZ6kBagPoEUsqbV github.com/go-logr/logr v1.2.3 h1:2DntVwHkVopvECVRSlL5PSo9eG+cAkDCuckLubN+rq0= github.com/go-logr/logr v1.2.3/go.mod h1:jdQByPbusPIv2/zmleS9BjJVeZ6kBagPoEUsqbVz/1A= github.com/go-logr/zapr v1.2.0/go.mod h1:Qa4Bsj2Vb+FAVeAKsLD8RLQ+YRJB8YDmOAKxaBQf7Ro= -github.com/go-openapi/analysis v0.21.2 h1:hXFrOYFHUAMQdu6zwAiKKJHJQ8kqZs1ux/ru1P1wLJU= -github.com/go-openapi/analysis v0.21.2/go.mod h1:HZwRk4RRisyG8vx2Oe6aqeSQcoxRp47Xkp3+K6q+LdY= +github.com/go-openapi/analysis v0.0.0-20180825180245-b006789cd277/go.mod h1:k70tL6pCuVxPJOHXQ+wIac1FUrvNkHolPie/cLEU6hI= +github.com/go-openapi/analysis v0.17.0/go.mod h1:IowGgpVeD0vNm45So8nr+IcQ3pxVtpRoBWb8PVZO0ik= +github.com/go-openapi/analysis v0.18.0/go.mod h1:IowGgpVeD0vNm45So8nr+IcQ3pxVtpRoBWb8PVZO0ik= +github.com/go-openapi/analysis v0.19.2/go.mod h1:3P1osvZa9jKjb8ed2TPng3f0i/UY9snX6gxi44djMjk= +github.com/go-openapi/analysis v0.19.4/go.mod h1:3P1osvZa9jKjb8ed2TPng3f0i/UY9snX6gxi44djMjk= +github.com/go-openapi/analysis v0.19.5/go.mod h1:hkEAkxagaIvIP7VTn8ygJNkd4kAYON2rCu0v0ObL0AU= +github.com/go-openapi/analysis v0.19.10/go.mod h1:qmhS3VNFxBlquFJ0RGoDtylO9y4pgTAUNE9AEEMdlJQ= +github.com/go-openapi/analysis v0.19.16/go.mod h1:GLInF007N83Ad3m8a/CbQ5TPzdnGT7workfHwuVjNVk= +github.com/go-openapi/analysis v0.20.0 h1:UN09o0kNhleunxW7LR+KnltD0YrJ8FF03pSqvAN3Vro= +github.com/go-openapi/analysis v0.20.0/go.mod h1:BMchjvaHDykmRMsK40iPtvyOfFdMMxlOmQr9FBZk+Og= +github.com/go-openapi/errors v0.17.0/go.mod h1:LcZQpmvG4wyF5j4IhA73wkLFQg+QJXOQHVjmcZxhka0= +github.com/go-openapi/errors v0.18.0/go.mod h1:LcZQpmvG4wyF5j4IhA73wkLFQg+QJXOQHVjmcZxhka0= +github.com/go-openapi/errors v0.19.2/go.mod h1:qX0BLWsyaKfvhluLejVpVNwNRdXZhEbTA4kxxpKBC94= +github.com/go-openapi/errors v0.19.3/go.mod h1:qX0BLWsyaKfvhluLejVpVNwNRdXZhEbTA4kxxpKBC94= +github.com/go-openapi/errors v0.19.6/go.mod h1:cM//ZKUKyO06HSwqAelJ5NsEMMcpa6VpXe8DOa1Mi1M= +github.com/go-openapi/errors v0.19.7/go.mod h1:cM//ZKUKyO06HSwqAelJ5NsEMMcpa6VpXe8DOa1Mi1M= github.com/go-openapi/errors v0.19.8/go.mod h1:cM//ZKUKyO06HSwqAelJ5NsEMMcpa6VpXe8DOa1Mi1M= github.com/go-openapi/errors v0.19.9/go.mod h1:cM//ZKUKyO06HSwqAelJ5NsEMMcpa6VpXe8DOa1Mi1M= github.com/go-openapi/errors v0.20.2 h1:dxy7PGTqEh94zj2E3h1cUmQQWiM1+aeCROfAr02EmK8= github.com/go-openapi/errors v0.20.2/go.mod h1:cM//ZKUKyO06HSwqAelJ5NsEMMcpa6VpXe8DOa1Mi1M= +github.com/go-openapi/jsonpointer v0.17.0/go.mod h1:cOnomiV+CVVwFLk0A/MExoFMjwdsUdVpsRhURCKh+3M= +github.com/go-openapi/jsonpointer v0.18.0/go.mod h1:cOnomiV+CVVwFLk0A/MExoFMjwdsUdVpsRhURCKh+3M= +github.com/go-openapi/jsonpointer v0.19.2/go.mod h1:3akKfEdA7DF1sugOqz1dVQHBcuDBPKZGEoHC/NkiQRg= github.com/go-openapi/jsonpointer v0.19.3/go.mod h1:Pl9vOtqEWErmShwVjC8pYs9cog34VGT37dQOVbmoatg= github.com/go-openapi/jsonpointer v0.19.5 h1:gZr+CIYByUqjcgeLXnQu2gHYQC9o73G2XUeOFYEICuY= github.com/go-openapi/jsonpointer v0.19.5/go.mod h1:Pl9vOtqEWErmShwVjC8pYs9cog34VGT37dQOVbmoatg= +github.com/go-openapi/jsonreference v0.17.0/go.mod h1:g4xxGn04lDIRh0GJb5QlpE3HfopLOL6uZrK/VgnsK9I= +github.com/go-openapi/jsonreference v0.18.0/go.mod h1:g4xxGn04lDIRh0GJb5QlpE3HfopLOL6uZrK/VgnsK9I= +github.com/go-openapi/jsonreference v0.19.2/go.mod h1:jMjeRr2HHw6nAVajTXJ4eiUwohSTlpa0o73RUL1owJc= github.com/go-openapi/jsonreference v0.19.3/go.mod h1:rjx6GuL8TTa9VaixXglHmQmIL98+wF9xc8zWvFonSJ8= +github.com/go-openapi/jsonreference v0.19.5 h1:1WJP/wi4OjB4iV8KVbH73rQaoialJrqv8gitZLxGLtM= github.com/go-openapi/jsonreference v0.19.5/go.mod h1:RdybgQwPxbL4UEjuAruzK1x3nE69AqPYEJeo/TWfEeg= -github.com/go-openapi/jsonreference v0.19.6 h1:UBIxjkht+AWIgYzCDSv2GN+E/togfwXUJFRTWhl2Jjs= -github.com/go-openapi/jsonreference v0.19.6/go.mod h1:diGHMEHg2IqXZGKxqyvWdfWU/aim5Dprw5bqpKkTvns= -github.com/go-openapi/loads v0.21.1 h1:Wb3nVZpdEzDTcly8S4HMkey6fjARRzb7iEaySimlDW0= -github.com/go-openapi/loads v0.21.1/go.mod h1:/DtAMXXneXFjbQMGEtbamCZb+4x7eGwkvZCvBmwUG+g= -github.com/go-openapi/runtime v0.24.1 h1:Sml5cgQKGYQHF+M7yYSHaH1eOjvTykrddTE/KtQVjqo= -github.com/go-openapi/runtime v0.24.1/go.mod h1:AKurw9fNre+h3ELZfk6ILsfvPN+bvvlaU/M9q/r9hpk= -github.com/go-openapi/spec v0.20.4 h1:O8hJrt0UMnhHcluhIdUgCLRWyM2x7QkBXRvOs7m+O1M= -github.com/go-openapi/spec v0.20.4/go.mod h1:faYFR1CvsJZ0mNsmsphTMSoRrNV3TEDoAM7FOEWeq8I= -github.com/go-openapi/strfmt v0.21.0/go.mod h1:ZRQ409bWMj+SOgXofQAGTIo2Ebu72Gs+WaRADcS5iNg= -github.com/go-openapi/strfmt v0.21.1/go.mod h1:I/XVKeLc5+MM5oPNN7P6urMOpuLXEcNrCX/rPGuWb0k= -github.com/go-openapi/strfmt v0.21.2/go.mod h1:I/XVKeLc5+MM5oPNN7P6urMOpuLXEcNrCX/rPGuWb0k= -github.com/go-openapi/strfmt v0.21.3 h1:xwhj5X6CjXEZZHMWy1zKJxvW9AfHC9pkyUjLvHtKG7o= -github.com/go-openapi/strfmt v0.21.3/go.mod h1:k+RzNO0Da+k3FrrynSNN8F7n/peCmQQqbbXjtDfvmGg= +github.com/go-openapi/loads v0.17.0/go.mod h1:72tmFy5wsWx89uEVddd0RjRWPZm92WRLhf7AC+0+OOU= +github.com/go-openapi/loads v0.18.0/go.mod h1:72tmFy5wsWx89uEVddd0RjRWPZm92WRLhf7AC+0+OOU= +github.com/go-openapi/loads v0.19.0/go.mod h1:72tmFy5wsWx89uEVddd0RjRWPZm92WRLhf7AC+0+OOU= +github.com/go-openapi/loads v0.19.2/go.mod h1:QAskZPMX5V0C2gvfkGZzJlINuP7Hx/4+ix5jWFxsNPs= +github.com/go-openapi/loads v0.19.3/go.mod h1:YVfqhUCdahYwR3f3iiwQLhicVRvLlU/WO5WPaZvcvSI= +github.com/go-openapi/loads v0.19.5/go.mod h1:dswLCAdonkRufe/gSUC3gN8nTSaB9uaS2es0x5/IbjY= +github.com/go-openapi/loads v0.19.6/go.mod h1:brCsvE6j8mnbmGBh103PT/QLHfbyDxA4hsKvYBNEGVc= +github.com/go-openapi/loads v0.19.7/go.mod h1:brCsvE6j8mnbmGBh103PT/QLHfbyDxA4hsKvYBNEGVc= +github.com/go-openapi/loads v0.20.0/go.mod h1:2LhKquiE513rN5xC6Aan6lYOSddlL8Mp20AW9kpviM4= +github.com/go-openapi/loads v0.20.2 h1:z5p5Xf5wujMxS1y8aP+vxwW5qYT2zdJBbXKmQUG3lcc= +github.com/go-openapi/loads v0.20.2/go.mod h1:hTVUotJ+UonAMMZsvakEgmWKgtulweO9vYP2bQYKA/o= +github.com/go-openapi/runtime v0.0.0-20180920151709-4f900dc2ade9/go.mod h1:6v9a6LTXWQCdL8k1AO3cvqx5OtZY/Y9wKTgaoP6YRfA= +github.com/go-openapi/runtime v0.19.0/go.mod h1:OwNfisksmmaZse4+gpV3Ne9AyMOlP1lt4sK4FXt0O64= +github.com/go-openapi/runtime v0.19.4/go.mod h1:X277bwSUBxVlCYR3r7xgZZGKVvBd/29gLDlFGtJ8NL4= +github.com/go-openapi/runtime v0.19.15/go.mod h1:dhGWCTKRXlAfGnQG0ONViOZpjfg0m2gUt9nTQPQZuoo= +github.com/go-openapi/runtime v0.19.16/go.mod h1:5P9104EJgYcizotuXhEuUrzVc+j1RiSjahULvYmlv98= +github.com/go-openapi/runtime v0.19.24 h1:TqagMVlRAOTwllE/7hNKx6rQ10O6T8ZzeJdMjSTKaD4= +github.com/go-openapi/runtime v0.19.24/go.mod h1:Lm9YGCeecBnUUkFTxPC4s1+lwrkJ0pthx8YvyjCfkgk= +github.com/go-openapi/spec v0.17.0/go.mod h1:XkF/MOi14NmjsfZ8VtAKf8pIlbZzyoTvZsdfssdxcBI= +github.com/go-openapi/spec v0.18.0/go.mod h1:XkF/MOi14NmjsfZ8VtAKf8pIlbZzyoTvZsdfssdxcBI= +github.com/go-openapi/spec v0.19.2/go.mod h1:sCxk3jxKgioEJikev4fgkNmwS+3kuYdJtcsZsD5zxMY= +github.com/go-openapi/spec v0.19.3/go.mod h1:FpwSN1ksY1eteniUU7X0N/BgJ7a4WvBFVA8Lj9mJglo= +github.com/go-openapi/spec v0.19.6/go.mod h1:Hm2Jr4jv8G1ciIAo+frC/Ft+rR2kQDh8JHKHb3gWUSk= +github.com/go-openapi/spec v0.19.8/go.mod h1:Hm2Jr4jv8G1ciIAo+frC/Ft+rR2kQDh8JHKHb3gWUSk= +github.com/go-openapi/spec v0.19.15/go.mod h1:+81FIL1JwC5P3/Iuuozq3pPE9dXdIEGxFutcFKaVbmU= +github.com/go-openapi/spec v0.20.0/go.mod h1:+81FIL1JwC5P3/Iuuozq3pPE9dXdIEGxFutcFKaVbmU= +github.com/go-openapi/spec v0.20.1/go.mod h1:93x7oh+d+FQsmsieroS4cmR3u0p/ywH649a3qwC9OsQ= +github.com/go-openapi/spec v0.20.3 h1:uH9RQ6vdyPSs2pSy9fL8QPspDF2AMIMPtmK5coSSjtQ= +github.com/go-openapi/spec v0.20.3/go.mod h1:gG4F8wdEDN+YPBMVnzE85Rbhf+Th2DTvA9nFPQ5AYEg= +github.com/go-openapi/strfmt v0.17.0/go.mod h1:P82hnJI0CXkErkXi8IKjPbNBM6lV6+5pLP5l494TcyU= +github.com/go-openapi/strfmt v0.18.0/go.mod h1:P82hnJI0CXkErkXi8IKjPbNBM6lV6+5pLP5l494TcyU= +github.com/go-openapi/strfmt v0.19.0/go.mod h1:+uW+93UVvGGq2qGaZxdDeJqSAqBqBdl+ZPMF/cC8nDY= +github.com/go-openapi/strfmt v0.19.2/go.mod h1:0yX7dbo8mKIvc3XSKp7MNfxw4JytCfCD6+bY1AVL9LU= +github.com/go-openapi/strfmt v0.19.3/go.mod h1:0yX7dbo8mKIvc3XSKp7MNfxw4JytCfCD6+bY1AVL9LU= +github.com/go-openapi/strfmt v0.19.4/go.mod h1:eftuHTlB/dI8Uq8JJOyRlieZf+WkkxUuk0dgdHXr2Qk= +github.com/go-openapi/strfmt v0.19.5/go.mod h1:eftuHTlB/dI8Uq8JJOyRlieZf+WkkxUuk0dgdHXr2Qk= +github.com/go-openapi/strfmt v0.19.11/go.mod h1:UukAYgTaQfqJuAFlNxxMWNvMYiwiXtLsF2VwmoFtbtc= +github.com/go-openapi/strfmt v0.20.0 h1:l2omNtmNbMc39IGptl9BuXBEKcZfS8zjrTsPKTiJiDM= +github.com/go-openapi/strfmt v0.20.0/go.mod h1:UukAYgTaQfqJuAFlNxxMWNvMYiwiXtLsF2VwmoFtbtc= +github.com/go-openapi/swag v0.17.0/go.mod h1:AByQ+nYG6gQg71GINrmuDXCPWdL640yX49/kXLo40Tg= +github.com/go-openapi/swag v0.18.0/go.mod h1:AByQ+nYG6gQg71GINrmuDXCPWdL640yX49/kXLo40Tg= +github.com/go-openapi/swag v0.19.2/go.mod h1:POnQmlKehdgb5mhVOsnJFsivZCEZ/vjK9gh66Z9tfKk= github.com/go-openapi/swag v0.19.5/go.mod h1:POnQmlKehdgb5mhVOsnJFsivZCEZ/vjK9gh66Z9tfKk= +github.com/go-openapi/swag v0.19.7/go.mod h1:ao+8BpOPyKdpQz3AOJfbeEVpLmWAvlT1IfTe5McPyhY= +github.com/go-openapi/swag v0.19.9/go.mod h1:ao+8BpOPyKdpQz3AOJfbeEVpLmWAvlT1IfTe5McPyhY= +github.com/go-openapi/swag v0.19.12/go.mod h1:eFdyEBkTdoAf/9RXBvj4cr1nH7GD8Kzo5HTt47gr72M= +github.com/go-openapi/swag v0.19.13/go.mod h1:QYRuS/SOXUCsnplDa677K7+DxSOj6IPNl/eQntq43wQ= +github.com/go-openapi/swag v0.19.14 h1:gm3vOOXfiuw5i9p5N9xJvfjvuofpyvLA9Wr6QfK5Fng= github.com/go-openapi/swag v0.19.14/go.mod h1:QYRuS/SOXUCsnplDa677K7+DxSOj6IPNl/eQntq43wQ= -github.com/go-openapi/swag v0.19.15/go.mod h1:QYRuS/SOXUCsnplDa677K7+DxSOj6IPNl/eQntq43wQ= -github.com/go-openapi/swag v0.21.1 h1:wm0rhTb5z7qpJRHBdPOMuY4QjVUMbF6/kwoYeRAOrKU= -github.com/go-openapi/swag v0.21.1/go.mod h1:QYRuS/SOXUCsnplDa677K7+DxSOj6IPNl/eQntq43wQ= -github.com/go-openapi/validate v0.21.0 h1:+Wqk39yKOhfpLqNLEC0/eViCkzM5FVXVqrvt526+wcI= -github.com/go-openapi/validate v0.21.0/go.mod h1:rjnrwK57VJ7A8xqfpAOEKRH8yQSGUriMu5/zuPSQ1hg= +github.com/go-openapi/validate v0.18.0/go.mod h1:Uh4HdOzKt19xGIGm1qHf/ofbX1YQ4Y+MYsct2VUrAJ4= +github.com/go-openapi/validate v0.19.2/go.mod h1:1tRCw7m3jtI8eNWEEliiAqUIcBztB2KDnRCRMUi7GTA= +github.com/go-openapi/validate v0.19.3/go.mod h1:90Vh6jjkTn+OT1Eefm0ZixWNFjhtOH7vS9k0lo6zwJo= +github.com/go-openapi/validate v0.19.10/go.mod h1:RKEZTUWDkxKQxN2jDT7ZnZi2bhZlbNMAuKvKB+IaGx8= +github.com/go-openapi/validate v0.19.12/go.mod h1:Rzou8hA/CBw8donlS6WNEUQupNvUZ0waH08tGe6kAQ4= +github.com/go-openapi/validate v0.19.15/go.mod h1:tbn/fdOwYHgrhPBzidZfJC2MIVvs9GA7monOmWBbeCI= +github.com/go-openapi/validate v0.20.1/go.mod h1:b60iJT+xNNLfaQJUqLI7946tYiFEOuE9E4k54HpKcJ0= +github.com/go-openapi/validate v0.20.2 h1:AhqDegYV3J3iQkMPJSXkvzymHKMTw0BST3RK3hTT4ts= +github.com/go-openapi/validate v0.20.2/go.mod h1:e7OJoKNgd0twXZwIn0A43tHbvIcr/rZIVCbJBpTUoY0= github.com/go-ozzo/ozzo-validation v3.6.0+incompatible h1:msy24VGS42fKO9K1vLz82/GeYW1cILu7Nuuj1N3BBkE= github.com/go-ozzo/ozzo-validation v3.6.0+incompatible/go.mod h1:gsEKFIVnabGBt6mXmxK0MoFy+cZoTJY6mu5Ll3LVLBU= github.com/go-sql-driver/mysql v1.4.1/go.mod h1:zAC/RDZ24gD3HViQzih4MyKcchzm+sOG5ZlKdlhCg5w= github.com/go-sql-driver/mysql v1.5.0/go.mod h1:DCzpHaOWr8IXmIStZouvnhqoel9Qv2LBy8hT2VhHyBg= github.com/go-sql-driver/mysql v1.6.0 h1:BCTh4TKNUYmOmMUcQ3IipzF5prigylS7XXjEkfCHuOE= github.com/go-sql-driver/mysql v1.6.0/go.mod h1:DCzpHaOWr8IXmIStZouvnhqoel9Qv2LBy8hT2VhHyBg= +github.com/go-stack/stack v1.8.0 h1:5SgMzNM5HxrEjV0ww2lTmX6E2Izsfxas4+YHWRs3Lsk= github.com/go-stack/stack v1.8.0/go.mod h1:v0f6uXyyMGvRgIKkXu+yp6POWl0qKG85gN/melR3HDY= -github.com/go-stack/stack v1.8.1/go.mod h1:dcoOX6HbPZSZptuspn9bctJ+N/CnF5gGygcUP3XYfe4= github.com/go-task/slim-sprig v0.0.0-20210107165309-348f09dbbbc0/go.mod h1:fyg7847qk6SyHyPtNmDHnmrv/HOrqktSC+C9fM+CJOE= github.com/gobuffalo/attrs v0.0.0-20190224210810-a9411de4debd/go.mod h1:4duuawTqi2wkkpB4ePgWMaai6/Kc6WEz83bhFwpHzj0= github.com/gobuffalo/depgen v0.0.0-20190329151759-d478694a28d3/go.mod h1:3STtPUQYuzV0gBVOY3vy6CfMm/ljR4pABfrTeHNLHUY= @@ -417,10 +468,11 @@ github.com/google/pprof v0.0.0-20210720184732-4bb14d4b1be1/go.mod h1:kpwsk12EmLe github.com/google/renameio v0.1.0/go.mod h1:KWCgfxg9yswjAJkECMjeO8J8rahYeXnNhOm40UhjYkI= github.com/google/shlex v0.0.0-20191202100458-e7afc7fbc510 h1:El6M4kTTCOh6aBiKaUGG7oYTSPP8MxqL4YI3kZKwcP4= github.com/google/shlex v0.0.0-20191202100458-e7afc7fbc510/go.mod h1:pupxD2MaaD3pAXIBCelhxNneeOaAeabZDe5s4K6zSpQ= +github.com/google/uuid v1.0.0/go.mod h1:TIyPZe4MgqvfeYDBFedMoGGpEw/LqOeaOT+nhxU+yHo= github.com/google/uuid v1.1.1/go.mod h1:TIyPZe4MgqvfeYDBFedMoGGpEw/LqOeaOT+nhxU+yHo= github.com/google/uuid v1.1.2/go.mod h1:TIyPZe4MgqvfeYDBFedMoGGpEw/LqOeaOT+nhxU+yHo= -github.com/google/uuid v1.3.0 h1:t6JiXgmwXMjEs8VusXIJk2BXHsn+wx8BZdTaoZ5fu7I= -github.com/google/uuid v1.3.0/go.mod h1:TIyPZe4MgqvfeYDBFedMoGGpEw/LqOeaOT+nhxU+yHo= +github.com/google/uuid v1.2.0 h1:qJYtXnJRWmpe7m/3XlyhrsLrEURqHRM2kxzoxXqyUDs= +github.com/google/uuid v1.2.0/go.mod h1:TIyPZe4MgqvfeYDBFedMoGGpEw/LqOeaOT+nhxU+yHo= github.com/googleapis/gax-go/v2 v2.0.4/go.mod h1:0Wqv26UfaUD9n4G6kQubkQ+KchISgw+vpHVxEJEs9eg= github.com/googleapis/gax-go/v2 v2.0.5/go.mod h1:DWXyrwAJ9X0FpwwEdw+IPEYBICEFu5mhpdKc/us6bOk= github.com/googleapis/gax-go/v2 v2.1.0/go.mod h1:Q3nei7sK6ybPYH7twZdmQpAd1MKb7pfu6SK+H1/DsU0= @@ -437,63 +489,34 @@ github.com/gregjones/httpcache v0.0.0-20180305231024-9cad4c3443a7 h1:pdN6V1QBWet github.com/gregjones/httpcache v0.0.0-20180305231024-9cad4c3443a7/go.mod h1:FecbI9+v66THATjSRHfNgh1IVFe/9kFxbXtjV0ctIMA= github.com/grpc-ecosystem/grpc-gateway v1.16.0/go.mod h1:BDjrQk3hbvj6Nolgz8mAMFbcEtjT1g+wF4CSlocrBnw= github.com/hashicorp/consul/api v1.1.0/go.mod h1:VmuI/Lkw1nC05EYQWNKwWGbkg+FbDBtguAZLlVdkD9Q= -github.com/hashicorp/consul/api v1.20.0 h1:9IHTjNVSZ7MIwjlW3N3a7iGiykCMDpxZu8jsxFJh0yc= -github.com/hashicorp/consul/api v1.20.0/go.mod h1:nR64eD44KQ59Of/ECwt2vUmIK2DKsDzAwTmwmLl8Wpo= -github.com/hashicorp/consul/envoyextensions v0.1.2 h1:PvPqJ/td3UpOeIKQl5ycFPUy46XZP9awfhAUCduDeI4= -github.com/hashicorp/consul/envoyextensions v0.1.2/go.mod h1:N94DQQkgITiA40zuTQ/UdPOLAAWobgHfVT5u7wxE/aU= github.com/hashicorp/consul/sdk v0.1.1/go.mod h1:VKf9jXwCTEY1QZP2MOLRhb5i/I/ssyNV1vwHyQBF0x8= -github.com/hashicorp/consul/sdk v0.13.1 h1:EygWVWWMczTzXGpO93awkHFzfUka6hLYJ0qhETd+6lY= -github.com/hashicorp/consul/troubleshoot v0.0.0-20230217154305-8dab825c3640 h1:P81kThpSzUW2oERDMrLsiZE3OuilLo3/EQhtVQW5M+8= -github.com/hashicorp/consul/troubleshoot v0.0.0-20230217154305-8dab825c3640/go.mod h1:rskvju2tK8XvHYTAILHjO7lpV1/uViHs3Q3mg9Rkwlg= -github.com/hashicorp/consul/troubleshoot v0.1.2 h1:c6uMTSt/qTMhK3e18nl4xW4j7JcANdQNHOEYhoXH1P8= -github.com/hashicorp/consul/troubleshoot v0.1.2/go.mod h1:q35QOtN7K5kFLPm2SXHBDD+PzsuBekcqTZuuoOTzbWA= github.com/hashicorp/errwrap v1.0.0/go.mod h1:YH+1FKiLXxHSkmPseP+kNlulaMuP3n2brvKWEqk/Jc4= github.com/hashicorp/errwrap v1.1.0 h1:OxrOeh75EUXMY8TBjag2fzXGZ40LB6IKw45YeGUDY2I= github.com/hashicorp/errwrap v1.1.0/go.mod h1:YH+1FKiLXxHSkmPseP+kNlulaMuP3n2brvKWEqk/Jc4= -github.com/hashicorp/go-cleanhttp v0.5.0/go.mod h1:JpRdi6/HCYpAwUzNwuwqhbovhLtngrth3wmdIIUrZ80= +github.com/hashicorp/go-cleanhttp v0.5.1 h1:dH3aiDG9Jvb5r5+bYHsikaOUIpcM0xvgMXVoDkXMzJM= github.com/hashicorp/go-cleanhttp v0.5.1/go.mod h1:JpRdi6/HCYpAwUzNwuwqhbovhLtngrth3wmdIIUrZ80= -github.com/hashicorp/go-cleanhttp v0.5.2 h1:035FKYIWjmULyFRBKPs8TBQoi0x6d9G4xc9neXJWAZQ= -github.com/hashicorp/go-cleanhttp v0.5.2/go.mod h1:kO/YDlP8L1346E6Sodw+PrpBSV4/SoxCXGY6BqNFT48= -github.com/hashicorp/go-hclog v1.2.1 h1:YQsLlGDJgwhXFpucSPyVbCBviQtjlHv3jLTlp8YmtEw= -github.com/hashicorp/go-hclog v1.2.1/go.mod h1:W4Qnvbt70Wk/zYJryRzDRU/4r0kIg0PVHBcfoyhpF5M= +github.com/hashicorp/go-hclog v0.16.2 h1:K4ev2ib4LdQETX5cSZBG0DVLk1jwGqSPXBjdah3veNs= +github.com/hashicorp/go-hclog v0.16.2/go.mod h1:whpDNt7SSdeAju8AWKIWsul05p54N/39EeqMAyrmvFQ= github.com/hashicorp/go-immutable-radix v1.0.0/go.mod h1:0y9vanUI8NX6FsYoO3zeMjhV/C5i9g4Q3DwcSNZ4P60= -github.com/hashicorp/go-immutable-radix v1.3.1 h1:DKHmCUm2hRBK510BaiZlwvpD40f8bJFeZnpfm2KLowc= -github.com/hashicorp/go-immutable-radix v1.3.1/go.mod h1:0y9vanUI8NX6FsYoO3zeMjhV/C5i9g4Q3DwcSNZ4P60= github.com/hashicorp/go-msgpack v0.5.3/go.mod h1:ahLV/dePpqEmjfWmKiqvPkv/twdG7iPBM1vqhUKIvfM= -github.com/hashicorp/go-msgpack v0.5.5 h1:i9R9JSrqIz0QVLz3sz+i3YJdT7TTSLcfLLzJi9aZTuI= github.com/hashicorp/go-multierror v1.0.0/go.mod h1:dHtQlpGsu+cZNNAkkCN/P3hoUDHhCYQXV3UM06sGGrk= -github.com/hashicorp/go-multierror v1.1.0/go.mod h1:spPvp8C1qA32ftKqdAHm4hHTbPw+vmowP0z+KUhOZdA= github.com/hashicorp/go-multierror v1.1.1 h1:H5DkEtf6CXdFp0N0Em5UCwQpXMWke8IA0+lD48awMYo= github.com/hashicorp/go-multierror v1.1.1/go.mod h1:iw975J/qwKPdAO1clOe2L8331t/9/fmwbPZ6JB6eMoM= -github.com/hashicorp/go-retryablehttp v0.5.3/go.mod h1:9B5zBasrRhHXnJnui7y6sL7es7NDiJgTc6Er0maI1Xs= github.com/hashicorp/go-rootcerts v1.0.0/go.mod h1:K6zTfqpRlCUIjkwsN4Z+hiSfzSTQa6eBIzfwKfwNnHU= -github.com/hashicorp/go-rootcerts v1.0.2 h1:jzhAVGtqPKbwpyCPELlgNWhE1znq+qwJtW5Oi2viEzc= -github.com/hashicorp/go-rootcerts v1.0.2/go.mod h1:pqUvnprVnM5bf7AOirdbb01K4ccR319Vf4pU3K5EGc8= github.com/hashicorp/go-sockaddr v1.0.0/go.mod h1:7Xibr9yA9JjQq1JpNB2Vw7kxv8xerXegt+ozgdvDeDU= -github.com/hashicorp/go-sockaddr v1.0.2 h1:ztczhD1jLxIRjVejw8gFomI1BQZOe2WoVOu0SyteCQc= github.com/hashicorp/go-syslog v1.0.0/go.mod h1:qPfqrKkXGihmCqbJM2mZgkZGvKG1dFdvsLplgctolz4= github.com/hashicorp/go-uuid v1.0.0/go.mod h1:6SBZvOh/SIDV7/2o3Jml5SYk/TvGqwFJ/bN7x4byOro= github.com/hashicorp/go-uuid v1.0.1/go.mod h1:6SBZvOh/SIDV7/2o3Jml5SYk/TvGqwFJ/bN7x4byOro= -github.com/hashicorp/go-uuid v1.0.2 h1:cfejS+Tpcp13yd5nYHWDI6qVCny6wyX2Mt5SGur2IGE= -github.com/hashicorp/go-version v1.2.1 h1:zEfKbn2+PDgroKdiOzqiE8rsmLqU2uwi5PB5pBJ3TkI= -github.com/hashicorp/go-version v1.2.1/go.mod h1:fltr4n8CU8Ke44wwGCBoEymUuxUHl09ZGVZPK5anwXA= github.com/hashicorp/go.net v0.0.1/go.mod h1:hjKkEWcCURg++eb33jQU7oqQcI9XDCnUzHA0oac0k90= github.com/hashicorp/golang-lru v0.5.0/go.mod h1:/m3WP610KZHVQ1SGc6re/UDhFvYD7pJ4Ao+sR/qLZy8= github.com/hashicorp/golang-lru v0.5.1/go.mod h1:/m3WP610KZHVQ1SGc6re/UDhFvYD7pJ4Ao+sR/qLZy8= -github.com/hashicorp/golang-lru v0.5.4 h1:YDjusn29QI/Das2iO9M0BHnIbxPeyuCHsjMW+lJfyTc= -github.com/hashicorp/golang-lru v0.5.4/go.mod h1:iADmTwqILo4mZ8BN3D2Q6+9jd8WM5uGBxy+E8yxSoD4= github.com/hashicorp/hcl v1.0.0/go.mod h1:E5yfLk+7swimpb2L/Alb/PJmXilQ/rhwaUYs4T20WEQ= github.com/hashicorp/hcp-sdk-go v0.23.1-0.20220921131124-49168300a7dc h1:on26TCKYnX7JzZCtwkR/LWHSqMu40PoZ6h/0e6Pq8ug= github.com/hashicorp/hcp-sdk-go v0.23.1-0.20220921131124-49168300a7dc/go.mod h1:/9UoDY2FYYA8lFaKBb2HmM/jKYZGANmf65q9QRc/cVw= github.com/hashicorp/logutils v1.0.0/go.mod h1:QIAnNjmIWmVIIkWDTG1z5v++HQmx9WQRO+LraFDTW64= github.com/hashicorp/mdns v1.0.0/go.mod h1:tL+uN++7HEJ6SQLQ2/p+z2pH24WQKWjBPkE0mNTz8vQ= -github.com/hashicorp/mdns v1.0.4/go.mod h1:mtBihi+LeNXGtG8L9dX59gAEa12BDtBQSp4v/YAJqrc= github.com/hashicorp/memberlist v0.1.3/go.mod h1:ajVTdAv/9Im8oMAAj5G31PhhMCZJV2pPBoIllUwCN7I= -github.com/hashicorp/memberlist v0.5.0 h1:EtYPN8DpAURiapus508I4n9CzHs2W+8NZGbmmR/prTM= -github.com/hashicorp/memberlist v0.5.0/go.mod h1:yvyXLpo0QaGE59Y7hDTsTzDD25JYBZ4mHgHUZ8lrOI0= github.com/hashicorp/serf v0.8.2/go.mod h1:6hOLApaqBFA1NXqRQAsxw9QxuDEvNxSQRwA/JwenrHc= -github.com/hashicorp/serf v0.10.1 h1:Z1H2J60yRKvfDYAOZLd2MU0ND4AH/WDz7xYHDWQsIPY= -github.com/hashicorp/serf v0.10.1/go.mod h1:yL2t6BqATOLGc5HF7qbFkTfXoPIY0WZdWHfEvMqbG+4= github.com/hpcloud/tail v1.0.0/go.mod h1:ab1qPbhIpdTxEkNHXyeSf5vhxWSCs/tWer42PpOxQnU= github.com/huandu/xstrings v1.3.1/go.mod h1:y5/lhBue+AyNmUVz9RLU9xbLR0o4KIIExikq4ovT0aE= github.com/huandu/xstrings v1.3.2 h1:L18LIDzqlW6xN2rEkpdV8+oL/IXWJ1APd+vsdYy4Wdw= @@ -502,10 +525,12 @@ github.com/ianlancetaylor/demangle v0.0.0-20181102032728-5e5cf60278f6/go.mod h1: github.com/ianlancetaylor/demangle v0.0.0-20200824232613-28f6c0f3b639/go.mod h1:aSSvb/t6k1mPoxDqO4vJh6VOCGPwU4O0C2/Eqndh1Sc= github.com/imdario/mergo v0.3.5/go.mod h1:2EnlNZ0deacrJVfApfmtdGgDfMuh/nq6Ok1EcJh5FfA= github.com/imdario/mergo v0.3.11/go.mod h1:jmQim1M+e3UYxmgPu/WyfjB3N3VflVyUjjjwH0dnCYA= -github.com/imdario/mergo v0.3.13 h1:lFzP57bqS/wsqKssCGmtLAb8A0wKjLGrve2q3PPVcBk= -github.com/imdario/mergo v0.3.13/go.mod h1:4lJ1jqUDcsbIECGy0RUJAXNIhg+6ocWgb1ALK2O4oXg= +github.com/imdario/mergo v0.3.12 h1:b6R2BslTbIEToALKP7LxUvijTsNI9TAe80pLWN2g/HU= +github.com/imdario/mergo v0.3.12/go.mod h1:jmQim1M+e3UYxmgPu/WyfjB3N3VflVyUjjjwH0dnCYA= github.com/inconshreveable/mousetrap v1.0.0 h1:Z8tu5sraLXCXIcARxBp/8cbvlwVa7Z1NHg9XEKhtSvM= github.com/inconshreveable/mousetrap v1.0.0/go.mod h1:PxqpIevigyE2G7u3NXJIT2ANytuPF1OarO4DADm73n8= +github.com/jmespath/go-jmespath v0.4.0/go.mod h1:T8mJZnbsbmF+m6zOOFylbeCJqk5+pHWvzYPziyZiYoo= +github.com/jmespath/go-jmespath/internal/testify v1.5.1/go.mod h1:L3OGu8Wl2/fWfCI6z80xFu9LTZmf1ZRjMHUOPmWr69U= github.com/jmoiron/sqlx v1.3.5 h1:vFFPA71p1o5gAeqtEAwLU4dnX2napprKtHr7PYIcN3g= github.com/jmoiron/sqlx v1.3.5/go.mod h1:nRVWtLre0KfCLJvgxzCsLVMogSvQ1zNJtpYr2Ccp0mQ= github.com/joho/godotenv v1.3.0/go.mod h1:7hK45KPybAkOC6peb+G5yklZfMxEjkZhHbwpqxOKXbg= @@ -515,7 +540,6 @@ github.com/josharian/intern v1.0.0/go.mod h1:5DoeVV0s6jJacbCEi61lwdGj/aVlrQvzHFF github.com/jpillora/backoff v1.0.0/go.mod h1:J/6gKK9jxlEcS3zixgDgUAsiuZ7yrSoa/FX5e0EB2j4= github.com/json-iterator/go v1.1.6/go.mod h1:+SdeFBvtyEkXs7REEP0seUULqWtbJapLOCVDaaPEHmU= github.com/json-iterator/go v1.1.7/go.mod h1:KdQUCv79m/52Kvf8AW2vK1V8akMuk1QjK/uOdHXbAo4= -github.com/json-iterator/go v1.1.9/go.mod h1:KdQUCv79m/52Kvf8AW2vK1V8akMuk1QjK/uOdHXbAo4= github.com/json-iterator/go v1.1.10/go.mod h1:KdQUCv79m/52Kvf8AW2vK1V8akMuk1QjK/uOdHXbAo4= github.com/json-iterator/go v1.1.11/go.mod h1:KdQUCv79m/52Kvf8AW2vK1V8akMuk1QjK/uOdHXbAo4= github.com/json-iterator/go v1.1.12 h1:PV8peI4a0ysnczrg+LtxykD8LfKY9ML6u2jnxaEnrnM= @@ -529,8 +553,10 @@ github.com/karrick/godirwalk v1.8.0/go.mod h1:H5KPZjojv4lE+QYImBI8xVtrBRgYrIVsaR github.com/karrick/godirwalk v1.10.3/go.mod h1:RoGL9dQei4vP9ilrpETWE8CLOZ1kiN0LhBygSwrAsHA= github.com/karrick/godirwalk v1.16.1 h1:DynhcF+bztK8gooS0+NDJFrdNZjJ3gzVzC545UNA9iw= github.com/karrick/godirwalk v1.16.1/go.mod h1:j4mkqPuvaLI8mp1DroR3P6ad7cyYd4c1qeJ3RV7ULlk= +github.com/kisielk/errcheck v1.2.0/go.mod h1:/BMXB+zMLi60iA8Vv6Ksmxu/1UDYcXs4uQLJ+jE2L00= github.com/kisielk/errcheck v1.5.0/go.mod h1:pFxgyoBC7bSaBwPgfKdkLd5X25qrDl4LWUI2bnpBCr8= github.com/kisielk/gotool v1.0.0/go.mod h1:XhKaO+MFFWcvkIS/tQcRk01m1F5IRFswLeQ+oQHNcck= +github.com/klauspost/compress v1.9.5/go.mod h1:RyIbtBH6LamlWaDj8nUwkbUhJ87Yi3uG0guNDohfE1A= github.com/klauspost/compress v1.13.6 h1:P76CopJELS0TiO2mebmnzgWaajssP/EszplttgQxcgc= github.com/klauspost/compress v1.13.6/go.mod h1:/3/Vjq9QcHkK5uEr5lBEmyoZ1iFhe47etQ6QUkpK6sk= github.com/konsorten/go-windows-terminal-sequences v1.0.1/go.mod h1:T0+1ngSBFLxvqU3pZ+m/2kptfBszLMUkC4ZK/EgS/cQ= @@ -541,9 +567,10 @@ github.com/kr/fs v0.1.0/go.mod h1:FFnZGqtBN9Gxj7eW1uZ42v5BccTP0vu6NEaFoC2HwRg= github.com/kr/logfmt v0.0.0-20140226030751-b84e30acd515/go.mod h1:+0opPa2QZZtGFBFZlji/RkVcI2GknAs/DXo4wKdlNEc= github.com/kr/pretty v0.1.0/go.mod h1:dAy3ld7l9f0ibDNOQOHHMYYIIbhfbHSm3C4ZsoJORNo= github.com/kr/pretty v0.2.0/go.mod h1:ipq/a2n7PKx3OHsz4KJII5eveXtPO4qwEXGdVfWzfnI= +github.com/kr/pretty v0.2.1 h1:Fmg33tUaq4/8ym9TJN1x7sLJnHVwhP33CNkpYV/7rwI= github.com/kr/pretty v0.2.1/go.mod h1:ipq/a2n7PKx3OHsz4KJII5eveXtPO4qwEXGdVfWzfnI= -github.com/kr/pretty v0.3.1 h1:flRD4NNwYAUpkphVc1HcthR4KEIFJ65n8Mw5qdRn3LE= github.com/kr/pty v1.1.1/go.mod h1:pFQYn66WHrOpPYNljwOMqo10TkYh1fy3cYio2l3bCsQ= +github.com/kr/pty v1.1.5/go.mod h1:9r2w37qlBe7rQ6e1fg1S/9xpWHSnaqNdHD3WcMdbPDA= github.com/kr/text v0.1.0/go.mod h1:4Jbv+DJW3UT/LiOwJeYQe1efqtUx/iVham/4vfdArNI= github.com/kr/text v0.2.0 h1:5Nx0Ya0ZqY2ygV366QzturHI13Jq95ApcVaJBhpS+AY= github.com/kr/text v0.2.0/go.mod h1:eLer722TekiGuMkidMxC/pM04lWEeraHUUmBw8l2grE= @@ -553,18 +580,20 @@ github.com/lann/ps v0.0.0-20150810152359-62de8c46ede0 h1:P6pPBnrTSX3DEVR4fDembhR github.com/lann/ps v0.0.0-20150810152359-62de8c46ede0/go.mod h1:vmVJ0l/dxyfGW6FmdpVm2joNMFikkuWg0EoCKLGUMNw= github.com/lib/pq v1.2.0/go.mod h1:5WUZQaWbwv1U+lTReE5YruASi9Al49XbQIvNi/34Woo= github.com/lib/pq v1.10.0/go.mod h1:AlVN5x4E4T544tWzH6hKfbfQvm3HdbOxrmggDNAPY9o= -github.com/lib/pq v1.10.7 h1:p7ZhMD+KsSRozJr34udlUrhboJwWAgCg34+/ZZNvZZw= -github.com/lib/pq v1.10.7/go.mod h1:AlVN5x4E4T544tWzH6hKfbfQvm3HdbOxrmggDNAPY9o= +github.com/lib/pq v1.10.6 h1:jbk+ZieJ0D7EVGJYpL9QTz7/YW6UHbmdnZWYyK5cdBs= +github.com/lib/pq v1.10.6/go.mod h1:AlVN5x4E4T544tWzH6hKfbfQvm3HdbOxrmggDNAPY9o= github.com/liggitt/tabwriter v0.0.0-20181228230101-89fcab3d43de h1:9TO3cAIGXtEhnIaL+V+BEER86oLrvS+kWobKpbJuye0= github.com/liggitt/tabwriter v0.0.0-20181228230101-89fcab3d43de/go.mod h1:zAbeS9B/r2mtpb6U+EI2rYA5OAXxsYw6wTamcNW+zcE= github.com/lithammer/dedent v1.1.0/go.mod h1:jrXYCQtgg0nJiN+StA2KgR7w6CiQNv9Fd/Z9BP0jIOc= github.com/magiconair/properties v1.8.5/go.mod h1:y3VJvCyxH9uVvJTWEGAELF3aiYNyPKd5NZ3oSwXrF60= +github.com/mailru/easyjson v0.0.0-20180823135443-60711f1a8329/go.mod h1:C1wdFJiN94OJF2b5HbByQZoLdCWB1Yqtg26g4irojpc= +github.com/mailru/easyjson v0.0.0-20190312143242-1de009706dbe/go.mod h1:C1wdFJiN94OJF2b5HbByQZoLdCWB1Yqtg26g4irojpc= github.com/mailru/easyjson v0.0.0-20190614124828-94de47d64c63/go.mod h1:C1wdFJiN94OJF2b5HbByQZoLdCWB1Yqtg26g4irojpc= github.com/mailru/easyjson v0.0.0-20190626092158-b2ccc519800e/go.mod h1:C1wdFJiN94OJF2b5HbByQZoLdCWB1Yqtg26g4irojpc= github.com/mailru/easyjson v0.7.0/go.mod h1:KAzv3t3aY1NaHWoQz1+4F1ccyAH66Jk7yos7ldAVICs= +github.com/mailru/easyjson v0.7.1/go.mod h1:KAzv3t3aY1NaHWoQz1+4F1ccyAH66Jk7yos7ldAVICs= +github.com/mailru/easyjson v0.7.6 h1:8yTIVnZgCoiM1TgqoeTl+LfU5Jg6/xL3QhGQnimLYnA= github.com/mailru/easyjson v0.7.6/go.mod h1:xzfreul335JAWq5oZzymOObrkdz5UnU4kGfJJLY9Nlc= -github.com/mailru/easyjson v0.7.7 h1:UGYAvKxe3sBsEDzO8ZeWOSlIQfWFlxbzLZe7hwFURr0= -github.com/mailru/easyjson v0.7.7/go.mod h1:xzfreul335JAWq5oZzymOObrkdz5UnU4kGfJJLY9Nlc= github.com/markbates/errx v1.1.0 h1:QDFeR+UP95dO12JgW+tgi2UVfo0V8YBHiUIOaeBPiEI= github.com/markbates/errx v1.1.0/go.mod h1:PLa46Oex9KNbVDZhKel8v1OT7hD5JZ2eI7AHhA0wswc= github.com/markbates/oncer v0.0.0-20181203154359-bf2de49a0be2/go.mod h1:Ld9puTsIW75CHf65OeIOkyKbteujpZVXDpWK6YGZbxE= @@ -574,34 +603,27 @@ github.com/markbates/safe v1.0.1 h1:yjZkbvRM6IzKj9tlu/zMJLS0n/V351OZWRnF3QfaUxI= github.com/markbates/safe v1.0.1/go.mod h1:nAqgmRi7cY2nqMc92/bSEeQA+R4OheNU2T1kNSCBdG0= github.com/mattn/go-colorable v0.0.9/go.mod h1:9vuHe8Xs5qXnSaW/c/ABM9alt+Vo+STaOChaDxuIBZU= github.com/mattn/go-colorable v0.1.4/go.mod h1:U0ppj6V5qS13XJ6of8GYAs25YV2eR4EVcfRqFIhoBtE= -github.com/mattn/go-colorable v0.1.6/go.mod h1:u6P/XSegPjTcexA+o6vUJrdnUu04hMope9wVRipJSqc= github.com/mattn/go-colorable v0.1.9/go.mod h1:u6P/XSegPjTcexA+o6vUJrdnUu04hMope9wVRipJSqc= +github.com/mattn/go-colorable v0.1.12 h1:jF+Du6AlPIjs2BiUiQlKOX0rt3SujHxPnksPKZbaA40= github.com/mattn/go-colorable v0.1.12/go.mod h1:u5H1YNBxpqRaxsYJYSkiCWKzEfiAb1Gb520KVy5xxl4= -github.com/mattn/go-colorable v0.1.13 h1:fFA4WZxdEF4tXPZVKMLwD8oUnCTTo08duU7wxecdEvA= -github.com/mattn/go-colorable v0.1.13/go.mod h1:7S9/ev0klgBDR4GtXTXX8a3vIGJpMovkB8vQcUbaXHg= github.com/mattn/go-isatty v0.0.3/go.mod h1:M+lRXTBqGeGNdLjl/ufCoiOlB5xdOkqRJdNxMWT7Zi4= github.com/mattn/go-isatty v0.0.8/go.mod h1:Iq45c/XA43vh69/j3iqttzPXn0bhXyGjM0Hdxcsrc5s= -github.com/mattn/go-isatty v0.0.11/go.mod h1:PhnuNfih5lzO57/f3n+odYbM4JtupLOxQOAqxQCu2WE= +github.com/mattn/go-isatty v0.0.10/go.mod h1:qgIWMr58cqv1PHHyhnkY9lrL7etaEgOFcMEpPG5Rm84= github.com/mattn/go-isatty v0.0.12/go.mod h1:cbi8OIDigv2wuxKPP5vlRcQ1OAZbq2CE4Kysco4FUpU= +github.com/mattn/go-isatty v0.0.14 h1:yVuAays6BHfxijgZPzw+3Zlu5yQgKGP2/hcQbHb7S9Y= github.com/mattn/go-isatty v0.0.14/go.mod h1:7GGIvUiUoEMVVmxf/4nioHXj79iQHKdU27kJ6hsGG94= -github.com/mattn/go-isatty v0.0.16 h1:bq3VjFmv/sOjHtdEhmkEV4x1AJtvUvOJ2PFAZ5+peKQ= -github.com/mattn/go-isatty v0.0.16/go.mod h1:kYGgaQfpe5nmfYZH+SKPsOc2e4SrIfOl2e/yFXSvRLM= github.com/mattn/go-oci8 v0.1.1/go.mod h1:wjDx6Xm9q7dFtHJvIlrI99JytznLw5wQ4R+9mNXJwGI= github.com/mattn/go-runewidth v0.0.7/go.mod h1:H031xJmbD/WCDINGzjvQ9THkh0rPKHF+m2gUSrubnMI= github.com/mattn/go-runewidth v0.0.9 h1:Lm995f3rfxdpd6TSmuVCHVb/QhupuXlYr8sCI/QdE+0= github.com/mattn/go-runewidth v0.0.9/go.mod h1:H031xJmbD/WCDINGzjvQ9THkh0rPKHF+m2gUSrubnMI= github.com/mattn/go-sqlite3 v1.11.0/go.mod h1:FPy6KqzDD04eiIsT53CuJW3U88zkxoIYsOqkbpncsNc= +github.com/mattn/go-sqlite3 v1.14.6 h1:dNPt6NO46WmLVt2DLNpwczCmdV5boIZ6g/tlDrlRUbg= github.com/mattn/go-sqlite3 v1.14.6/go.mod h1:NyWgC/yNuGj7Q9rpYnZvas74GogHl5/Z4A/KQRfk6bU= -github.com/mattn/go-sqlite3 v1.14.15 h1:vfoHhTN1af61xCRSWzFIWzx2YskyMTwHLrExkBOjvxI= github.com/matttproud/golang_protobuf_extensions v1.0.1/go.mod h1:D8He9yQNgCq6Z5Ld7szi9bcBfOoFv/3dc6xSMkL2PC0= github.com/matttproud/golang_protobuf_extensions v1.0.2-0.20181231171920-c182affec369 h1:I0XW9+e1XWDxdcEniV4rQAIOPUGDq67JSCiRCgGCZLI= github.com/matttproud/golang_protobuf_extensions v1.0.2-0.20181231171920-c182affec369/go.mod h1:BSXmuO+STAnVfrANrmjBb36TMTDstsz7MSK+HVaYKv4= github.com/miekg/dns v1.0.14/go.mod h1:W1PPwlIAgtquWBMBEV9nkV9Cazfe8ScdGz/Lj7v3Nrg= -github.com/miekg/dns v1.1.26/go.mod h1:bPDLeHnStXmXAq1m/Ch/hvfNHr14JKNPMBo3VZKjuso= -github.com/miekg/dns v1.1.41 h1:WMszZWJG0XmzbK9FEmzH2TVcqYzFesusSIB41b8KHxY= -github.com/miekg/dns v1.1.41/go.mod h1:p6aan82bvRIyn+zDIv9xYNUpwa73JcSh9BKwknJysuI= github.com/mitchellh/cli v1.0.0/go.mod h1:hNIlj7HEI86fIcpObd7a0FcrxTWetlwJDGcceTlRvqc= -github.com/mitchellh/cli v1.1.0/go.mod h1:xcISNoH86gajksDmfB23e/pu+B+GeFRMYmoHXxx3xhI= github.com/mitchellh/cli v1.1.2 h1:PvH+lL2B7IQ101xQL63Of8yFS2y+aDlsFcsqNc+u/Kw= github.com/mitchellh/cli v1.1.2/go.mod h1:6iaV0fGdElS6dPBx0EApTxHrcWvmJphyh2n8YBLPPZ4= github.com/mitchellh/colorstring v0.0.0-20190213212951-d06e56a500db h1:62I3jR2EmQ4l5rM/4FEfDWcRD+abF5XlKShorW5LRoQ= @@ -610,8 +632,6 @@ github.com/mitchellh/copystructure v1.0.0/go.mod h1:SNtv71yrdKgLRyLFxmLdkAbkKEFW github.com/mitchellh/copystructure v1.2.0 h1:vpKXTN4ewci03Vljg/q9QvCGUDttBOGBIa15WveJJGw= github.com/mitchellh/copystructure v1.2.0/go.mod h1:qLl+cE2AmVv+CoeAwDPye/v+N2HKCj9FbZEVFJRxO9s= github.com/mitchellh/go-homedir v1.0.0/go.mod h1:SfyaCUpYCn1Vlf4IUYiD9fPX4A5wJrkLzIz1N1q0pr0= -github.com/mitchellh/go-homedir v1.1.0 h1:lukF9ziXFxDFPkA1vsr5zpc1XuPDn/wFntq5mG+4E0Y= -github.com/mitchellh/go-homedir v1.1.0/go.mod h1:SfyaCUpYCn1Vlf4IUYiD9fPX4A5wJrkLzIz1N1q0pr0= github.com/mitchellh/go-testing-interface v1.0.0/go.mod h1:kRemZodwjscx+RGhAo8eIhFbs2+BFgRtFPeD/KE+zxI= github.com/mitchellh/go-wordwrap v1.0.0/go.mod h1:ZXFpozHsX6DPmq2I0TCekCxypsnAUbP2oI0UX1GXzOo= github.com/mitchellh/go-wordwrap v1.0.1 h1:TLuKupo69TCn6TQSyGxwI1EblZZEsQ0vMlAFQflz0v0= @@ -620,11 +640,11 @@ github.com/mitchellh/gox v0.4.0/go.mod h1:Sd9lOJ0+aimLBi73mGofS1ycjY8lL3uZM3JPS4 github.com/mitchellh/iochan v1.0.0/go.mod h1:JwYml1nuB7xOzsp52dPpHFffvOCDupsG0QubkSMEySY= github.com/mitchellh/mapstructure v0.0.0-20160808181253-ca63d7c062ee/go.mod h1:FVVH3fgwuzCH5S8UJGiWEs2h04kUh9fWfEaFds41c1Y= github.com/mitchellh/mapstructure v1.1.2/go.mod h1:FVVH3fgwuzCH5S8UJGiWEs2h04kUh9fWfEaFds41c1Y= +github.com/mitchellh/mapstructure v1.3.2/go.mod h1:bFUtVrKA4DC2yAKiSyO/QUcy7e+RRV2QTWOzhPopBRo= github.com/mitchellh/mapstructure v1.3.3/go.mod h1:bFUtVrKA4DC2yAKiSyO/QUcy7e+RRV2QTWOzhPopBRo= +github.com/mitchellh/mapstructure v1.4.0/go.mod h1:bFUtVrKA4DC2yAKiSyO/QUcy7e+RRV2QTWOzhPopBRo= +github.com/mitchellh/mapstructure v1.4.1 h1:CpVNEelQCZBooIPDn+AR3NpivK/TIKU8bDxdASFVQag= github.com/mitchellh/mapstructure v1.4.1/go.mod h1:bFUtVrKA4DC2yAKiSyO/QUcy7e+RRV2QTWOzhPopBRo= -github.com/mitchellh/mapstructure v1.4.3/go.mod h1:bFUtVrKA4DC2yAKiSyO/QUcy7e+RRV2QTWOzhPopBRo= -github.com/mitchellh/mapstructure v1.5.0 h1:jeMsZIYE/09sWLaz43PL7Gy6RuMjD2eJVyuac5Z2hdY= -github.com/mitchellh/mapstructure v1.5.0/go.mod h1:bFUtVrKA4DC2yAKiSyO/QUcy7e+RRV2QTWOzhPopBRo= github.com/mitchellh/reflectwalk v1.0.0/go.mod h1:mSTlrgnPZtwu0c4WaC2kGObEpuNDbx0jmZXqmk4esnw= github.com/mitchellh/reflectwalk v1.0.2 h1:G2LzWKi524PWgd3mLHV8Y5k7s6XUvT0Gef6zxSIeXaQ= github.com/mitchellh/reflectwalk v1.0.2/go.mod h1:mSTlrgnPZtwu0c4WaC2kGObEpuNDbx0jmZXqmk4esnw= @@ -657,8 +677,6 @@ github.com/niemeyer/pretty v0.0.0-20200227124842-a10e7caefd8e/go.mod h1:zD1mROLA github.com/nxadm/tail v1.4.4/go.mod h1:kenIhsEOeOJmVchQTgglprH7qJGnHDVpk1VPCcaMI8A= github.com/nxadm/tail v1.4.8 h1:nPr65rt6Y5JFSKQO7qToXr7pePgD6Gwiw05lkbyAQTE= github.com/nxadm/tail v1.4.8/go.mod h1:+ncqLTQzXmGhMZNUePPaPqPvBxHAIsmXswZKocGu+AU= -github.com/oklog/ulid v1.3.1 h1:EGfNDEx6MqHz8B3uNV6QAib1UR2Lm97sHi3ocA6ESJ4= -github.com/oklog/ulid v1.3.1/go.mod h1:CirwcVhetQ6Lv90oh/F+FBtV6XMibvdAFo93nm5qn4U= github.com/olekukonko/tablewriter v0.0.4/go.mod h1:zq6QwlOf5SlnkVbMSr5EoBv3636FWnp+qbPhuoO21uA= github.com/olekukonko/tablewriter v0.0.5 h1:P2Ga83D34wi1o9J6Wh1mRuqd4mF/x/lgBS7N7AbDhec= github.com/olekukonko/tablewriter v0.0.5/go.mod h1:hPp6KlRPjbx+hW8ykQs1w3UBbZlj6HuIJcUGPhkA7kY= @@ -677,11 +695,9 @@ github.com/opencontainers/go-digest v1.0.0 h1:apOUWs51W5PlhuyGyz9FCeeBIOUDA/6nW8 github.com/opencontainers/go-digest v1.0.0/go.mod h1:0JzlMkj0TRzQZfJkVvzbP0HBR3IKzErnv2BNG4W4MAM= github.com/opencontainers/image-spec v1.0.3-0.20211202183452-c5a74bcca799 h1:rc3tiVYb5z54aKaDfakKn0dDjIyPpTtszkjuMzyt7ec= github.com/opencontainers/image-spec v1.0.3-0.20211202183452-c5a74bcca799/go.mod h1:BtxoFyWECRxE4U/7sNtV5W15zMzWCbyJoFRP3s7yZA0= -github.com/opentracing/opentracing-go v1.2.0 h1:uEJPy/1a5RIPAJ0Ov+OIO8OxWu77jEv+1B0VhjKrZUs= -github.com/opentracing/opentracing-go v1.2.0/go.mod h1:GxEUsuufX4nBwe+T+Wl9TAgYrxe9dPLANfrWvHYVTgc= github.com/pascaldekloe/goe v0.0.0-20180627143212-57f6aae5913c/go.mod h1:lzWF7FIEvWOWxwDKqyGYQf6ZUaNfKdP144TG7ZOy1lc= -github.com/pascaldekloe/goe v0.1.0 h1:cBOtyMzM9HTpWjXfbbunk26uA6nG3a8n06Wieeh0MwY= -github.com/pascaldekloe/goe v0.1.0/go.mod h1:lzWF7FIEvWOWxwDKqyGYQf6ZUaNfKdP144TG7ZOy1lc= +github.com/pborman/uuid v1.2.0/go.mod h1:X/NO0urCmaxf9VXbdlT7C2Yzkj2IKimNn4k+gtPdI/k= +github.com/pelletier/go-toml v1.4.0/go.mod h1:PN7xzY2wHTK0K9p34ErDQMlFxa51Fk0OUruD3k1mMwo= github.com/pelletier/go-toml v1.7.0/go.mod h1:vwGMzjaWMwyfHwgIBhI2YUM4fB6nL6lVAvS1LBMMhTE= github.com/pelletier/go-toml v1.9.3/go.mod h1:u1nR/EPcESfeI/szUZKdtJ0xRNbUoANCkoOuaOx1Y+c= github.com/peterbourgon/diskv v2.0.1+incompatible h1:UBdAOUP5p4RWqPBg048CAvpKN+vxiaj6gdUUzhl4XmI= @@ -693,18 +709,16 @@ github.com/pkg/errors v0.8.1/go.mod h1:bwawxfHBFNV+L2hUp1rHADufV3IMtnDRdf1r5NINE github.com/pkg/errors v0.9.1 h1:FEBLx1zS214owpjy7qsBeixbURkuhQAwrK5UwLGTwt4= github.com/pkg/errors v0.9.1/go.mod h1:bwawxfHBFNV+L2hUp1rHADufV3IMtnDRdf1r5NINEl0= github.com/pkg/sftp v1.10.1/go.mod h1:lYOWFsE0bwd1+KfKJaKeuokY15vzFx25BLbzYYoAxZI= +github.com/pmezard/go-difflib v1.0.0 h1:4DBwDE0NGyQoBHbLQYPwSUPoCMWR5BEzIk/f1lZbAQM= github.com/pmezard/go-difflib v1.0.0/go.mod h1:iKH77koFhYxTK1pcRnkKkqfTogsbg7gZNVY4sRDYZ/4= -github.com/pmezard/go-difflib v1.0.1-0.20181226105442-5d4384ee4fb2 h1:Jamvg5psRIccs7FGNTlIRMkT8wgtp5eCXdBlqhYGL6U= -github.com/pmezard/go-difflib v1.0.1-0.20181226105442-5d4384ee4fb2/go.mod h1:iKH77koFhYxTK1pcRnkKkqfTogsbg7gZNVY4sRDYZ/4= github.com/posener/complete v1.1.1/go.mod h1:em0nMJCgc9GFtwrmVmEMR/ZL6WyhyjMBndrE9hABlRI= github.com/posener/complete v1.2.3 h1:NP0eAhjcjImqslEwo/1hq7gpajME0fTLTezBKDqfXqo= github.com/posener/complete v1.2.3/go.mod h1:WZIdtGGp+qx0sLrYKtIRAruyNpv6hFCicSgv7Sy7s/s= +github.com/poy/onpar v0.0.0-20190519213022-ee068f8ea4d1 h1:oL4IBbcqwhhNWh31bjOX8C/OCy0zs9906d/VUru+bqg= github.com/poy/onpar v0.0.0-20190519213022-ee068f8ea4d1/go.mod h1:nSbFQvMj97ZyhFRSJYtut+msi4sOY6zJDGCdSc+/rZU= -github.com/poy/onpar v1.1.2 h1:QaNrNiZx0+Nar5dLgTVp5mXkyoVFIbepjyEoGSnhbAY= github.com/prometheus/client_golang v0.9.1/go.mod h1:7SWBe2y4D6OKWSNQJUaRYU/AaXPKyh/dDVn+NZz0KFw= github.com/prometheus/client_golang v1.0.0/go.mod h1:db9x61etRT2tGnBNRi70OPL5FsnadC4Ky3P0J6CfImo= github.com/prometheus/client_golang v1.1.0/go.mod h1:I1FGZT9+L76gKKOs5djB6ezCbFQP1xR9D75/vuwEF3g= -github.com/prometheus/client_golang v1.4.0/go.mod h1:e9GMxYsXl05ICDXkRhurwBS4Q3OK1iX/F2sw+iXX5zU= github.com/prometheus/client_golang v1.7.1/go.mod h1:PY5Wy2awLA44sXw4AOSfFBetzPP4j5+D6mVACh+pe2M= github.com/prometheus/client_golang v1.11.0/go.mod h1:Z6t4BnS23TR94PD6BsDNk8yVqroYurpAkEiz0P2BEV0= github.com/prometheus/client_golang v1.12.1/go.mod h1:3Z9XVyYiZYEO+YQWt3RD2R3jrbd179Rt297l4aS6nDY= @@ -717,7 +731,6 @@ github.com/prometheus/client_model v0.2.0 h1:uq5h0d+GuxiXLJLNABMgp2qUWDPiLvgCzz2 github.com/prometheus/client_model v0.2.0/go.mod h1:xMI15A0UPsDsEKsMN9yxemIoYk6Tm2C1GtYGdfGttqA= github.com/prometheus/common v0.4.1/go.mod h1:TNfzLD0ON7rHzMJeJkieUDPYmFC7Snx/y86RQel1bk4= github.com/prometheus/common v0.6.0/go.mod h1:eBmuwkDJBwy6iBfxCBob6t6dR6ENT/y+J+Zk0j9GMYc= -github.com/prometheus/common v0.9.1/go.mod h1:yhUN8i9wzaXS3w1O07YhxHEBxD+W35wd8bs7vj7HSQ4= github.com/prometheus/common v0.10.0/go.mod h1:Tlit/dnDKsSWFlCLTWaA1cyBgKHSMdTB80sz/V91rCo= github.com/prometheus/common v0.26.0/go.mod h1:M7rCNAaPfAosfx8veZJCuw84e35h3Cfd9VFqTh1DIvc= github.com/prometheus/common v0.32.1 h1:hWIdL3N2HoUx3B8j3YN9mWor0qhY/NlEKZEaXxuIRh4= @@ -725,7 +738,6 @@ github.com/prometheus/common v0.32.1/go.mod h1:vu+V0TpY+O6vW9J44gczi3Ap/oXXR10b+ github.com/prometheus/procfs v0.0.0-20181005140218-185b4288413d/go.mod h1:c3At6R/oaqEKCNdg8wHV1ftS6bRYblBhIjjI8uT2IGk= github.com/prometheus/procfs v0.0.2/go.mod h1:TjEm7ze935MbeOT/UhFTIMYKhuLP4wbCsTZCD3I8kEA= github.com/prometheus/procfs v0.0.3/go.mod h1:4A/X28fw3Fc593LaREMrKMqOKvUAntwMDaekg4FpcdQ= -github.com/prometheus/procfs v0.0.8/go.mod h1:7Qr8sr6344vo1JqZ6HhLceV9o3AJ1Ff+GxbHq6oeK9A= github.com/prometheus/procfs v0.1.3/go.mod h1:lV6e/gmhEcM9IjHGsFOCxxuZ+z1YqCvr4OA4YeYWdaU= github.com/prometheus/procfs v0.6.0/go.mod h1:cz+aTbrPOrUb4q7XlbU9ygM+/jj0fzG6c1xBZuNvfVA= github.com/prometheus/procfs v0.7.3 h1:4jVXhlkAyzOScmCkXBTOLRLTz8EeU+eyjrwB/EPq0VU= @@ -734,7 +746,6 @@ github.com/rogpeppe/fastuuid v1.2.0/go.mod h1:jVj6XXZzXRy/MSR5jhDC/2q6DgLz+nrA6L github.com/rogpeppe/go-internal v1.1.0/go.mod h1:M8bDsm7K2OlrFYOpmOWEs/qY81heoFRclV5y23lUDJ4= github.com/rogpeppe/go-internal v1.2.2/go.mod h1:M8bDsm7K2OlrFYOpmOWEs/qY81heoFRclV5y23lUDJ4= github.com/rogpeppe/go-internal v1.3.0/go.mod h1:M8bDsm7K2OlrFYOpmOWEs/qY81heoFRclV5y23lUDJ4= -github.com/rogpeppe/go-internal v1.8.0 h1:FCbCCtXNOY3UtUuHUYaghJg4y7Fd14rXifAYUAtL9R8= github.com/rogpeppe/go-internal v1.8.0/go.mod h1:WmiCO8CzOY8rg0OYDC4/i/2WRWAB6poM+XZ2dLUbcbE= github.com/rubenv/sql-migrate v1.1.1 h1:haR5Hn8hbW9/SpAICrXoZqXnywS7Q5WijwkQENPeNWY= github.com/rubenv/sql-migrate v1.1.1/go.mod h1:/7TZymwxN8VWumcIxw1jjHEcR1djpdkMHQPT4FWdnbQ= @@ -743,8 +754,8 @@ github.com/russross/blackfriday v1.5.2/go.mod h1:JO/DiYxRf+HjHt06OyowR9PTA263kcR github.com/russross/blackfriday/v2 v2.0.1/go.mod h1:+Rmxgy9KzJVeS9/2gXHxylqXiyQDYRxCVz55jmeOWTM= github.com/russross/blackfriday/v2 v2.1.0/go.mod h1:+Rmxgy9KzJVeS9/2gXHxylqXiyQDYRxCVz55jmeOWTM= github.com/ryanuber/columnize v0.0.0-20160712163229-9b3edd62028f/go.mod h1:sm1tb6uqfes/u+d4ooFouqFdy9/2g9QGwK3SQygK0Ts= -github.com/sean-/seed v0.0.0-20170313163322-e2103e2c3529 h1:nn5Wsu0esKSJiIVhscUtVbo7ada43DJhG55ua/hjS5I= github.com/sean-/seed v0.0.0-20170313163322-e2103e2c3529/go.mod h1:DxrIzT+xaE7yg65j358z/aeFdxmN0P9QXhEzd20vsDc= +github.com/sergi/go-diff v1.0.0/go.mod h1:0CfEIISq7TuYL3j771MWULgwwjU+GofnZX9QAmXWZgo= github.com/sergi/go-diff v1.1.0 h1:we8PVUC3FE2uYfodKH/nBHMSetSfHDR6scGdBi+erh0= github.com/sergi/go-diff v1.1.0/go.mod h1:STckp+ISIX8hZLjrqAeVduY0gWCT9IjLuqbuNXdaHfM= github.com/shopspring/decimal v1.2.0 h1:abSATXmQEYyShuxI4/vyW3tV1MrKAJzCZ/0zLUXYbsQ= @@ -780,28 +791,22 @@ github.com/spf13/viper v1.8.1/go.mod h1:o0Pch8wJ9BVSWGQMbra6iw0oQ5oktSIBaujf1rJH github.com/stoewer/go-strcase v1.2.0/go.mod h1:IBiWB2sKIp3wVVQ3Y035++gc+knqhUQag1KpM8ahLw8= github.com/stretchr/objx v0.1.0/go.mod h1:HFkY916IF+rwdDfMAkV7OtwuqBVzrE8GR6GFx+wExME= github.com/stretchr/objx v0.1.1/go.mod h1:HFkY916IF+rwdDfMAkV7OtwuqBVzrE8GR6GFx+wExME= +github.com/stretchr/objx v0.2.0 h1:Hbg2NidpLE8veEBkEZTL3CvlkUIVzuU9jDplZO54c48= github.com/stretchr/objx v0.2.0/go.mod h1:qt09Ya8vawLte6SNmTgCsAVtYtaKzEcn8ATUoHMkEqE= -github.com/stretchr/objx v0.4.0 h1:M2gUjqZET1qApGOWNSnZ49BAIMX4F/1plDv3+l31EJ4= -github.com/stretchr/objx v0.4.0/go.mod h1:YvHI0jy2hoMjB+UWwv71VJQ9isScKT/TqJzVSSt89Yw= github.com/stretchr/testify v1.2.2/go.mod h1:a8OnRcib4nhh0OaRAV+Yts87kKdq0PP7pXfy6kDkUVs= github.com/stretchr/testify v1.3.0/go.mod h1:M5WIy9Dh21IEIfnGCwXGc5bZfKNJtfHm1UVUgZn+9EI= github.com/stretchr/testify v1.4.0/go.mod h1:j7eGeouHqKxXV5pUuKE4zz7dFj8WfuZ+81PSLYec5m4= github.com/stretchr/testify v1.5.1/go.mod h1:5W2xD1RspED5o8YsWQXVCued0rvSQ+mT+I5cxcmMvtA= github.com/stretchr/testify v1.6.1/go.mod h1:6Fq8oRcR53rry900zMqJjRRixrwX3KX962/h/Wwjteg= github.com/stretchr/testify v1.7.0/go.mod h1:6Fq8oRcR53rry900zMqJjRRixrwX3KX962/h/Wwjteg= -github.com/stretchr/testify v1.7.1/go.mod h1:6Fq8oRcR53rry900zMqJjRRixrwX3KX962/h/Wwjteg= +github.com/stretchr/testify v1.7.2 h1:4jaiDzPyXQvSd7D0EjG45355tLlV3VOECpq10pLC+8s= github.com/stretchr/testify v1.7.2/go.mod h1:R6va5+xMeoiuVRoj+gSkQ7d3FALtqAAGI1FQKckRals= -github.com/stretchr/testify v1.8.0 h1:pSgiaMZlXftHpm5L7V1+rVB+AZJydKsMxsQBIJw4PKk= -github.com/stretchr/testify v1.8.0/go.mod h1:yNjHg4UonilssWZ8iaSj1OCr/vHnekPRkoO+kdMU+MU= github.com/subosito/gotenv v1.2.0/go.mod h1:N0PQaV/YGNqwC0u51sEeR/aUtSLEXKX9iv69rRypqCw= github.com/tidwall/pretty v1.0.0 h1:HsD+QiTn7sK6flMKIvNmpqz1qrpP3Ps6jOKIKMooyg4= github.com/tidwall/pretty v1.0.0/go.mod h1:XNkn88O1ChpSDQmQeStsy+sBenx6DDtFZJxhVysOjyk= -github.com/tv42/httpunix v0.0.0-20150427012821-b75d8614f926/go.mod h1:9ESjWnEqriFuLhtthL60Sar/7RFoluCcXsuvEwTV5KM= -github.com/xdg-go/pbkdf2 v1.0.0/go.mod h1:jrpuAogTd400dnrH08LKmI/xc1MbPOebTwRqcT5RDeI= -github.com/xdg-go/scram v1.0.2/go.mod h1:1WAq6h33pAW+iRreB34OORO2Nf7qel3VV3fjBj+hCSs= -github.com/xdg-go/scram v1.1.1/go.mod h1:RaEWvsqvNKKvBPvcKeFjrG2cJqOkHTiyTpzz23ni57g= -github.com/xdg-go/stringprep v1.0.2/go.mod h1:8F9zXuvzgwmyT5DUm4GUfZGDdT3W+LCvS6+da4O5kxM= -github.com/xdg-go/stringprep v1.0.3/go.mod h1:W3f5j4i+9rC0kuIEJL0ky1VpHXQU3ocBgklLGvcBnW8= +github.com/vektah/gqlparser v1.1.2/go.mod h1:1ycwN7Ij5njmMkPPAOaRFY4rET2Enx7IkVv3vaXspKw= +github.com/xdg/scram v0.0.0-20180814205039-7eeb5667e42c/go.mod h1:lB8K/P019DLNhemzwFU4jHLhdvlE6uDZjXFejJXr49I= +github.com/xdg/stringprep v0.0.0-20180714160509-73f8eece6fdc/go.mod h1:Jhud4/sHMO4oL310DaZAKk9ZaJ08SJfe+sJh0HrGL1Y= github.com/xeipuuv/gojsonpointer v0.0.0-20180127040702-4e3ac2762d5f h1:J9EGpcZtP0E/raorCMxlFGSTBrsSlaDGf3jU/qvAE2c= github.com/xeipuuv/gojsonpointer v0.0.0-20180127040702-4e3ac2762d5f/go.mod h1:N2zxlSyiKSe5eX1tZViRH5QA0qijqEDrYZiPEAiq3wU= github.com/xeipuuv/gojsonreference v0.0.0-20180127040603-bd5ef7bd5415 h1:EzJWgHovont7NscjpAxXsDA8S8BMYve8Y5+7cuRE7R0= @@ -810,7 +815,6 @@ github.com/xeipuuv/gojsonschema v1.2.0 h1:LhYJRs+L4fBtjZUfuSZIKGeVu0QRy8e5Xi7D17 github.com/xeipuuv/gojsonschema v1.2.0/go.mod h1:anYRn/JVcOK2ZgGU+IjEV4nwlhoK5sQluxsYJ78Id3Y= github.com/xlab/treeprint v0.0.0-20181112141820-a009c3971eca h1:1CFlNzQhALwjS9mBAUkycX616GzgsuYUOCHA5+HSlXI= github.com/xlab/treeprint v0.0.0-20181112141820-a009c3971eca/go.mod h1:ce1O1j6UtZfjr22oyGxGLbauSBp2YVXpARAosm7dHBg= -github.com/youmark/pkcs8 v0.0.0-20181117223130-1be2e3e5546d/go.mod h1:rHwXgn7JulP+udvsHwJoVG1YGAP6VLg4y9I5dyZdqmA= github.com/yuin/goldmark v1.1.25/go.mod h1:3hX8gzYuyVAZsxl0MRgGTJEmQBFcNTphYh9decYSb74= github.com/yuin/goldmark v1.1.27/go.mod h1:3hX8gzYuyVAZsxl0MRgGTJEmQBFcNTphYh9decYSb74= github.com/yuin/goldmark v1.1.32/go.mod h1:3hX8gzYuyVAZsxl0MRgGTJEmQBFcNTphYh9decYSb74= @@ -821,16 +825,19 @@ github.com/yuin/goldmark v1.4.1/go.mod h1:mwnBkeHKe2W/ZEtQ+71ViKU8L12m81fl3OWwC1 github.com/yvasiyarov/go-metrics v0.0.0-20140926110328-57bccd1ccd43 h1:+lm10QQTNSBd8DVTNGHx7o/IKu9HYDvLMffDhbyLccI= github.com/yvasiyarov/gorelic v0.0.0-20141212073537-a9bba5b9ab50 h1:hlE8//ciYMztlGpl/VA+Zm1AcTPHYkHJPbHqE6WJUXE= github.com/yvasiyarov/newrelic_platform_go v0.0.0-20140908184405-b21fdbd4370f h1:ERexzlUfuTvpE74urLSbIQW0Z/6hF9t8U4NsJLaioAY= +github.com/ziutek/mymysql v1.5.4 h1:GB0qdRGsTwQSBVYuVShFBKaXSnSnYYC2d9knnE1LHFs= github.com/ziutek/mymysql v1.5.4/go.mod h1:LMSpPZ6DbqWFxNCHW77HeMg9I646SAhApZ/wKdgO/C0= go.etcd.io/etcd/api/v3 v3.5.0/go.mod h1:cbVKeC6lCfl7j/8jBhAK6aIYO9XOjdptoxU/nLQcPvs= go.etcd.io/etcd/client/pkg/v3 v3.5.0/go.mod h1:IJHfcCEKxYu1Os13ZdwCwIUTUVGYTSAM3YSwc9/Ac1g= go.etcd.io/etcd/client/v2 v2.305.0/go.mod h1:h9puh54ZTgAKtEbut2oe9P4L/oqKCVB6xsXlzd7alYQ= -go.mongodb.org/mongo-driver v1.7.3/go.mod h1:NqaYOwnXWr5Pm7AOpO5QFxKJ503nbMse/R79oO62zWg= -go.mongodb.org/mongo-driver v1.7.5/go.mod h1:VXEWRZ6URJIkUq2SCAyapmhH0ZLRBP+FT4xhp5Zvxng= -go.mongodb.org/mongo-driver v1.8.3/go.mod h1:0sQWfOeY63QTntERDJJ/0SuKK0T1uVSgKCuAROlKEPY= -go.mongodb.org/mongo-driver v1.10.0/go.mod h1:wsihk0Kdgv8Kqu1Anit4sfK+22vSFbUrAVEYRhCXrA8= -go.mongodb.org/mongo-driver v1.11.1 h1:QP0znIRTuL0jf1oBQoAoM0C6ZJfBK4kx0Uumtv1A7w8= -go.mongodb.org/mongo-driver v1.11.1/go.mod h1:s7p5vEtfbeR1gYi6pnj3c3/urpbLv2T5Sfd6Rp2HBB8= +go.mongodb.org/mongo-driver v1.0.3/go.mod h1:u7ryQJ+DOzQmeO7zB6MHyr8jkEQvC8vH7qLUO4lqsUM= +go.mongodb.org/mongo-driver v1.1.1/go.mod h1:u7ryQJ+DOzQmeO7zB6MHyr8jkEQvC8vH7qLUO4lqsUM= +go.mongodb.org/mongo-driver v1.3.0/go.mod h1:MSWZXKOynuguX+JSvwP8i+58jYCXxbia8HS3gZBapIE= +go.mongodb.org/mongo-driver v1.3.4/go.mod h1:MSWZXKOynuguX+JSvwP8i+58jYCXxbia8HS3gZBapIE= +go.mongodb.org/mongo-driver v1.4.3/go.mod h1:WcMNYLx/IlOxLe6JRJiv2uXuCz6zBLndR4SoGjYphSc= +go.mongodb.org/mongo-driver v1.4.4/go.mod h1:WcMNYLx/IlOxLe6JRJiv2uXuCz6zBLndR4SoGjYphSc= +go.mongodb.org/mongo-driver v1.4.6 h1:rh7GdYmDrb8AQSkF8yteAus8qYOgOASWDOv1BWqBXkU= +go.mongodb.org/mongo-driver v1.4.6/go.mod h1:WcMNYLx/IlOxLe6JRJiv2uXuCz6zBLndR4SoGjYphSc= go.opencensus.io v0.21.0/go.mod h1:mSImk1erAIZhrmZN+AvHh14ztQfjbGwt4TtuofqLduU= go.opencensus.io v0.22.0/go.mod h1:+kGneAE2xo2IficOXnaByMWTGM9T73dGwxeWcUqIpI8= go.opencensus.io v0.22.2/go.mod h1:yxeiOL68Rb0Xd1ddK5vPZ/oVn4vY4Ynel7k9FzqtOIw= @@ -850,11 +857,9 @@ go.opentelemetry.io/otel/sdk/export/metric v0.20.0/go.mod h1:h7RBNMsDJ5pmI1zExLi go.opentelemetry.io/otel/sdk/metric v0.20.0/go.mod h1:knxiS8Xd4E/N+ZqKmUPf3gTTZ4/0TjTXukfxjzSTpHE= go.opentelemetry.io/otel/trace v0.20.0/go.mod h1:6GjCW8zgDjwGHGa6GkyeB8+/5vjT16gUEi0Nf1iBdgw= go.opentelemetry.io/proto/otlp v0.7.0/go.mod h1:PqfVotwruBrMGOCsRd/89rSnXhoiJIqeYNgFYFoEGnI= -go.opentelemetry.io/proto/otlp v0.11.0 h1:cLDgIBTf4lLOlztkhzAEdQsJ4Lj+i5Wc9k6Nn0K1VyU= -go.opentelemetry.io/proto/otlp v0.11.0/go.mod h1:QpEjXPrNQzrFDZgoTo49dgHR9RYRSrg3NAKnUGl9YpQ= go.starlark.net v0.0.0-20200306205701-8dd3e2ee1dd5/go.mod h1:nmDLcffg48OtT/PSW0Hg7FvpRQsQh5OSqIylirxKC7o= -go.starlark.net v0.0.0-20230128213706-3f75dec8e403 h1:jPeC7Exc+m8OBJUlWbBLh0O5UZPM7yU5W4adnhhbG4U= -go.starlark.net v0.0.0-20230128213706-3f75dec8e403/go.mod h1:jxU+3+j+71eXOW14274+SmmuW82qJzl6iZSeqEtTGds= +go.starlark.net v0.0.0-20200707032745-474f21a9602d h1:uFqwFYlX7d5ZSp+IqhXxct0SybXrTzEBDvb2CkEhPBs= +go.starlark.net v0.0.0-20200707032745-474f21a9602d/go.mod h1:f0znQkUKRrkk36XxWbGjMqQM8wGv/xHBVE2qc3B5oFU= go.uber.org/atomic v1.7.0/go.mod h1:fEN4uk6kAWBTFdckzkM89CLk9XfWZrxpCo0nPH17wJc= go.uber.org/goleak v1.1.10/go.mod h1:8a7PlsEVH3e/a/GLqe5IIrQx6GzcnRmZEufDUTk4A7A= go.uber.org/multierr v1.6.0/go.mod h1:cdWPpRnG4AhwMwsgIHip0KRBQjJy5kYEpYjJxpXp9iU= @@ -863,24 +868,25 @@ go.uber.org/zap v1.19.0/go.mod h1:xg/QME4nWcxGxrpdeYfq7UvYrLh66cuVKdrbD1XF/NI= golang.org/x/crypto v0.0.0-20180904163835-0709b304e793/go.mod h1:6SG95UA2DQfeDnfUPMdvaQW0Q7yPrPDi9nlGo2tz2b4= golang.org/x/crypto v0.0.0-20181029021203-45a5f77698d3/go.mod h1:6SG95UA2DQfeDnfUPMdvaQW0Q7yPrPDi9nlGo2tz2b4= golang.org/x/crypto v0.0.0-20190308221718-c2843e01d9a2/go.mod h1:djNgcEr1/C05ACkg1iLfiJU5Ep61QUkGW8qpdssI0+w= +golang.org/x/crypto v0.0.0-20190320223903-b7391e95e576/go.mod h1:djNgcEr1/C05ACkg1iLfiJU5Ep61QUkGW8qpdssI0+w= golang.org/x/crypto v0.0.0-20190325154230-a5d413f7728c/go.mod h1:djNgcEr1/C05ACkg1iLfiJU5Ep61QUkGW8qpdssI0+w= golang.org/x/crypto v0.0.0-20190422162423-af44ce270edf/go.mod h1:WFFai1msRO1wXaEeE5yQxYXgSfI8pQAWXbQop6sCtWE= golang.org/x/crypto v0.0.0-20190510104115-cbcb75029529/go.mod h1:yigFU9vqHzYiE8UmvKecakEJjdnWj3jj499lnFckfCI= +golang.org/x/crypto v0.0.0-20190530122614-20be4c3c3ed5/go.mod h1:yigFU9vqHzYiE8UmvKecakEJjdnWj3jj499lnFckfCI= golang.org/x/crypto v0.0.0-20190605123033-f99c8df09eb5/go.mod h1:yigFU9vqHzYiE8UmvKecakEJjdnWj3jj499lnFckfCI= +golang.org/x/crypto v0.0.0-20190611184440-5c40567a22f8/go.mod h1:yigFU9vqHzYiE8UmvKecakEJjdnWj3jj499lnFckfCI= +golang.org/x/crypto v0.0.0-20190617133340-57b3e21c3d56/go.mod h1:yigFU9vqHzYiE8UmvKecakEJjdnWj3jj499lnFckfCI= golang.org/x/crypto v0.0.0-20190820162420-60c769a6c586/go.mod h1:yigFU9vqHzYiE8UmvKecakEJjdnWj3jj499lnFckfCI= -golang.org/x/crypto v0.0.0-20190923035154-9ee001bba392/go.mod h1:/lpIB1dKB+9EgE3H3cr1v9wB50oz8l4C4h62xy7jSTY= golang.org/x/crypto v0.0.0-20191011191535-87dc89f01550/go.mod h1:yigFU9vqHzYiE8UmvKecakEJjdnWj3jj499lnFckfCI= -golang.org/x/crypto v0.0.0-20200302210943-78000ba7a073/go.mod h1:LzIPMQfyMNhhGPhUkYOs5KpL4U8rLKemX1yGLhDgUto= golang.org/x/crypto v0.0.0-20200414173820-0848c9571904/go.mod h1:LzIPMQfyMNhhGPhUkYOs5KpL4U8rLKemX1yGLhDgUto= golang.org/x/crypto v0.0.0-20200622213623-75b288015ac9/go.mod h1:LzIPMQfyMNhhGPhUkYOs5KpL4U8rLKemX1yGLhDgUto= golang.org/x/crypto v0.0.0-20200820211705-5c72a883971a/go.mod h1:LzIPMQfyMNhhGPhUkYOs5KpL4U8rLKemX1yGLhDgUto= golang.org/x/crypto v0.0.0-20201002170205-7f63de1d35b0/go.mod h1:LzIPMQfyMNhhGPhUkYOs5KpL4U8rLKemX1yGLhDgUto= -golang.org/x/crypto v0.0.0-20201216223049-8b5274cf687f/go.mod h1:jdWPYTVW3xRLrWPugEBEK3UY2ZEsg3UU495nc5E+M+I= golang.org/x/crypto v0.0.0-20210921155107-089bfa567519/go.mod h1:GvvjBRRGRdwPK5ydBHafDWAxML/pGHZbMvKqRZ5+Abc= golang.org/x/crypto v0.0.0-20211215153901-e495a2d5b3d3/go.mod h1:IxCIyHEi3zRg3s0A5j5BB6A9Jmi73HwBIUl50j+osU4= golang.org/x/crypto v0.0.0-20220214200702-86341886e292/go.mod h1:IxCIyHEi3zRg3s0A5j5BB6A9Jmi73HwBIUl50j+osU4= -golang.org/x/crypto v0.0.0-20220622213112-05595931fe9d h1:sK3txAijHtOK88l68nt020reeT1ZdKLIYetKl95FzVY= -golang.org/x/crypto v0.0.0-20220622213112-05595931fe9d/go.mod h1:IxCIyHEi3zRg3s0A5j5BB6A9Jmi73HwBIUl50j+osU4= +golang.org/x/crypto v0.0.0-20220525230936-793ad666bf5e h1:T8NU3HyQ8ClP4SEE+KbFlg6n0NhuTsN4MyznaarGsZM= +golang.org/x/crypto v0.0.0-20220525230936-793ad666bf5e/go.mod h1:IxCIyHEi3zRg3s0A5j5BB6A9Jmi73HwBIUl50j+osU4= golang.org/x/exp v0.0.0-20190121172915-509febef88a4/go.mod h1:CJ0aWSM057203Lf6IL+f9T1iT9GByDxfZKAQTCR3kQA= golang.org/x/exp v0.0.0-20190306152737-a1d7652674e8/go.mod h1:CJ0aWSM057203Lf6IL+f9T1iT9GByDxfZKAQTCR3kQA= golang.org/x/exp v0.0.0-20190510132918-efd6b22b2522/go.mod h1:ZjyILWgesfNpC6sMxTJOJm9Kp84zZh5NQWvqDGG3Qr8= @@ -920,12 +926,14 @@ golang.org/x/mod v0.6.0-dev.0.20220106191415-9b9b3d81d5e3/go.mod h1:3p9vT2HGsQu2 golang.org/x/net v0.0.0-20180724234803-3673e40ba225/go.mod h1:mL1N/T3taQHkDXs73rZJwtUhF3w3ftmwwsq0BUmARs4= golang.org/x/net v0.0.0-20180826012351-8a410e7b638d/go.mod h1:mL1N/T3taQHkDXs73rZJwtUhF3w3ftmwwsq0BUmARs4= golang.org/x/net v0.0.0-20180906233101-161cd47e91fd/go.mod h1:mL1N/T3taQHkDXs73rZJwtUhF3w3ftmwwsq0BUmARs4= +golang.org/x/net v0.0.0-20181005035420-146acd28ed58/go.mod h1:mL1N/T3taQHkDXs73rZJwtUhF3w3ftmwwsq0BUmARs4= golang.org/x/net v0.0.0-20181023162649-9b4f9f5ad519/go.mod h1:mL1N/T3taQHkDXs73rZJwtUhF3w3ftmwwsq0BUmARs4= golang.org/x/net v0.0.0-20181114220301-adae6a3d119a/go.mod h1:mL1N/T3taQHkDXs73rZJwtUhF3w3ftmwwsq0BUmARs4= golang.org/x/net v0.0.0-20181201002055-351d144fa1fc/go.mod h1:mL1N/T3taQHkDXs73rZJwtUhF3w3ftmwwsq0BUmARs4= golang.org/x/net v0.0.0-20190108225652-1e06a53dbb7e/go.mod h1:mL1N/T3taQHkDXs73rZJwtUhF3w3ftmwwsq0BUmARs4= golang.org/x/net v0.0.0-20190213061140-3a22650c66bd/go.mod h1:mL1N/T3taQHkDXs73rZJwtUhF3w3ftmwwsq0BUmARs4= golang.org/x/net v0.0.0-20190311183353-d8887717615a/go.mod h1:t9HGtf8HONx5eT2rtn7q6eTqICYqUVnKs3thJo3Qplg= +golang.org/x/net v0.0.0-20190320064053-1272bf9dcd53/go.mod h1:t9HGtf8HONx5eT2rtn7q6eTqICYqUVnKs3thJo3Qplg= golang.org/x/net v0.0.0-20190404232315-eb5bcb51f2a3/go.mod h1:t9HGtf8HONx5eT2rtn7q6eTqICYqUVnKs3thJo3Qplg= golang.org/x/net v0.0.0-20190501004415-9ce7a6920f09/go.mod h1:t9HGtf8HONx5eT2rtn7q6eTqICYqUVnKs3thJo3Qplg= golang.org/x/net v0.0.0-20190503192946-f4e77d36d62c/go.mod h1:t9HGtf8HONx5eT2rtn7q6eTqICYqUVnKs3thJo3Qplg= @@ -935,7 +943,6 @@ golang.org/x/net v0.0.0-20190620200207-3b0461eec859/go.mod h1:z5CRVTTTmAJ677TzLL golang.org/x/net v0.0.0-20190628185345-da137c7871d7/go.mod h1:z5CRVTTTmAJ677TzLLGU+0bjPO0LkuOLi4/5GtJWs/s= golang.org/x/net v0.0.0-20190724013045-ca1201d0de80/go.mod h1:z5CRVTTTmAJ677TzLLGU+0bjPO0LkuOLi4/5GtJWs/s= golang.org/x/net v0.0.0-20190827160401-ba9fcec4b297/go.mod h1:z5CRVTTTmAJ677TzLLGU+0bjPO0LkuOLi4/5GtJWs/s= -golang.org/x/net v0.0.0-20190923162816-aa69164e4478/go.mod h1:z5CRVTTTmAJ677TzLLGU+0bjPO0LkuOLi4/5GtJWs/s= golang.org/x/net v0.0.0-20191209160850-c0dbc17a3553/go.mod h1:z5CRVTTTmAJ677TzLLGU+0bjPO0LkuOLi4/5GtJWs/s= golang.org/x/net v0.0.0-20200114155413-6afb5195e5aa/go.mod h1:z5CRVTTTmAJ677TzLLGU+0bjPO0LkuOLi4/5GtJWs/s= golang.org/x/net v0.0.0-20200202094626-16171245cfb2/go.mod h1:z5CRVTTTmAJ677TzLLGU+0bjPO0LkuOLi4/5GtJWs/s= @@ -948,27 +955,28 @@ golang.org/x/net v0.0.0-20200506145744-7e3656a0809f/go.mod h1:qpuaurCH72eLCgpAm/ golang.org/x/net v0.0.0-20200513185701-a91f0712d120/go.mod h1:qpuaurCH72eLCgpAm/N6yyVIVM9cpaDIP3A8BGJEC5A= golang.org/x/net v0.0.0-20200520004742-59133d7f0dd7/go.mod h1:qpuaurCH72eLCgpAm/N6yyVIVM9cpaDIP3A8BGJEC5A= golang.org/x/net v0.0.0-20200520182314-0ba52f642ac2/go.mod h1:qpuaurCH72eLCgpAm/N6yyVIVM9cpaDIP3A8BGJEC5A= +golang.org/x/net v0.0.0-20200602114024-627f9648deb9/go.mod h1:qpuaurCH72eLCgpAm/N6yyVIVM9cpaDIP3A8BGJEC5A= golang.org/x/net v0.0.0-20200625001655-4c5254603344/go.mod h1:/O7V0waA8r7cgGh81Ro3o1hOxt32SMVPicZroKQ2sZA= golang.org/x/net v0.0.0-20200707034311-ab3426394381/go.mod h1:/O7V0waA8r7cgGh81Ro3o1hOxt32SMVPicZroKQ2sZA= golang.org/x/net v0.0.0-20200822124328-c89045814202/go.mod h1:/O7V0waA8r7cgGh81Ro3o1hOxt32SMVPicZroKQ2sZA= golang.org/x/net v0.0.0-20201021035429-f5854403a974/go.mod h1:sp8m0HH+o8qH0wwXwYZr8TS3Oi6o0r6Gce1SSxlDquU= golang.org/x/net v0.0.0-20201031054903-ff519b6c9102/go.mod h1:sp8m0HH+o8qH0wwXwYZr8TS3Oi6o0r6Gce1SSxlDquU= golang.org/x/net v0.0.0-20201110031124-69a78807bb2b/go.mod h1:sp8m0HH+o8qH0wwXwYZr8TS3Oi6o0r6Gce1SSxlDquU= +golang.org/x/net v0.0.0-20201202161906-c7110b5ffcbb/go.mod h1:sp8m0HH+o8qH0wwXwYZr8TS3Oi6o0r6Gce1SSxlDquU= golang.org/x/net v0.0.0-20201209123823-ac852fbbde11/go.mod h1:m0MpNAwzfU5UDzcl9v0D8zg8gWTRqZa9RBIspLL5mdg= +golang.org/x/net v0.0.0-20201224014010-6772e930b67b/go.mod h1:m0MpNAwzfU5UDzcl9v0D8zg8gWTRqZa9RBIspLL5mdg= golang.org/x/net v0.0.0-20210119194325-5f4716e94777/go.mod h1:m0MpNAwzfU5UDzcl9v0D8zg8gWTRqZa9RBIspLL5mdg= golang.org/x/net v0.0.0-20210226172049-e18ecbb05110/go.mod h1:m0MpNAwzfU5UDzcl9v0D8zg8gWTRqZa9RBIspLL5mdg= golang.org/x/net v0.0.0-20210316092652-d523dce5a7f4/go.mod h1:RBQZq4jEuRlivfhVLdyRGr576XBO4/greRjx4P4O3yc= golang.org/x/net v0.0.0-20210405180319-a5a99cb37ef4/go.mod h1:p54w0d4576C0XHj96bSt6lcn1PtDYWL6XObtHCRCNQM= -golang.org/x/net v0.0.0-20210410081132-afb366fc7cd1/go.mod h1:9tjilg8BloeKEkVJvy7fQ90B1CfIiPueXVOjqfkSzI8= -golang.org/x/net v0.0.0-20210421230115-4e50805a0758/go.mod h1:72T/g9IO56b78aLF+1Kcs5dz7/ng1VjMUvfKvpfy+jM= golang.org/x/net v0.0.0-20210503060351-7fd8e65b6420/go.mod h1:9nx3DQGgdP8bBQD5qxJ1jj9UTztislL4KSBs9R2vV5Y= golang.org/x/net v0.0.0-20210525063256-abc453219eb5/go.mod h1:9nx3DQGgdP8bBQD5qxJ1jj9UTztislL4KSBs9R2vV5Y= golang.org/x/net v0.0.0-20210805182204-aaa1db679c0d/go.mod h1:9nx3DQGgdP8bBQD5qxJ1jj9UTztislL4KSBs9R2vV5Y= golang.org/x/net v0.0.0-20211015210444-4f30a5c0130f/go.mod h1:9nx3DQGgdP8bBQD5qxJ1jj9UTztislL4KSBs9R2vV5Y= golang.org/x/net v0.0.0-20211112202133-69e39bad7dc2/go.mod h1:9nx3DQGgdP8bBQD5qxJ1jj9UTztislL4KSBs9R2vV5Y= golang.org/x/net v0.0.0-20220127200216-cd36cc0744dd/go.mod h1:CfG3xpIq0wQ8r1q4Su4UZFWDARRcnwPjda9FqA0JpMk= -golang.org/x/net v0.4.0 h1:Q5QPcMlvfxFTAPV0+07Xz/MpK9NTXu2VDUuy0FeMfaU= -golang.org/x/net v0.4.0/go.mod h1:MBQ8lrhLObU/6UmLb4fmbmk5OcyYmqtbGd/9yIeKjEE= +golang.org/x/net v0.7.0 h1:rJrUqqhjsgNp7KqAIc25s9pZnjU7TUcSY7HcVZjdn1g= +golang.org/x/net v0.7.0/go.mod h1:2Tu9+aMcznHK/AK1HMvgo6xiTLG5rD5rZLDS+rp2Bjs= golang.org/x/oauth2 v0.0.0-20180821212333-d2e6202438be/go.mod h1:N/0e6XlmueqKjAGxoOufVs8QHGRruUQn6yWY3a++T0U= golang.org/x/oauth2 v0.0.0-20190226205417-e64efc72b421/go.mod h1:gOpvHmFTYa4IltrdGE7lF6nIHvwfUNPOp7c8zoXwtLw= golang.org/x/oauth2 v0.0.0-20190604053449-0f29369cfe45/go.mod h1:gOpvHmFTYa4IltrdGE7lF6nIHvwfUNPOp7c8zoXwtLw= @@ -985,9 +993,8 @@ golang.org/x/oauth2 v0.0.0-20210514164344-f6687ab2804c/go.mod h1:KelEdhl1UZF7XfJ golang.org/x/oauth2 v0.0.0-20210628180205-a41e5a781914/go.mod h1:KelEdhl1UZF7XfJ4dDtk6s++YSgaE7mD/BuKKDLBl4A= golang.org/x/oauth2 v0.0.0-20210805134026-6f1e6394065a/go.mod h1:KelEdhl1UZF7XfJ4dDtk6s++YSgaE7mD/BuKKDLBl4A= golang.org/x/oauth2 v0.0.0-20210819190943-2bc19b11175f/go.mod h1:KelEdhl1UZF7XfJ4dDtk6s++YSgaE7mD/BuKKDLBl4A= +golang.org/x/oauth2 v0.0.0-20211104180415-d3ed0bb246c8 h1:RerP+noqYHUQ8CMRcPlC2nvTa4dcBIjegkuWdcUDuqg= golang.org/x/oauth2 v0.0.0-20211104180415-d3ed0bb246c8/go.mod h1:KelEdhl1UZF7XfJ4dDtk6s++YSgaE7mD/BuKKDLBl4A= -golang.org/x/oauth2 v0.0.0-20220909003341-f21342109be1 h1:lxqLZaMad/dJHMFZH0NiNpiEZI/nhgWhe4wgzpE+MuA= -golang.org/x/oauth2 v0.0.0-20220909003341-f21342109be1/go.mod h1:h4gKUeWbJ4rQPri7E0u6Gs4e9Ri2zaLxzw5DI5XGrYg= golang.org/x/sync v0.0.0-20180314180146-1d60e4601c6f/go.mod h1:RxMgew5VJxzue5/jJTE5uejpjVlOe/izrB70Jof72aM= golang.org/x/sync v0.0.0-20181108010431-42b317875d0f/go.mod h1:RxMgew5VJxzue5/jJTE5uejpjVlOe/izrB70Jof72aM= golang.org/x/sync v0.0.0-20181221193216-37e7f081c4d4/go.mod h1:RxMgew5VJxzue5/jJTE5uejpjVlOe/izrB70Jof72aM= @@ -1011,6 +1018,7 @@ golang.org/x/sys v0.0.0-20181116152217-5ac8a444bdc5/go.mod h1:STP8DvDyc/dI5b8T5h golang.org/x/sys v0.0.0-20190215142949-d0b11bdaac8a/go.mod h1:STP8DvDyc/dI5b8T5hshtkjS+E42TnysNCUPdjciGhY= golang.org/x/sys v0.0.0-20190222072716-a9d3bda3a223/go.mod h1:STP8DvDyc/dI5b8T5hshtkjS+E42TnysNCUPdjciGhY= golang.org/x/sys v0.0.0-20190312061237-fead79001313/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= +golang.org/x/sys v0.0.0-20190321052220-f7bb7a8bee54/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= golang.org/x/sys v0.0.0-20190403152447-81d4e9dc473e/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= golang.org/x/sys v0.0.0-20190412213103-97732733099d/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= golang.org/x/sys v0.0.0-20190419153524-e8e3143a4f4a/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= @@ -1019,15 +1027,15 @@ golang.org/x/sys v0.0.0-20190502145724-3ef323f4f1fd/go.mod h1:h1NjWce9XRLGQEsW7w golang.org/x/sys v0.0.0-20190507160741-ecd444e8653b/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= golang.org/x/sys v0.0.0-20190531175056-4c3a928424d2/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= golang.org/x/sys v0.0.0-20190606165138-5da285871e9c/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= +golang.org/x/sys v0.0.0-20190616124812-15dcb6c0061f/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= golang.org/x/sys v0.0.0-20190624142023-c5567b49c5d0/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= golang.org/x/sys v0.0.0-20190726091711-fc99dfbffb4e/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= golang.org/x/sys v0.0.0-20190801041406-cbf593c0f2f3/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= golang.org/x/sys v0.0.0-20190904154756-749cb33beabd/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= -golang.org/x/sys v0.0.0-20190922100055-0a153f010e69/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= -golang.org/x/sys v0.0.0-20190924154521-2837fb4f24fe/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= golang.org/x/sys v0.0.0-20191001151750-bb3f8db39f24/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= golang.org/x/sys v0.0.0-20191002063906-3421d5a6bb1c/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= golang.org/x/sys v0.0.0-20191005200804-aed5e4c7ecf9/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= +golang.org/x/sys v0.0.0-20191008105621-543471e840be/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= golang.org/x/sys v0.0.0-20191026070338-33540a1f6037/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= golang.org/x/sys v0.0.0-20191120155948-bd437916bb0e/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= golang.org/x/sys v0.0.0-20191204072324-ce4227a45e2e/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= @@ -1059,13 +1067,11 @@ golang.org/x/sys v0.0.0-20210112080510-489259a85091/go.mod h1:h1NjWce9XRLGQEsW7w golang.org/x/sys v0.0.0-20210119212857-b64e53b001e4/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= golang.org/x/sys v0.0.0-20210124154548-22da62e12c0c/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= golang.org/x/sys v0.0.0-20210220050731-9a76102bfb43/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= -golang.org/x/sys v0.0.0-20210303074136-134d130e1a04/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= golang.org/x/sys v0.0.0-20210305230114-8fe3ee5dd75b/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= golang.org/x/sys v0.0.0-20210315160823-c6e025ad8005/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= golang.org/x/sys v0.0.0-20210320140829-1e4c9ba3b0c4/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= golang.org/x/sys v0.0.0-20210330210617-4fbd30eecc44/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= golang.org/x/sys v0.0.0-20210403161142-5e06dd20ab57/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= -golang.org/x/sys v0.0.0-20210420072515-93ed5bcd2bfe/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= golang.org/x/sys v0.0.0-20210423082822-04245dca01da/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= golang.org/x/sys v0.0.0-20210510120138-977fb7262007/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg= golang.org/x/sys v0.0.0-20210514084401-e8d321eab015/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg= @@ -1085,18 +1091,12 @@ golang.org/x/sys v0.0.0-20211216021012-1d35b9e2eb4e/go.mod h1:oPkhp1MJrh7nUepCBc golang.org/x/sys v0.0.0-20220114195835-da31bd327af9/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg= golang.org/x/sys v0.0.0-20220209214540-3681064d5158/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg= golang.org/x/sys v0.0.0-20220412211240-33da011f77ad/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg= -golang.org/x/sys v0.0.0-20220503163025-988cb79eb6c6/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg= -golang.org/x/sys v0.0.0-20220715151400-c0bba94af5f8/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg= -golang.org/x/sys v0.0.0-20220728004956-3c1f35247d10/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg= -golang.org/x/sys v0.0.0-20220811171246-fbc7d0a398ab/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg= -golang.org/x/sys v0.3.0 h1:w8ZOecv6NaNa/zC8944JTU3vz4u6Lagfk4RPQxv92NQ= -golang.org/x/sys v0.3.0/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg= -golang.org/x/term v0.0.0-20201117132131-f5c789dd3221/go.mod h1:Nr5EML6q2oocZ2LXRh80K7BxOlk5/8JxuGnuhpl+muw= +golang.org/x/sys v0.5.0 h1:MUK/U/4lj1t1oPg0HfuXDN/Z1wv31ZJ/YcPiGccS4DU= +golang.org/x/sys v0.5.0/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg= golang.org/x/term v0.0.0-20201126162022-7de9c90e9dd1/go.mod h1:bj7SfCRtBDWHUb9snDiAeCFNEtKQo2Wmx5Cou7ajbmo= golang.org/x/term v0.0.0-20210927222741-03fcf44c2211/go.mod h1:jbD1KX2456YbFQfuXm/mYQcufACuNUgVhRMnK/tPxf8= -golang.org/x/term v0.0.0-20220526004731-065cf7ba2467/go.mod h1:jbD1KX2456YbFQfuXm/mYQcufACuNUgVhRMnK/tPxf8= -golang.org/x/term v0.3.0 h1:qoo4akIqOcDME5bhc/NgxUdovd6BSS2uMsVjB56q1xI= -golang.org/x/term v0.3.0/go.mod h1:q750SLmJuPmVoN1blW3UFBPREJfb1KmY3vwxfr+nFDA= +golang.org/x/term v0.5.0 h1:n2a8QNdAb0sZNpU9R1ALUXBbY+w51fCQDN+7EdxNBsY= +golang.org/x/term v0.5.0/go.mod h1:jMB1sMXY+tzblOD4FWmEbocvup2/aLOaQEp7JmGp78k= golang.org/x/text v0.0.0-20170915032832-14c0d48ead0c/go.mod h1:NqM8EUOU14njkJ3fqMW+pc6Ldnwhi/IjpwHt7yyuwOQ= golang.org/x/text v0.3.0/go.mod h1:NqM8EUOU14njkJ3fqMW+pc6Ldnwhi/IjpwHt7yyuwOQ= golang.org/x/text v0.3.1-0.20180807135948-17ff2d5776d2/go.mod h1:NqM8EUOU14njkJ3fqMW+pc6Ldnwhi/IjpwHt7yyuwOQ= @@ -1106,8 +1106,8 @@ golang.org/x/text v0.3.4/go.mod h1:5Zoc/QRtKVWzQhOtBMvqHzDpF6irO9z98xDceosuGiQ= golang.org/x/text v0.3.5/go.mod h1:5Zoc/QRtKVWzQhOtBMvqHzDpF6irO9z98xDceosuGiQ= golang.org/x/text v0.3.6/go.mod h1:5Zoc/QRtKVWzQhOtBMvqHzDpF6irO9z98xDceosuGiQ= golang.org/x/text v0.3.7/go.mod h1:u+2+/6zg+i71rQMx5EYifcz6MCKuco9NR6JIITiCfzQ= -golang.org/x/text v0.5.0 h1:OLmvp0KP+FVG99Ct/qFiL/Fhk4zp4QQnZ7b2U+5piUM= -golang.org/x/text v0.5.0/go.mod h1:mrYo+phRRbMaCq/xk9113O4dZlRixOauAjOtrjsXDZ8= +golang.org/x/text v0.7.0 h1:4BRB4x83lYWy72KwLD/qYDuTu7q9PjSagHvijDw7cLo= +golang.org/x/text v0.7.0/go.mod h1:mrYo+phRRbMaCq/xk9113O4dZlRixOauAjOtrjsXDZ8= golang.org/x/time v0.0.0-20181108054448-85acf8d2951c/go.mod h1:tRJNPiyCQ0inRvYxbN9jk5I+vvW/OXSQhTDSoE431IQ= golang.org/x/time v0.0.0-20190308202827-9d24e82272b4/go.mod h1:tRJNPiyCQ0inRvYxbN9jk5I+vvW/OXSQhTDSoE431IQ= golang.org/x/time v0.0.0-20191024005414-555d28b269f0/go.mod h1:tRJNPiyCQ0inRvYxbN9jk5I+vvW/OXSQhTDSoE431IQ= @@ -1115,7 +1115,9 @@ golang.org/x/time v0.0.0-20220210224613-90d013bbcef8/go.mod h1:tRJNPiyCQ0inRvYxb golang.org/x/time v0.0.0-20220609170525-579cf78fd858 h1:Dpdu/EMxGMFgq0CeYMh4fazTD2vtlZRYE7wyynxJb9U= golang.org/x/time v0.0.0-20220609170525-579cf78fd858/go.mod h1:tRJNPiyCQ0inRvYxbN9jk5I+vvW/OXSQhTDSoE431IQ= golang.org/x/tools v0.0.0-20180917221912-90fa682c2a6e/go.mod h1:n7NCudcB/nEzxVGmLbDWY5pfWTLqBcC2KZ6jyYvM4mQ= +golang.org/x/tools v0.0.0-20181030221726-6c7e314b6563/go.mod h1:n7NCudcB/nEzxVGmLbDWY5pfWTLqBcC2KZ6jyYvM4mQ= golang.org/x/tools v0.0.0-20190114222345-bf090417da8b/go.mod h1:n7NCudcB/nEzxVGmLbDWY5pfWTLqBcC2KZ6jyYvM4mQ= +golang.org/x/tools v0.0.0-20190125232054-d66bd3c5d5a6/go.mod h1:n7NCudcB/nEzxVGmLbDWY5pfWTLqBcC2KZ6jyYvM4mQ= golang.org/x/tools v0.0.0-20190226205152-f727befe758c/go.mod h1:9Yl7xja0Znq3iFh3HoIrodX9oNMXvdceNzlUR8zjMvY= golang.org/x/tools v0.0.0-20190311212946-11955173bddd/go.mod h1:LCzVGOaR6xXOjkQ3onu1FJEFr0SW1gC7cKk1uF8kGRs= golang.org/x/tools v0.0.0-20190312151545-0bb0c0a6e846/go.mod h1:LCzVGOaR6xXOjkQ3onu1FJEFr0SW1gC7cKk1uF8kGRs= @@ -1129,11 +1131,12 @@ golang.org/x/tools v0.0.0-20190506145303-2d16b83fe98c/go.mod h1:RgjU9mgBXZiqYHBn golang.org/x/tools v0.0.0-20190524140312-2c0ae7006135/go.mod h1:RgjU9mgBXZiqYHBnxXauZ1Gv1EHHAz9KjViQ78xBX0Q= golang.org/x/tools v0.0.0-20190531172133-b3315ee88b7d/go.mod h1:/rFqwRUd4F7ZHNgwSSTFct+R/Kf4OFW1sUzUTQQTgfc= golang.org/x/tools v0.0.0-20190606124116-d0a3d012864b/go.mod h1:/rFqwRUd4F7ZHNgwSSTFct+R/Kf4OFW1sUzUTQQTgfc= +golang.org/x/tools v0.0.0-20190614205625-5aca471b1d59/go.mod h1:/rFqwRUd4F7ZHNgwSSTFct+R/Kf4OFW1sUzUTQQTgfc= +golang.org/x/tools v0.0.0-20190617190820-da514acc4774/go.mod h1:/rFqwRUd4F7ZHNgwSSTFct+R/Kf4OFW1sUzUTQQTgfc= golang.org/x/tools v0.0.0-20190621195816-6e04913cbbac/go.mod h1:/rFqwRUd4F7ZHNgwSSTFct+R/Kf4OFW1sUzUTQQTgfc= golang.org/x/tools v0.0.0-20190624222133-a101b041ded4/go.mod h1:/rFqwRUd4F7ZHNgwSSTFct+R/Kf4OFW1sUzUTQQTgfc= golang.org/x/tools v0.0.0-20190628153133-6cdbf07be9d0/go.mod h1:/rFqwRUd4F7ZHNgwSSTFct+R/Kf4OFW1sUzUTQQTgfc= golang.org/x/tools v0.0.0-20190816200558-6889da9d5479/go.mod h1:b+2E5dAYhXwXZwtnZ6UAqBI28+e2cm9otk0dWdXHAEo= -golang.org/x/tools v0.0.0-20190907020128-2ca718005c18/go.mod h1:b+2E5dAYhXwXZwtnZ6UAqBI28+e2cm9otk0dWdXHAEo= golang.org/x/tools v0.0.0-20190911174233-4f2ddba30aff/go.mod h1:b+2E5dAYhXwXZwtnZ6UAqBI28+e2cm9otk0dWdXHAEo= golang.org/x/tools v0.0.0-20191012152004-8de300cfc20a/go.mod h1:b+2E5dAYhXwXZwtnZ6UAqBI28+e2cm9otk0dWdXHAEo= golang.org/x/tools v0.0.0-20191108193012-7d206e10da11/go.mod h1:b+2E5dAYhXwXZwtnZ6UAqBI28+e2cm9otk0dWdXHAEo= @@ -1283,8 +1286,8 @@ google.golang.org/genproto v0.0.0-20210924002016-3dee208752a0/go.mod h1:5CzLGKJ6 google.golang.org/genproto v0.0.0-20211118181313-81c1377c94b1/go.mod h1:5CzLGKJ67TSI2B9POpiiyGha0AjJvZIUgRMt1dSmuhc= google.golang.org/genproto v0.0.0-20211206160659-862468c7d6e0/go.mod h1:5CzLGKJ67TSI2B9POpiiyGha0AjJvZIUgRMt1dSmuhc= google.golang.org/genproto v0.0.0-20220107163113-42d7afdf6368/go.mod h1:5CzLGKJ67TSI2B9POpiiyGha0AjJvZIUgRMt1dSmuhc= -google.golang.org/genproto v0.0.0-20220921223823-23cae91e6737 h1:K1zaaMdYBXRyX+cwFnxj7M6zwDyumLQMZ5xqwGvjreQ= -google.golang.org/genproto v0.0.0-20220921223823-23cae91e6737/go.mod h1:2r/26NEF3bFmT3eC3aZreahSal0C3Shl8Gi6vyDYqOQ= +google.golang.org/genproto v0.0.0-20220502173005-c8bf987b8c21 h1:hrbNEivu7Zn1pxvHk6MBrq9iE22woVILTHqexqBxe6I= +google.golang.org/genproto v0.0.0-20220502173005-c8bf987b8c21/go.mod h1:RAyBrSAP7Fh3Nc84ghnVLDPuV51xc9agzmm4Ph6i0Q4= google.golang.org/grpc v1.19.0/go.mod h1:mqu4LbDTu4XGKhr4mRzUsmM4RtVoemTSY81AxZiDr8c= google.golang.org/grpc v1.20.1/go.mod h1:10oTOabMzJvdu6/UiuZezV6QK5dSlG84ov/aaiqXj38= google.golang.org/grpc v1.21.1/go.mod h1:oYelfM1adQP15Ek0mdvEgi9Df8B9CZIaU1084ijfRaM= @@ -1310,9 +1313,9 @@ google.golang.org/grpc v1.38.0/go.mod h1:NREThFqKR1f3iQ6oBuvc5LadQuXVGo9rkm5ZGrQ google.golang.org/grpc v1.39.0/go.mod h1:PImNr+rS9TWYb2O4/emRugxiyHZ5JyHW5F+RPnDzfrE= google.golang.org/grpc v1.39.1/go.mod h1:PImNr+rS9TWYb2O4/emRugxiyHZ5JyHW5F+RPnDzfrE= google.golang.org/grpc v1.40.0/go.mod h1:ogyxbiOoUXAkP+4+xa6PZSE9DZgIHtSpzjDTB9KAK34= -google.golang.org/grpc v1.42.0/go.mod h1:k+4IHHFw41K8+bbowsex27ge2rCb65oeWqe4jJ590SU= -google.golang.org/grpc v1.49.0 h1:WTLtQzmQori5FUH25Pq4WT22oCsv8USpQ+F6rqtsmxw= -google.golang.org/grpc v1.49.0/go.mod h1:ZgQEeidpAuNRZ8iRrlBKXZQP1ghovWIVhdJRyCDK+GI= +google.golang.org/grpc v1.46.0/go.mod h1:vN9eftEi1UMyUsIF80+uQXhHjbXYbm0uXoFCACuMGWk= +google.golang.org/grpc v1.47.0 h1:9n77onPX5F3qfFCqjy9dhn8PbNQsIKeVU04J9G7umt8= +google.golang.org/grpc v1.47.0/go.mod h1:vN9eftEi1UMyUsIF80+uQXhHjbXYbm0uXoFCACuMGWk= google.golang.org/grpc/cmd/protoc-gen-go-grpc v1.1.0/go.mod h1:6Kw0yEErY5E/yWrBtf03jp27GLLJujG4z/JK95pnjjw= google.golang.org/protobuf v0.0.0-20200109180630-ec00e32a8dfd/go.mod h1:DFci5gLYBciE7Vtevhsrf46CRTquxDuWsQurQQe4oz8= google.golang.org/protobuf v0.0.0-20200221191635-4d8936d0db64/go.mod h1:kwYJMbMJ01Woi6D6+Kah6886xMZcty6N08ah7+eCXa0= @@ -1327,8 +1330,8 @@ google.golang.org/protobuf v1.25.0/go.mod h1:9JNX74DMeImyA3h4bdi1ymwjUzf21/xIlba google.golang.org/protobuf v1.26.0-rc.1/go.mod h1:jlhhOSvTdKEhbULTjvd4ARK9grFBp09yW+WbY/TyQbw= google.golang.org/protobuf v1.26.0/go.mod h1:9q0QmTI4eRPtz6boOQmLYwt+qCgq0jsYwAQnmE0givc= google.golang.org/protobuf v1.27.1/go.mod h1:9q0QmTI4eRPtz6boOQmLYwt+qCgq0jsYwAQnmE0givc= -google.golang.org/protobuf v1.28.1 h1:d0NfwRgPtno5B1Wa6L2DAG+KivqkdutMf1UhdNx175w= -google.golang.org/protobuf v1.28.1/go.mod h1:HV8QOd/L58Z+nl8r43ehVNZIU/HEI6OcFqwMG9pJV4I= +google.golang.org/protobuf v1.28.0 h1:w43yiav+6bVFTBQFZX0r7ipe9JQ1QsbMgHwbBziscLw= +google.golang.org/protobuf v1.28.0/go.mod h1:HV8QOd/L58Z+nl8r43ehVNZIU/HEI6OcFqwMG9pJV4I= gopkg.in/alecthomas/kingpin.v2 v2.2.6/go.mod h1:FMv+mEhP44yOT+4EoQTLFTRgOQ1FBLkstjWtayDeSgw= gopkg.in/check.v1 v0.0.0-20161208181325-20d25e280405/go.mod h1:Co6ibVJAznAaIkqp8huTwlJQCZ016jof/cbN4VW5Yz0= gopkg.in/check.v1 v1.0.0-20180628173108-788fd7840127/go.mod h1:Co6ibVJAznAaIkqp8huTwlJQCZ016jof/cbN4VW5Yz0= @@ -1356,7 +1359,6 @@ gopkg.in/yaml.v3 v3.0.0-20200313102051-9f266ea9e77c/go.mod h1:K4uyk7z7BCEPqu6E+C gopkg.in/yaml.v3 v3.0.0-20200605160147-a5ece683394c/go.mod h1:K4uyk7z7BCEPqu6E+C64Yfv1cQ7kz7rIZviUmN+EgEM= gopkg.in/yaml.v3 v3.0.0-20200615113413-eeeca48fe776/go.mod h1:K4uyk7z7BCEPqu6E+C64Yfv1cQ7kz7rIZviUmN+EgEM= gopkg.in/yaml.v3 v3.0.0-20210107192922-496545a6307b/go.mod h1:K4uyk7z7BCEPqu6E+C64Yfv1cQ7kz7rIZviUmN+EgEM= -gopkg.in/yaml.v3 v3.0.0/go.mod h1:K4uyk7z7BCEPqu6E+C64Yfv1cQ7kz7rIZviUmN+EgEM= gopkg.in/yaml.v3 v3.0.1 h1:fxVm/GzAzEWqLHuvctI91KS9hhNmmWOoWu0XTYJS7CA= gopkg.in/yaml.v3 v3.0.1/go.mod h1:K4uyk7z7BCEPqu6E+C64Yfv1cQ7kz7rIZviUmN+EgEM= gotest.tools/v3 v3.0.2/go.mod h1:3SzNCllyD9/Y+b5r9JIKQ474KzkZyqLqEfYqMsX94Bk= diff --git a/cli/preset/demo.go b/cli/preset/demo.go index ee1b100114..bf6c0bb122 100644 --- a/cli/preset/demo.go +++ b/cli/preset/demo.go @@ -29,6 +29,8 @@ connectInject: enableGatewayMetrics: true server: replicas: 1 +controller: + enabled: true ui: enabled: true service: diff --git a/cli/preset/quickstart.go b/cli/preset/quickstart.go index 823a60e312..52b3f000b1 100644 --- a/cli/preset/quickstart.go +++ b/cli/preset/quickstart.go @@ -29,6 +29,8 @@ connectInject: enableGatewayMetrics: true server: replicas: 1 +controller: + enabled: true ui: enabled: true service: diff --git a/cli/preset/secure.go b/cli/preset/secure.go index 6fccc956a6..ded436804c 100644 --- a/cli/preset/secure.go +++ b/cli/preset/secure.go @@ -29,6 +29,8 @@ server: replicas: 1 connectInject: enabled: true +controller: + enabled: true ` return config.ConvertToMap(values), nil diff --git a/cli/version/version.go b/cli/version/version.go index 8ae06829bb..19d9b3f112 100644 --- a/cli/version/version.go +++ b/cli/version/version.go @@ -14,12 +14,12 @@ var ( // // Version must conform to the format expected by // github.com/hashicorp/go-version for tests to work. - Version = "1.2.0" + Version = "1.0.6" // A pre-release marker for the version. If this is "" (empty string) // then it means that it is a final release. Otherwise, this is a pre-release // such as "dev" (in development), "beta", "rc1", etc. - VersionPrerelease = "dev" + VersionPrerelease = "" ) // GetHumanVersion composes the parts of the version in a way that's suitable diff --git a/control-plane/Dockerfile b/control-plane/Dockerfile index 850cdd42c6..9d69ab45aa 100644 --- a/control-plane/Dockerfile +++ b/control-plane/Dockerfile @@ -13,7 +13,7 @@ # go-discover builds the discover binary (which we don't currently publish # either). -FROM golang:1.19.2-alpine as go-discover +FROM golang:1.19.9-alpine as go-discover RUN CGO_ENABLED=0 go install github.com/hashicorp/go-discover/cmd/discover@49f60c093101c9c5f6b04d5b1c80164251a761a6 # dev copies the binary from a local build diff --git a/control-plane/api/v1alpha1/proxydefaults_types.go b/control-plane/api/v1alpha1/proxydefaults_types.go index 543d8f7ae4..215ec708ff 100644 --- a/control-plane/api/v1alpha1/proxydefaults_types.go +++ b/control-plane/api/v1alpha1/proxydefaults_types.go @@ -75,10 +75,6 @@ type ProxyDefaultsSpec struct { MeshGateway MeshGateway `json:"meshGateway,omitempty"` // Expose controls the default expose path configuration for Envoy. Expose Expose `json:"expose,omitempty"` - // AccessLogs controls all envoy instances' access logging configuration. - AccessLogs *AccessLogs `json:"accessLogs,omitempty"` - // EnvoyExtensions are a list of extensions to modify Envoy proxy configuration. - EnvoyExtensions EnvoyExtensions `json:"envoyExtensions,omitempty"` } func (in *ProxyDefaults) GetObjectMeta() metav1.ObjectMeta { @@ -169,8 +165,6 @@ func (in *ProxyDefaults) ToConsul(datacenter string) capi.ConfigEntry { Expose: in.Spec.Expose.toConsul(), Config: consulConfig, TransparentProxy: in.Spec.TransparentProxy.toConsul(), - AccessLogs: in.Spec.AccessLogs.toConsul(), - EnvoyExtensions: in.Spec.EnvoyExtensions.toConsul(), Meta: meta(datacenter), } } @@ -201,12 +195,7 @@ func (in *ProxyDefaults) Validate(_ common.ConsulMeta) error { if err := in.validateConfig(path.Child("config")); err != nil { allErrs = append(allErrs, err) } - if err := in.Spec.AccessLogs.validate(path.Child("accessLogs")); err != nil { - allErrs = append(allErrs, err) - } allErrs = append(allErrs, in.Spec.Expose.validate(path.Child("expose"))...) - allErrs = append(allErrs, in.Spec.EnvoyExtensions.validate(path.Child("envoyExtensions"))...) - if len(allErrs) > 0 { return apierrors.NewInvalid( schema.GroupKind{Group: ConsulHashicorpGroup, Kind: ProxyDefaultsKubeKind}, @@ -244,93 +233,7 @@ func (in *ProxyDefaults) validateConfig(path *field.Path) *field.Error { } var outConfig map[string]interface{} if err := json.Unmarshal(in.Spec.Config, &outConfig); err != nil { - return field.Invalid(path, string(in.Spec.Config), fmt.Sprintf(`must be valid map value: %s`, err)) + return field.Invalid(path, in.Spec.Config, fmt.Sprintf(`must be valid map value: %s`, err)) } return nil } - -// LogSinkType represents the destination for Envoy access logs. -// One of "file", "stderr", or "stdout". -type LogSinkType string - -const ( - DefaultLogSinkType LogSinkType = "" - FileLogSinkType LogSinkType = "file" - StdErrLogSinkType LogSinkType = "stderr" - StdOutLogSinkType LogSinkType = "stdout" -) - -// AccessLogs describes the access logging configuration for all Envoy proxies in the mesh. -type AccessLogs struct { - // Enabled turns on all access logging - Enabled bool `json:"enabled,omitempty"` - - // DisableListenerLogs turns off just listener logs for connections rejected by Envoy because they don't - // have a matching listener filter. - DisableListenerLogs bool `json:"disableListenerLogs,omitempty"` - - // Type selects the output for logs - // one of "file", "stderr". "stdout" - Type LogSinkType `json:"type,omitempty"` - - // Path is the output file to write logs for file-type logging - Path string `json:"path,omitempty"` - - // JSONFormat is a JSON-formatted string of an Envoy access log format dictionary. - // See for more info on formatting: https://www.envoyproxy.io/docs/envoy/latest/configuration/observability/access_log/usage#format-dictionaries - // Defining JSONFormat and TextFormat is invalid. - JSONFormat string `json:"jsonFormat,omitempty"` - - // TextFormat is a representation of Envoy access logs format. - // See for more info on formatting: https://www.envoyproxy.io/docs/envoy/latest/configuration/observability/access_log/usage#format-strings - // Defining JSONFormat and TextFormat is invalid. - TextFormat string `json:"textFormat,omitempty"` -} - -func (in *AccessLogs) validate(path *field.Path) *field.Error { - if in == nil { - return nil - } - - switch in.Type { - case DefaultLogSinkType, StdErrLogSinkType, StdOutLogSinkType: - // OK - case FileLogSinkType: - if in.Path == "" { - return field.Invalid(path.Child("path"), in.Path, "path must be specified when using file type access logs") - } - default: - return field.Invalid(path.Child("type"), in.Type, "invalid access log type (must be one of \"stdout\", \"stderr\", \"file\"") - } - - if in.JSONFormat != "" && in.TextFormat != "" { - return field.Invalid(path.Child("textFormat"), in.TextFormat, "cannot specify both access log jsonFormat and textFormat") - } - - if in.Type != FileLogSinkType && in.Path != "" { - return field.Invalid(path.Child("path"), in.Path, "path is only valid for file type access logs") - } - - if in.JSONFormat != "" { - msg := json.RawMessage{} - if err := json.Unmarshal([]byte(in.JSONFormat), &msg); err != nil { - return field.Invalid(path.Child("jsonFormat"), in.JSONFormat, "invalid access log json") - } - } - - return nil -} - -func (in *AccessLogs) toConsul() *capi.AccessLogsConfig { - if in == nil { - return nil - } - return &capi.AccessLogsConfig{ - Enabled: in.Enabled, - DisableListenerLogs: in.DisableListenerLogs, - JSONFormat: in.JSONFormat, - Path: in.Path, - TextFormat: in.TextFormat, - Type: capi.LogSinkType(in.Type), - } -} diff --git a/control-plane/api/v1alpha1/proxydefaults_types_test.go b/control-plane/api/v1alpha1/proxydefaults_types_test.go index 225068c136..2950a3a36e 100644 --- a/control-plane/api/v1alpha1/proxydefaults_types_test.go +++ b/control-plane/api/v1alpha1/proxydefaults_types_test.go @@ -71,25 +71,6 @@ func TestProxyDefaults_MatchesConsul(t *testing.T) { OutboundListenerPort: 1000, DialedDirectly: true, }, - AccessLogs: &AccessLogs{ - Enabled: true, - DisableListenerLogs: true, - Type: FileLogSinkType, - Path: "/var/log/envoy.logs", - TextFormat: "ITS WORKING %START_TIME%", - }, - EnvoyExtensions: EnvoyExtensions{ - EnvoyExtension{ - Name: "aws_request_signing", - Arguments: json.RawMessage(`{"AWSServiceName": "s3", "Region": "us-west-2"}`), - Required: false, - }, - EnvoyExtension{ - Name: "zipkin", - Arguments: json.RawMessage(`{"ClusterName": "zipkin_cluster", "Port": "9411", "CollectorEndpoint":"/api/v2/spans"}`), - Required: true, - }, - }, }, }, Theirs: &capi.ProxyConfigEntry{ @@ -122,32 +103,6 @@ func TestProxyDefaults_MatchesConsul(t *testing.T) { OutboundListenerPort: 1000, DialedDirectly: true, }, - AccessLogs: &capi.AccessLogsConfig{ - Enabled: true, - DisableListenerLogs: true, - Type: capi.FileLogSinkType, - Path: "/var/log/envoy.logs", - TextFormat: "ITS WORKING %START_TIME%", - }, - EnvoyExtensions: []capi.EnvoyExtension{ - { - Name: "aws_request_signing", - Arguments: map[string]interface{}{ - "AWSServiceName": "s3", - "Region": "us-west-2", - }, - Required: false, - }, - { - Name: "zipkin", - Arguments: map[string]interface{}{ - "ClusterName": "zipkin_cluster", - "Port": "9411", - "CollectorEndpoint": "/api/v2/spans", - }, - Required: true, - }, - }, }, Matches: true, }, @@ -281,25 +236,6 @@ func TestProxyDefaults_ToConsul(t *testing.T) { OutboundListenerPort: 1000, DialedDirectly: true, }, - AccessLogs: &AccessLogs{ - Enabled: true, - DisableListenerLogs: true, - Type: FileLogSinkType, - Path: "/var/log/envoy.logs", - TextFormat: "ITS WORKING %START_TIME%", - }, - EnvoyExtensions: EnvoyExtensions{ - EnvoyExtension{ - Name: "aws_request_signing", - Arguments: json.RawMessage(`{"AWSServiceName": "s3", "Region": "us-west-2"}`), - Required: false, - }, - EnvoyExtension{ - Name: "zipkin", - Arguments: json.RawMessage(`{"ClusterName": "zipkin_cluster", "Port": "9411", "CollectorEndpoint":"/api/v2/spans"}`), - Required: true, - }, - }, }, }, Exp: &capi.ProxyConfigEntry{ @@ -333,32 +269,6 @@ func TestProxyDefaults_ToConsul(t *testing.T) { OutboundListenerPort: 1000, DialedDirectly: true, }, - AccessLogs: &capi.AccessLogsConfig{ - Enabled: true, - DisableListenerLogs: true, - Type: capi.FileLogSinkType, - Path: "/var/log/envoy.logs", - TextFormat: "ITS WORKING %START_TIME%", - }, - EnvoyExtensions: []capi.EnvoyExtension{ - { - Name: "aws_request_signing", - Arguments: map[string]interface{}{ - "AWSServiceName": "s3", - "Region": "us-west-2", - }, - Required: false, - }, - { - Name: "zipkin", - Arguments: map[string]interface{}{ - "ClusterName": "zipkin_cluster", - "Port": "9411", - "CollectorEndpoint": "/api/v2/spans", - }, - Required: true, - }, - }, Meta: map[string]string{ common.SourceKey: common.SourceValue, common.DatacenterKey: "datacenter", @@ -383,30 +293,8 @@ func TestProxyDefaults_Validate(t *testing.T) { input *ProxyDefaults expectedErrMsg string }{ - "valid envoyExtension": { - input: &ProxyDefaults{ - ObjectMeta: metav1.ObjectMeta{ - Name: "global", - }, - Spec: ProxyDefaultsSpec{ - EnvoyExtensions: EnvoyExtensions{ - EnvoyExtension{ - Name: "aws_request_signing", - Arguments: json.RawMessage(`{"AWSServiceName": "s3", "Region": "us-west-2"}`), - Required: false, - }, - EnvoyExtension{ - Name: "zipkin", - Arguments: json.RawMessage(`{"ClusterName": "zipkin_cluster", "Port": "9411", "CollectorEndpoint":"/api/v2/spans"}`), - Required: true, - }, - }, - }, - }, - expectedErrMsg: "", - }, "meshgateway.mode": { - input: &ProxyDefaults{ + &ProxyDefaults{ ObjectMeta: metav1.ObjectMeta{ Name: "global", }, @@ -416,10 +304,10 @@ func TestProxyDefaults_Validate(t *testing.T) { }, }, }, - expectedErrMsg: `proxydefaults.consul.hashicorp.com "global" is invalid: spec.meshGateway.mode: Invalid value: "foobar": must be one of "remote", "local", "none", ""`, + `proxydefaults.consul.hashicorp.com "global" is invalid: spec.meshGateway.mode: Invalid value: "foobar": must be one of "remote", "local", "none", ""`, }, "expose.paths[].protocol": { - input: &ProxyDefaults{ + &ProxyDefaults{ ObjectMeta: metav1.ObjectMeta{ Name: "global", }, @@ -434,10 +322,10 @@ func TestProxyDefaults_Validate(t *testing.T) { }, }, }, - expectedErrMsg: `proxydefaults.consul.hashicorp.com "global" is invalid: spec.expose.paths[0].protocol: Invalid value: "invalid-protocol": must be one of "http", "http2"`, + `proxydefaults.consul.hashicorp.com "global" is invalid: spec.expose.paths[0].protocol: Invalid value: "invalid-protocol": must be one of "http", "http2"`, }, "expose.paths[].path": { - input: &ProxyDefaults{ + &ProxyDefaults{ ObjectMeta: metav1.ObjectMeta{ Name: "global", }, @@ -452,10 +340,10 @@ func TestProxyDefaults_Validate(t *testing.T) { }, }, }, - expectedErrMsg: `proxydefaults.consul.hashicorp.com "global" is invalid: spec.expose.paths[0].path: Invalid value: "invalid-path": must begin with a '/'`, + `proxydefaults.consul.hashicorp.com "global" is invalid: spec.expose.paths[0].path: Invalid value: "invalid-path": must begin with a '/'`, }, "transparentProxy.outboundListenerPort": { - input: &ProxyDefaults{ + &ProxyDefaults{ ObjectMeta: metav1.ObjectMeta{ Name: "global", }, @@ -465,10 +353,10 @@ func TestProxyDefaults_Validate(t *testing.T) { }, }, }, - expectedErrMsg: "proxydefaults.consul.hashicorp.com \"global\" is invalid: spec.transparentProxy.outboundListenerPort: Invalid value: 1000: use the annotation `consul.hashicorp.com/transparent-proxy-outbound-listener-port` to configure the Outbound Listener Port", + "proxydefaults.consul.hashicorp.com \"global\" is invalid: spec.transparentProxy.outboundListenerPort: Invalid value: 1000: use the annotation `consul.hashicorp.com/transparent-proxy-outbound-listener-port` to configure the Outbound Listener Port", }, "mode": { - input: &ProxyDefaults{ + &ProxyDefaults{ ObjectMeta: metav1.ObjectMeta{ Name: "global", }, @@ -476,137 +364,10 @@ func TestProxyDefaults_Validate(t *testing.T) { Mode: proxyModeRef("transparent"), }, }, - expectedErrMsg: "proxydefaults.consul.hashicorp.com \"global\" is invalid: spec.mode: Invalid value: \"transparent\": use the annotation `consul.hashicorp.com/transparent-proxy` to configure the Transparent Proxy Mode", - }, - "accessLogs.type": { - input: &ProxyDefaults{ - ObjectMeta: metav1.ObjectMeta{ - Name: "global", - }, - Spec: ProxyDefaultsSpec{ - AccessLogs: &AccessLogs{ - Type: "foo", - }, - }, - }, - expectedErrMsg: "proxydefaults.consul.hashicorp.com \"global\" is invalid: spec.accessLogs.type: Invalid value: \"foo\": invalid access log type (must be one of \"stdout\", \"stderr\", \"file\"", - }, - "accessLogs.path missing": { - input: &ProxyDefaults{ - ObjectMeta: metav1.ObjectMeta{ - Name: "global", - }, - Spec: ProxyDefaultsSpec{ - AccessLogs: &AccessLogs{ - Type: "file", - }, - }, - }, - expectedErrMsg: "proxydefaults.consul.hashicorp.com \"global\" is invalid: spec.accessLogs.path: Invalid value: \"\": path must be specified when using file type access logs", - }, - "accessLogs.path for wrong type": { - input: &ProxyDefaults{ - ObjectMeta: metav1.ObjectMeta{ - Name: "global", - }, - Spec: ProxyDefaultsSpec{ - AccessLogs: &AccessLogs{ - Path: "/var/log/envoy.logs", - }, - }, - }, - expectedErrMsg: "proxydefaults.consul.hashicorp.com \"global\" is invalid: spec.accessLogs.path: Invalid value: \"/var/log/envoy.logs\": path is only valid for file type access logs", - }, - "accessLogs.jsonFormat": { - input: &ProxyDefaults{ - ObjectMeta: metav1.ObjectMeta{ - Name: "global", - }, - Spec: ProxyDefaultsSpec{ - AccessLogs: &AccessLogs{ - JSONFormat: "{ \"start_time\": \"%START_TIME\"", // intentionally missing the closing brace - }, - }, - }, - expectedErrMsg: "proxydefaults.consul.hashicorp.com \"global\" is invalid: spec.accessLogs.jsonFormat: Invalid value: \"{ \\\"start_time\\\": \\\"%START_TIME\\\"\": invalid access log json", - }, - "accessLogs.textFormat": { - input: &ProxyDefaults{ - ObjectMeta: metav1.ObjectMeta{ - Name: "global", - }, - Spec: ProxyDefaultsSpec{ - AccessLogs: &AccessLogs{ - JSONFormat: "{ \"start_time\": \"%START_TIME\" }", - TextFormat: "MY START TIME %START_TIME", - }, - }, - }, - expectedErrMsg: "proxydefaults.consul.hashicorp.com \"global\" is invalid: spec.accessLogs.textFormat: Invalid value: \"MY START TIME %START_TIME\": cannot specify both access log jsonFormat and textFormat", - }, - "envoyExtension.arguments single empty": { - input: &ProxyDefaults{ - ObjectMeta: metav1.ObjectMeta{ - Name: "global", - }, - Spec: ProxyDefaultsSpec{ - EnvoyExtensions: EnvoyExtensions{ - EnvoyExtension{ - Name: "aws_request_signing", - Arguments: json.RawMessage(`{"AWSServiceName": "s3", "Region": "us-west-2"}`), - Required: false, - }, - EnvoyExtension{ - Name: "zipkin", - Arguments: nil, - Required: true, - }, - }, - }, - }, - expectedErrMsg: `proxydefaults.consul.hashicorp.com "global" is invalid: spec.envoyExtensions.envoyExtension[1].arguments: Required value: arguments must be defined`, - }, - "envoyExtension.arguments multi empty": { - input: &ProxyDefaults{ - ObjectMeta: metav1.ObjectMeta{ - Name: "global", - }, - Spec: ProxyDefaultsSpec{ - EnvoyExtensions: EnvoyExtensions{ - EnvoyExtension{ - Name: "aws_request_signing", - Arguments: nil, - Required: false, - }, - EnvoyExtension{ - Name: "zipkin", - Arguments: nil, - Required: true, - }, - }, - }, - }, - expectedErrMsg: `proxydefaults.consul.hashicorp.com "global" is invalid: [spec.envoyExtensions.envoyExtension[0].arguments: Required value: arguments must be defined, spec.envoyExtensions.envoyExtension[1].arguments: Required value: arguments must be defined]`, - }, - "envoyExtension.arguments invalid json": { - input: &ProxyDefaults{ - ObjectMeta: metav1.ObjectMeta{ - Name: "global", - }, - Spec: ProxyDefaultsSpec{ - EnvoyExtensions: EnvoyExtensions{ - EnvoyExtension{ - Name: "aws_request_signing", - Arguments: json.RawMessage(`{"SOME_INVALID_JSON"}`), - Required: false, - }, - }, - }, - }, - expectedErrMsg: `proxydefaults.consul.hashicorp.com "global" is invalid: spec.envoyExtensions.envoyExtension[0].arguments: Invalid value: "{\"SOME_INVALID_JSON\"}": must be valid map value: invalid character '}' after object key`, + "proxydefaults.consul.hashicorp.com \"global\" is invalid: spec.mode: Invalid value: \"transparent\": use the annotation `consul.hashicorp.com/transparent-proxy` to configure the Transparent Proxy Mode", }, "multi-error": { - input: &ProxyDefaults{ + &ProxyDefaults{ ObjectMeta: metav1.ObjectMeta{ Name: "global", }, @@ -625,14 +386,10 @@ func TestProxyDefaults_Validate(t *testing.T) { TransparentProxy: &TransparentProxy{ OutboundListenerPort: 1000, }, - AccessLogs: &AccessLogs{ - JSONFormat: "{ \"start_time\": \"%START_TIME\" }", - TextFormat: "MY START TIME %START_TIME", - }, Mode: proxyModeRef("transparent"), }, }, - expectedErrMsg: "proxydefaults.consul.hashicorp.com \"global\" is invalid: [spec.meshGateway.mode: Invalid value: \"invalid-mode\": must be one of \"remote\", \"local\", \"none\", \"\", spec.transparentProxy.outboundListenerPort: Invalid value: 1000: use the annotation `consul.hashicorp.com/transparent-proxy-outbound-listener-port` to configure the Outbound Listener Port, spec.mode: Invalid value: \"transparent\": use the annotation `consul.hashicorp.com/transparent-proxy` to configure the Transparent Proxy Mode, spec.accessLogs.textFormat: Invalid value: \"MY START TIME %START_TIME\": cannot specify both access log jsonFormat and textFormat, spec.expose.paths[0].path: Invalid value: \"invalid-path\": must begin with a '/', spec.expose.paths[0].protocol: Invalid value: \"invalid-protocol\": must be one of \"http\", \"http2\"]", + "proxydefaults.consul.hashicorp.com \"global\" is invalid: [spec.meshGateway.mode: Invalid value: \"invalid-mode\": must be one of \"remote\", \"local\", \"none\", \"\", spec.transparentProxy.outboundListenerPort: Invalid value: 1000: use the annotation `consul.hashicorp.com/transparent-proxy-outbound-listener-port` to configure the Outbound Listener Port, spec.mode: Invalid value: \"transparent\": use the annotation `consul.hashicorp.com/transparent-proxy` to configure the Transparent Proxy Mode, spec.expose.paths[0].path: Invalid value: \"invalid-path\": must begin with a '/', spec.expose.paths[0].protocol: Invalid value: \"invalid-protocol\": must be one of \"http\", \"http2\"]", }, } for name, testCase := range cases { diff --git a/control-plane/api/v1alpha1/proxydefaults_webhook_test.go b/control-plane/api/v1alpha1/proxydefaults_webhook_test.go index 3136540089..cc36d994dd 100644 --- a/control-plane/api/v1alpha1/proxydefaults_webhook_test.go +++ b/control-plane/api/v1alpha1/proxydefaults_webhook_test.go @@ -46,7 +46,7 @@ func TestValidateProxyDefault(t *testing.T) { }, expAllow: false, // This error message is because the value "1" is valid JSON but is an invalid map - expErrMessage: "proxydefaults.consul.hashicorp.com \"global\" is invalid: spec.config: Invalid value: \"1\": must be valid map value: json: cannot unmarshal number into Go value of type map[string]interface {}", + expErrMessage: "proxydefaults.consul.hashicorp.com \"global\" is invalid: spec.config: Invalid value: json.RawMessage{0x31}: must be valid map value: json: cannot unmarshal number into Go value of type map[string]interface {}", }, "proxy default exists": { existingResources: []runtime.Object{&ProxyDefaults{ diff --git a/control-plane/api/v1alpha1/servicedefaults_types.go b/control-plane/api/v1alpha1/servicedefaults_types.go index 06da8b1d2c..a5193e980f 100644 --- a/control-plane/api/v1alpha1/servicedefaults_types.go +++ b/control-plane/api/v1alpha1/servicedefaults_types.go @@ -4,9 +4,11 @@ import ( "fmt" "net" "strings" + "time" "github.com/google/go-cmp/cmp" "github.com/google/go-cmp/cmp/cmpopts" + "github.com/hashicorp/consul-k8s/control-plane/api/common" capi "github.com/hashicorp/consul/api" "github.com/miekg/dns" corev1 "k8s.io/api/core/v1" @@ -14,8 +16,6 @@ import ( metav1 "k8s.io/apimachinery/pkg/apis/meta/v1" "k8s.io/apimachinery/pkg/runtime/schema" "k8s.io/apimachinery/pkg/util/validation/field" - - "github.com/hashicorp/consul-k8s/control-plane/api/common" ) const ( @@ -89,19 +89,13 @@ type ServiceDefaultsSpec struct { // MaxInboundConnections is the maximum number of concurrent inbound connections to // each service instance. Defaults to 0 (using consul's default) if not set. MaxInboundConnections int `json:"maxInboundConnections,omitempty"` - // LocalConnectTimeoutMs is the number of milliseconds allowed to make connections to the local application + // The number of milliseconds allowed to make connections to the local application // instance before timing out. Defaults to 5000. LocalConnectTimeoutMs int `json:"localConnectTimeoutMs,omitempty"` - // LocalRequestTimeoutMs is the timeout for HTTP requests to the local application instance in milliseconds. + // In milliseconds, the timeout for HTTP requests to the local application instance. // Applies to HTTP-based protocols only. If not specified, inherits the Envoy default for // route timeouts (15s). LocalRequestTimeoutMs int `json:"localRequestTimeoutMs,omitempty"` - // BalanceInboundConnections sets the strategy for allocating inbound connections to the service across - // proxy threads. The only supported value is exact_balance. By default, no connection balancing is used. - // Refer to the Envoy Connection Balance config for details. - BalanceInboundConnections string `json:"balanceInboundConnections,omitempty"` - // EnvoyExtensions are a list of extensions to modify Envoy proxy configuration. - EnvoyExtensions EnvoyExtensions `json:"envoyExtensions,omitempty"` } type Upstreams struct { @@ -114,14 +108,12 @@ type Upstreams struct { } type Upstream struct { - // Name is only accepted within service ServiceDefaultsSpec.UpstreamConfig.Overrides config entry. + // Name is only accepted within a service-defaults config entry. Name string `json:"name,omitempty"` - // Namespace is only accepted within service ServiceDefaultsSpec.UpstreamConfig.Overrides config entry. + // Namespace is only accepted within a service-defaults config entry. Namespace string `json:"namespace,omitempty"` - // Partition is only accepted within service ServiceDefaultsSpec.UpstreamConfig.Overrides config entry. + // Partition is only accepted within a service-defaults config entry. Partition string `json:"partition,omitempty"` - // Peer is only accepted within service ServiceDefaultsSpec.UpstreamConfig.Overrides config entry. - Peer string `json:"peer,omitempty"` // EnvoyListenerJSON is a complete override ("escape hatch") for the upstream's // listener. // Note: This escape hatch is NOT compatible with the discovery chain and @@ -181,6 +173,13 @@ type PassiveHealthCheck struct { // when an outlier status is detected through consecutive 5xx. // This setting can be used to disable ejection or to ramp it up slowly. EnforcingConsecutive5xx *uint32 `json:"enforcing_consecutive_5xx,omitempty"` + // The maximum % of an upstream cluster that can be ejected due to outlier detection. + // Defaults to 10% but will eject at least one host regardless of the value. + MaxEjectionPercent *uint32 `json:",omitempty" alias:"max_ejection_percent"` + // The base time that a host is ejected for. The real time is equal to the base time + // multiplied by the number of times the host has been ejected and is capped by + // max_ejection_time (Default 300s). Defaults to 30000ms or 30s. + BaseEjectionTime *time.Duration `json:",omitempty" alias:"base_ejection_time"` } type ServiceDefaultsDestination struct { @@ -269,21 +268,19 @@ func (in *ServiceDefaults) SyncedConditionStatus() corev1.ConditionStatus { // ToConsul converts the entry into it's Consul equivalent struct. func (in *ServiceDefaults) ToConsul(datacenter string) capi.ConfigEntry { return &capi.ServiceConfigEntry{ - Kind: in.ConsulKind(), - Name: in.ConsulName(), - Protocol: in.Spec.Protocol, - MeshGateway: in.Spec.MeshGateway.toConsul(), - Expose: in.Spec.Expose.toConsul(), - ExternalSNI: in.Spec.ExternalSNI, - TransparentProxy: in.Spec.TransparentProxy.toConsul(), - UpstreamConfig: in.Spec.UpstreamConfig.toConsul(), - Destination: in.Spec.Destination.toConsul(), - Meta: meta(datacenter), - MaxInboundConnections: in.Spec.MaxInboundConnections, - LocalConnectTimeoutMs: in.Spec.LocalConnectTimeoutMs, - LocalRequestTimeoutMs: in.Spec.LocalRequestTimeoutMs, - BalanceInboundConnections: in.Spec.BalanceInboundConnections, - EnvoyExtensions: in.Spec.EnvoyExtensions.toConsul(), + Kind: in.ConsulKind(), + Name: in.ConsulName(), + Protocol: in.Spec.Protocol, + MeshGateway: in.Spec.MeshGateway.toConsul(), + Expose: in.Spec.Expose.toConsul(), + ExternalSNI: in.Spec.ExternalSNI, + TransparentProxy: in.Spec.TransparentProxy.toConsul(), + UpstreamConfig: in.Spec.UpstreamConfig.toConsul(), + Destination: in.Spec.Destination.toConsul(), + Meta: meta(datacenter), + MaxInboundConnections: in.Spec.MaxInboundConnections, + LocalConnectTimeoutMs: in.Spec.LocalConnectTimeoutMs, + LocalRequestTimeoutMs: in.Spec.LocalRequestTimeoutMs, } } @@ -322,13 +319,8 @@ func (in *ServiceDefaults) Validate(consulMeta common.ConsulMeta) error { allErrs = append(allErrs, field.Invalid(path.Child("localRequestTimeoutMs"), in.Spec.LocalRequestTimeoutMs, "LocalRequestTimeoutMs must be > 0")) } - if in.Spec.BalanceInboundConnections != "" && in.Spec.BalanceInboundConnections != "exact_balance" { - allErrs = append(allErrs, field.Invalid(path.Child("balanceInboundConnections"), in.Spec.BalanceInboundConnections, "BalanceInboundConnections must be an empty string or exact_balance")) - } - allErrs = append(allErrs, in.Spec.UpstreamConfig.validate(path.Child("upstreamConfig"), consulMeta.PartitionsEnabled)...) allErrs = append(allErrs, in.Spec.Expose.validate(path.Child("expose"))...) - allErrs = append(allErrs, in.Spec.EnvoyExtensions.validate(path.Child("envoyExtensions"))...) if len(allErrs) > 0 { return apierrors.NewInvalid( @@ -377,25 +369,10 @@ func (in *Upstream) validate(path *field.Path, kind string, partitionsEnabled bo if in.Name != "" { errs = append(errs, field.Invalid(path.Child("name"), in.Name, "upstream.name for a default upstream must be \"\"")) } - if in.Namespace != "" { - errs = append(errs, field.Invalid(path.Child("namespace"), in.Namespace, "upstream.namespace for a default upstream must be \"\"")) - } - if in.Partition != "" { - errs = append(errs, field.Invalid(path.Child("partition"), in.Partition, "upstream.partition for a default upstream must be \"\"")) - } - if in.Peer != "" { - errs = append(errs, field.Invalid(path.Child("peer"), in.Peer, "upstream.peer for a default upstream must be \"\"")) - } } else if kind == overrideUpstream { if in.Name == "" { errs = append(errs, field.Invalid(path.Child("name"), in.Name, "upstream.name for an override upstream cannot be \"\"")) } - if in.Namespace != "" && in.Peer != "" { - errs = append(errs, field.Invalid(path, in, "both namespace and peer cannot be specified.")) - } - if in.Partition != "" && in.Peer != "" { - errs = append(errs, field.Invalid(path, in, "both partition and peer cannot be specified.")) - } } if !partitionsEnabled && in.Partition != "" { errs = append(errs, field.Invalid(path.Child("partition"), in.Partition, "Consul Enterprise Admin Partitions must be enabled to set upstream.partition")) @@ -414,7 +391,6 @@ func (in *Upstream) toConsul() *capi.UpstreamConfig { Name: in.Name, Namespace: in.Namespace, Partition: in.Partition, - Peer: in.Peer, EnvoyListenerJSON: in.EnvoyListenerJSON, EnvoyClusterJSON: in.EnvoyClusterJSON, Protocol: in.Protocol, @@ -445,6 +421,8 @@ func (in *PassiveHealthCheck) toConsul() *capi.PassiveHealthCheck { Interval: in.Interval.Duration, MaxFailures: in.MaxFailures, EnforcingConsecutive5xx: in.EnforcingConsecutive5xx, + MaxEjectionPercent: in.MaxEjectionPercent, + BaseEjectionTime: in.BaseEjectionTime, } } diff --git a/control-plane/api/v1alpha1/servicedefaults_types_test.go b/control-plane/api/v1alpha1/servicedefaults_types_test.go index 33ec6d2f40..8404d94934 100644 --- a/control-plane/api/v1alpha1/servicedefaults_types_test.go +++ b/control-plane/api/v1alpha1/servicedefaults_types_test.go @@ -1,17 +1,15 @@ package v1alpha1 import ( - "encoding/json" "testing" "time" + "github.com/hashicorp/consul-k8s/control-plane/api/common" capi "github.com/hashicorp/consul/api" "github.com/stretchr/testify/require" corev1 "k8s.io/api/core/v1" metav1 "k8s.io/apimachinery/pkg/apis/meta/v1" "k8s.io/utils/pointer" - - "github.com/hashicorp/consul-k8s/control-plane/api/common" ) func TestServiceDefaults_ToConsul(t *testing.T) { @@ -87,6 +85,8 @@ func TestServiceDefaults_ToConsul(t *testing.T) { }, MaxFailures: uint32(20), EnforcingConsecutive5xx: pointer.Uint32(100), + MaxEjectionPercent: pointer.Uint32(10), + BaseEjectionTime: pointer.Duration(10 * time.Second), }, MeshGateway: MeshGateway{ Mode: "local", @@ -112,6 +112,8 @@ func TestServiceDefaults_ToConsul(t *testing.T) { }, MaxFailures: uint32(10), EnforcingConsecutive5xx: pointer.Uint32(60), + MaxEjectionPercent: pointer.Uint32(20), + BaseEjectionTime: pointer.Duration(20 * time.Second), }, MeshGateway: MeshGateway{ Mode: "remote", @@ -136,6 +138,8 @@ func TestServiceDefaults_ToConsul(t *testing.T) { }, MaxFailures: uint32(10), EnforcingConsecutive5xx: pointer.Uint32(60), + MaxEjectionPercent: pointer.Uint32(30), + BaseEjectionTime: pointer.Duration(30 * time.Second), }, MeshGateway: MeshGateway{ Mode: "remote", @@ -143,19 +147,6 @@ func TestServiceDefaults_ToConsul(t *testing.T) { }, }, }, - BalanceInboundConnections: "exact_balance", - EnvoyExtensions: EnvoyExtensions{ - EnvoyExtension{ - Name: "aws_request_signing", - Arguments: json.RawMessage(`{"AWSServiceName": "s3", "Region": "us-west-2"}`), - Required: false, - }, - EnvoyExtension{ - Name: "zipkin", - Arguments: json.RawMessage(`{"ClusterName": "zipkin_cluster", "Port": "9411", "CollectorEndpoint":"/api/v2/spans"}`), - Required: true, - }, - }, Destination: &ServiceDefaultsDestination{ Addresses: []string{"api.google.com"}, Port: 443, @@ -212,6 +203,8 @@ func TestServiceDefaults_ToConsul(t *testing.T) { Interval: 2 * time.Second, MaxFailures: uint32(20), EnforcingConsecutive5xx: pointer.Uint32(100), + MaxEjectionPercent: pointer.Uint32(10), + BaseEjectionTime: pointer.Duration(10 * time.Second), }, MeshGateway: capi.MeshGatewayConfig{ Mode: "local", @@ -235,6 +228,8 @@ func TestServiceDefaults_ToConsul(t *testing.T) { Interval: 2 * time.Second, MaxFailures: uint32(10), EnforcingConsecutive5xx: pointer.Uint32(60), + MaxEjectionPercent: pointer.Uint32(20), + BaseEjectionTime: pointer.Duration(20 * time.Second), }, MeshGateway: capi.MeshGatewayConfig{ Mode: "remote", @@ -257,6 +252,8 @@ func TestServiceDefaults_ToConsul(t *testing.T) { Interval: 2 * time.Second, MaxFailures: uint32(10), EnforcingConsecutive5xx: pointer.Uint32(60), + MaxEjectionPercent: pointer.Uint32(30), + BaseEjectionTime: pointer.Duration(30 * time.Second), }, MeshGateway: capi.MeshGatewayConfig{ Mode: "remote", @@ -264,26 +261,6 @@ func TestServiceDefaults_ToConsul(t *testing.T) { }, }, }, - BalanceInboundConnections: "exact_balance", - EnvoyExtensions: []capi.EnvoyExtension{ - { - Name: "aws_request_signing", - Arguments: map[string]interface{}{ - "AWSServiceName": "s3", - "Region": "us-west-2", - }, - Required: false, - }, - { - Name: "zipkin", - Arguments: map[string]interface{}{ - "ClusterName": "zipkin_cluster", - "Port": "9411", - "CollectorEndpoint": "/api/v2/spans", - }, - Required: true, - }, - }, Destination: &capi.DestinationConfig{ Addresses: []string{"api.google.com"}, Port: 443, @@ -383,6 +360,8 @@ func TestServiceDefaults_MatchesConsul(t *testing.T) { }, MaxFailures: uint32(20), EnforcingConsecutive5xx: pointer.Uint32(100), + MaxEjectionPercent: pointer.Uint32(10), + BaseEjectionTime: pointer.Duration(10 * time.Second), }, MeshGateway: MeshGateway{ Mode: "local", @@ -407,6 +386,8 @@ func TestServiceDefaults_MatchesConsul(t *testing.T) { }, MaxFailures: uint32(10), EnforcingConsecutive5xx: pointer.Uint32(60), + MaxEjectionPercent: pointer.Uint32(20), + BaseEjectionTime: pointer.Duration(20 * time.Second), }, MeshGateway: MeshGateway{ Mode: "remote", @@ -430,6 +411,8 @@ func TestServiceDefaults_MatchesConsul(t *testing.T) { }, MaxFailures: uint32(10), EnforcingConsecutive5xx: pointer.Uint32(60), + MaxEjectionPercent: pointer.Uint32(30), + BaseEjectionTime: pointer.Duration(30 * time.Second), }, MeshGateway: MeshGateway{ Mode: "remote", @@ -437,19 +420,6 @@ func TestServiceDefaults_MatchesConsul(t *testing.T) { }, }, }, - BalanceInboundConnections: "exact_balance", - EnvoyExtensions: EnvoyExtensions{ - EnvoyExtension{ - Name: "aws_request_signing", - Arguments: json.RawMessage(`{"AWSServiceName": "s3", "Region": "us-west-2"}`), - Required: false, - }, - EnvoyExtension{ - Name: "zipkin", - Arguments: json.RawMessage(`{"ClusterName": "zipkin_cluster", "Port": "9411", "CollectorEndpoint":"/api/v2/spans"}`), - Required: true, - }, - }, Destination: &ServiceDefaultsDestination{ Addresses: []string{"api.google.com"}, Port: 443, @@ -501,6 +471,8 @@ func TestServiceDefaults_MatchesConsul(t *testing.T) { Interval: 2 * time.Second, MaxFailures: uint32(20), EnforcingConsecutive5xx: pointer.Uint32(100), + MaxEjectionPercent: pointer.Uint32(10), + BaseEjectionTime: pointer.Duration(10 * time.Second), }, MeshGateway: capi.MeshGatewayConfig{ Mode: "local", @@ -523,6 +495,8 @@ func TestServiceDefaults_MatchesConsul(t *testing.T) { Interval: 2 * time.Second, MaxFailures: uint32(10), EnforcingConsecutive5xx: pointer.Uint32(60), + MaxEjectionPercent: pointer.Uint32(20), + BaseEjectionTime: pointer.Duration(20 * time.Second), }, MeshGateway: capi.MeshGatewayConfig{ Mode: "remote", @@ -544,6 +518,8 @@ func TestServiceDefaults_MatchesConsul(t *testing.T) { Interval: 2 * time.Second, MaxFailures: uint32(10), EnforcingConsecutive5xx: pointer.Uint32(60), + MaxEjectionPercent: pointer.Uint32(30), + BaseEjectionTime: pointer.Duration(30 * time.Second), }, MeshGateway: capi.MeshGatewayConfig{ Mode: "remote", @@ -551,26 +527,6 @@ func TestServiceDefaults_MatchesConsul(t *testing.T) { }, }, }, - BalanceInboundConnections: "exact_balance", - EnvoyExtensions: []capi.EnvoyExtension{ - { - Name: "aws_request_signing", - Arguments: map[string]interface{}{ - "AWSServiceName": "s3", - "Region": "us-west-2", - }, - Required: false, - }, - { - Name: "zipkin", - Arguments: map[string]interface{}{ - "ClusterName": "zipkin_cluster", - "Port": "9411", - "CollectorEndpoint": "/api/v2/spans", - }, - Required: true, - }, - }, Destination: &capi.DestinationConfig{ Addresses: []string{"api.google.com"}, Port: 443, @@ -706,39 +662,6 @@ func TestServiceDefaults_Validate(t *testing.T) { }, expectedErrMsg: "", }, - "valid - balanceInboundConnections": { - input: &ServiceDefaults{ - ObjectMeta: metav1.ObjectMeta{ - Name: "my-service", - }, - Spec: ServiceDefaultsSpec{ - BalanceInboundConnections: "exact_balance", - }, - }, - expectedErrMsg: "", - }, - "valid - envoyExtension": { - input: &ServiceDefaults{ - ObjectMeta: metav1.ObjectMeta{ - Name: "my-service", - }, - Spec: ServiceDefaultsSpec{ - EnvoyExtensions: EnvoyExtensions{ - EnvoyExtension{ - Name: "aws_request_signing", - Arguments: json.RawMessage(`{"AWSServiceName": "s3", "Region": "us-west-2"}`), - Required: false, - }, - EnvoyExtension{ - Name: "zipkin", - Arguments: json.RawMessage(`{"ClusterName": "zipkin_cluster", "Port": "9411", "CollectorEndpoint":"/api/v2/spans"}`), - Required: true, - }, - }, - }, - }, - expectedErrMsg: "", - }, "protocol": { input: &ServiceDefaults{ ObjectMeta: metav1.ObjectMeta{ @@ -855,21 +778,6 @@ func TestServiceDefaults_Validate(t *testing.T) { }, expectedErrMsg: `servicedefaults.consul.hashicorp.com "my-service" is invalid: spec.upstreamConfig.defaults.name: Invalid value: "foobar": upstream.name for a default upstream must be ""`, }, - "upstreamConfig.defaults.namespace": { - input: &ServiceDefaults{ - ObjectMeta: metav1.ObjectMeta{ - Name: "my-service", - }, - Spec: ServiceDefaultsSpec{ - UpstreamConfig: &Upstreams{ - Defaults: &Upstream{ - Namespace: "foobar", - }, - }, - }, - }, - expectedErrMsg: `servicedefaults.consul.hashicorp.com "my-service" is invalid: spec.upstreamConfig.defaults.namespace: Invalid value: "foobar": upstream.namespace for a default upstream must be ""`, - }, "upstreamConfig.defaults.partition": { input: &ServiceDefaults{ ObjectMeta: metav1.ObjectMeta{ @@ -884,22 +792,7 @@ func TestServiceDefaults_Validate(t *testing.T) { }, }, partitionsEnabled: false, - expectedErrMsg: `servicedefaults.consul.hashicorp.com "my-service" is invalid: [spec.upstreamConfig.defaults.partition: Invalid value: "upstream": upstream.partition for a default upstream must be "", spec.upstreamConfig.defaults.partition: Invalid value: "upstream": Consul Enterprise Admin Partitions must be enabled to set upstream.partition]`, - }, - "upstreamConfig.defaults.peer": { - input: &ServiceDefaults{ - ObjectMeta: metav1.ObjectMeta{ - Name: "my-service", - }, - Spec: ServiceDefaultsSpec{ - UpstreamConfig: &Upstreams{ - Defaults: &Upstream{ - Peer: "foobar", - }, - }, - }, - }, - expectedErrMsg: `servicedefaults.consul.hashicorp.com "my-service" is invalid: spec.upstreamConfig.defaults.peer: Invalid value: "foobar": upstream.peer for a default upstream must be ""`, + expectedErrMsg: `servicedefaults.consul.hashicorp.com "my-service" is invalid: spec.upstreamConfig.defaults.partition: Invalid value: "upstream": Consul Enterprise Admin Partitions must be enabled to set upstream.partition`, }, "upstreamConfig.overrides.meshGateway": { input: &ServiceDefaults{ @@ -956,44 +849,6 @@ func TestServiceDefaults_Validate(t *testing.T) { }, expectedErrMsg: `servicedefaults.consul.hashicorp.com "my-service" is invalid: spec.upstreamConfig.overrides[0].partition: Invalid value: "upstream": Consul Enterprise Admin Partitions must be enabled to set upstream.partition`, }, - "upstreamConfig.overrides.partition and namespace": { - input: &ServiceDefaults{ - ObjectMeta: metav1.ObjectMeta{ - Name: "my-service", - }, - Spec: ServiceDefaultsSpec{ - UpstreamConfig: &Upstreams{ - Overrides: []*Upstream{ - { - Name: "service", - Namespace: "namespace", - Peer: "peer", - }, - }, - }, - }, - }, - expectedErrMsg: `servicedefaults.consul.hashicorp.com "my-service" is invalid: spec.upstreamConfig.overrides[0]: Invalid value: v1alpha1.Upstream{Name:"service", Namespace:"namespace", Partition:"", Peer:"peer", EnvoyListenerJSON:"", EnvoyClusterJSON:"", Protocol:"", ConnectTimeoutMs:0, Limits:(*v1alpha1.UpstreamLimits)(nil), PassiveHealthCheck:(*v1alpha1.PassiveHealthCheck)(nil), MeshGateway:v1alpha1.MeshGateway{Mode:""}}: both namespace and peer cannot be specified.`, - }, - "upstreamConfig.overrides.partition and peer": { - input: &ServiceDefaults{ - ObjectMeta: metav1.ObjectMeta{ - Name: "my-service", - }, - Spec: ServiceDefaultsSpec{ - UpstreamConfig: &Upstreams{ - Overrides: []*Upstream{ - { - Name: "service", - Partition: "upstream", - Peer: "peer", - }, - }, - }, - }, - }, - expectedErrMsg: `servicedefaults.consul.hashicorp.com "my-service" is invalid: [spec.upstreamConfig.overrides[0]: Invalid value: v1alpha1.Upstream{Name:"service", Namespace:"", Partition:"upstream", Peer:"peer", EnvoyListenerJSON:"", EnvoyClusterJSON:"", Protocol:"", ConnectTimeoutMs:0, Limits:(*v1alpha1.UpstreamLimits)(nil), PassiveHealthCheck:(*v1alpha1.PassiveHealthCheck)(nil), MeshGateway:v1alpha1.MeshGateway{Mode:""}}: both partition and peer cannot be specified., spec.upstreamConfig.overrides[0].partition: Invalid value: "upstream": Consul Enterprise Admin Partitions must be enabled to set upstream.partition]`, - }, "multi-error": { input: &ServiceDefaults{ ObjectMeta: metav1.ObjectMeta{ @@ -1084,111 +939,6 @@ func TestServiceDefaults_Validate(t *testing.T) { }, expectedErrMsg: `servicedefaults.consul.hashicorp.com "my-service" is invalid: spec.destination.port: Invalid value: 0x0: invalid port number`, }, - "MaxInboundConnections (invalid value)": { - input: &ServiceDefaults{ - ObjectMeta: metav1.ObjectMeta{ - Name: "my-service", - }, - Spec: ServiceDefaultsSpec{ - MaxInboundConnections: -1, - }, - }, - expectedErrMsg: `servicedefaults.consul.hashicorp.com "my-service" is invalid: spec.maxinboundconnections: Invalid value: -1: MaxInboundConnections must be > 0`, - }, - "LocalConnectTimeoutMs (invalid value)": { - input: &ServiceDefaults{ - ObjectMeta: metav1.ObjectMeta{ - Name: "my-service", - }, - Spec: ServiceDefaultsSpec{ - LocalConnectTimeoutMs: -1, - }, - }, - expectedErrMsg: `servicedefaults.consul.hashicorp.com "my-service" is invalid: spec.localConnectTimeoutMs: Invalid value: -1: LocalConnectTimeoutMs must be > 0`, - }, - "LocalRequestTimeoutMs (invalid value)": { - input: &ServiceDefaults{ - ObjectMeta: metav1.ObjectMeta{ - Name: "my-service", - }, - Spec: ServiceDefaultsSpec{ - LocalRequestTimeoutMs: -1, - }, - }, - expectedErrMsg: `servicedefaults.consul.hashicorp.com "my-service" is invalid: spec.localRequestTimeoutMs: Invalid value: -1: LocalRequestTimeoutMs must be > 0`, - }, - "balanceInboundConnections (invalid value)": { - input: &ServiceDefaults{ - ObjectMeta: metav1.ObjectMeta{ - Name: "my-service", - }, - Spec: ServiceDefaultsSpec{ - BalanceInboundConnections: "not_exact_balance", - }, - }, - expectedErrMsg: `servicedefaults.consul.hashicorp.com "my-service" is invalid: spec.balanceInboundConnections: Invalid value: "not_exact_balance": BalanceInboundConnections must be an empty string or exact_balance`, - }, - "envoyExtension.arguments (single empty)": { - input: &ServiceDefaults{ - ObjectMeta: metav1.ObjectMeta{ - Name: "my-service", - }, - Spec: ServiceDefaultsSpec{ - EnvoyExtensions: EnvoyExtensions{ - EnvoyExtension{ - Name: "aws_request_signing", - Arguments: json.RawMessage(`{"AWSServiceName": "s3", "Region": "us-west-2"}`), - Required: false, - }, - EnvoyExtension{ - Name: "zipkin", - Arguments: nil, - Required: true, - }, - }, - }, - }, - expectedErrMsg: `servicedefaults.consul.hashicorp.com "my-service" is invalid: spec.envoyExtensions.envoyExtension[1].arguments: Required value: arguments must be defined`, - }, - "envoyExtension.arguments (multi empty)": { - input: &ServiceDefaults{ - ObjectMeta: metav1.ObjectMeta{ - Name: "my-service", - }, - Spec: ServiceDefaultsSpec{ - EnvoyExtensions: EnvoyExtensions{ - EnvoyExtension{ - Name: "aws_request_signing", - Arguments: nil, - Required: false, - }, - EnvoyExtension{ - Name: "aws_request_signing", - Arguments: nil, - Required: false, - }, - }, - }, - }, - expectedErrMsg: `servicedefaults.consul.hashicorp.com "my-service" is invalid: [spec.envoyExtensions.envoyExtension[0].arguments: Required value: arguments must be defined, spec.envoyExtensions.envoyExtension[1].arguments: Required value: arguments must be defined]`, - }, - "envoyExtension.arguments (invalid json)": { - input: &ServiceDefaults{ - ObjectMeta: metav1.ObjectMeta{ - Name: "my-service", - }, - Spec: ServiceDefaultsSpec{ - EnvoyExtensions: EnvoyExtensions{ - EnvoyExtension{ - Name: "aws_request_signing", - Arguments: json.RawMessage(`{"SOME_INVALID_JSON"}`), - Required: false, - }, - }, - }, - }, - expectedErrMsg: `servicedefaults.consul.hashicorp.com "my-service" is invalid: spec.envoyExtensions.envoyExtension[0].arguments: Invalid value: "{\"SOME_INVALID_JSON\"}": must be valid map value: invalid character '}' after object key`, - }, } for name, testCase := range cases { diff --git a/control-plane/api/v1alpha1/shared_types.go b/control-plane/api/v1alpha1/shared_types.go index edcaba5a46..9b884cf476 100644 --- a/control-plane/api/v1alpha1/shared_types.go +++ b/control-plane/api/v1alpha1/shared_types.go @@ -1,7 +1,6 @@ package v1alpha1 import ( - "encoding/json" "fmt" "strings" @@ -80,19 +79,6 @@ type HTTPHeaderModifiers struct { Remove []string `json:"remove,omitempty"` } -// EnvoyExtension has configuration for an extension that patches Envoy resources. -type EnvoyExtension struct { - Name string `json:"name,omitempty"` - Required bool `json:"required,omitempty"` - // +kubebuilder:validation:Type=object - // +kubebuilder:validation:Schemaless - // +kubebuilder:pruning:PreserveUnknownFields - Arguments json.RawMessage `json:"arguments,omitempty"` -} - -// EnvoyExtensions represents a list of the EnvoyExtension configuration. -type EnvoyExtensions []EnvoyExtension - func (in MeshGateway) toConsul() capi.MeshGatewayConfig { mode := capi.MeshGatewayMode(in.Mode) switch mode { @@ -190,58 +176,6 @@ func (in *HTTPHeaderModifiers) toConsul() *capi.HTTPHeaderModifiers { } } -func (in EnvoyExtensions) toConsul() []capi.EnvoyExtension { - if in == nil { - return nil - } - - outConfig := make([]capi.EnvoyExtension, 0) - - for _, e := range in { - consulExtension := capi.EnvoyExtension{ - Name: e.Name, - Required: e.Required, - } - - // We already validate that arguments is present - var args map[string]interface{} - _ = json.Unmarshal(e.Arguments, &args) - consulExtension.Arguments = args - outConfig = append(outConfig, consulExtension) - } - - return outConfig -} - -func (in EnvoyExtensions) validate(path *field.Path) field.ErrorList { - if len(in) == 0 { - return nil - } - - var errs field.ErrorList - for i, e := range in { - if err := e.validate(path.Child("envoyExtension").Index(i)); err != nil { - errs = append(errs, err) - } - } - - return errs -} - -func (in EnvoyExtension) validate(path *field.Path) *field.Error { - // Validate that the arguments are not nil - if in.Arguments == nil { - err := field.Required(path.Child("arguments"), "arguments must be defined") - return err - } - // Validate that the arguments are valid json - var outConfig map[string]interface{} - if err := json.Unmarshal(in.Arguments, &outConfig); err != nil { - return field.Invalid(path.Child("arguments"), string(in.Arguments), fmt.Sprintf(`must be valid map value: %s`, err)) - } - return nil -} - func notInSliceMessage(slice []string) string { return fmt.Sprintf(`must be one of "%s"`, strings.Join(slice, `", "`)) } diff --git a/control-plane/api/v1alpha1/zz_generated.deepcopy.go b/control-plane/api/v1alpha1/zz_generated.deepcopy.go index d12db29d14..213164bc6b 100644 --- a/control-plane/api/v1alpha1/zz_generated.deepcopy.go +++ b/control-plane/api/v1alpha1/zz_generated.deepcopy.go @@ -8,23 +8,9 @@ package v1alpha1 import ( "encoding/json" runtime "k8s.io/apimachinery/pkg/runtime" + timex "time" ) -// DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil. -func (in *AccessLogs) DeepCopyInto(out *AccessLogs) { - *out = *in -} - -// DeepCopy is an autogenerated deepcopy function, copying the receiver, creating a new AccessLogs. -func (in *AccessLogs) DeepCopy() *AccessLogs { - if in == nil { - return nil - } - out := new(AccessLogs) - in.DeepCopyInto(out) - return out -} - // DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil. func (in *Condition) DeepCopyInto(out *Condition) { *out = *in @@ -78,47 +64,6 @@ func (in *CookieConfig) DeepCopy() *CookieConfig { return out } -// DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil. -func (in *EnvoyExtension) DeepCopyInto(out *EnvoyExtension) { - *out = *in - if in.Arguments != nil { - in, out := &in.Arguments, &out.Arguments - *out = make(json.RawMessage, len(*in)) - copy(*out, *in) - } -} - -// DeepCopy is an autogenerated deepcopy function, copying the receiver, creating a new EnvoyExtension. -func (in *EnvoyExtension) DeepCopy() *EnvoyExtension { - if in == nil { - return nil - } - out := new(EnvoyExtension) - in.DeepCopyInto(out) - return out -} - -// DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil. -func (in EnvoyExtensions) DeepCopyInto(out *EnvoyExtensions) { - { - in := &in - *out = make(EnvoyExtensions, len(*in)) - for i := range *in { - (*in)[i].DeepCopyInto(&(*out)[i]) - } - } -} - -// DeepCopy is an autogenerated deepcopy function, copying the receiver, creating a new EnvoyExtensions. -func (in EnvoyExtensions) DeepCopy() EnvoyExtensions { - if in == nil { - return nil - } - out := new(EnvoyExtensions) - in.DeepCopyInto(out) - return *out -} - // DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil. func (in *ExportedService) DeepCopyInto(out *ExportedService) { *out = *in @@ -904,6 +849,16 @@ func (in *PassiveHealthCheck) DeepCopyInto(out *PassiveHealthCheck) { *out = new(uint32) **out = **in } + if in.MaxEjectionPercent != nil { + in, out := &in.MaxEjectionPercent, &out.MaxEjectionPercent + *out = new(uint32) + **out = **in + } + if in.BaseEjectionTime != nil { + in, out := &in.BaseEjectionTime, &out.BaseEjectionTime + *out = new(timex.Duration) + **out = **in + } } // DeepCopy is an autogenerated deepcopy function, copying the receiver, creating a new PassiveHealthCheck. @@ -1260,18 +1215,6 @@ func (in *ProxyDefaultsSpec) DeepCopyInto(out *ProxyDefaultsSpec) { } out.MeshGateway = in.MeshGateway in.Expose.DeepCopyInto(&out.Expose) - if in.AccessLogs != nil { - in, out := &in.AccessLogs, &out.AccessLogs - *out = new(AccessLogs) - **out = **in - } - if in.EnvoyExtensions != nil { - in, out := &in.EnvoyExtensions, &out.EnvoyExtensions - *out = make(EnvoyExtensions, len(*in)) - for i := range *in { - (*in)[i].DeepCopyInto(&(*out)[i]) - } - } } // DeepCopy is an autogenerated deepcopy function, copying the receiver, creating a new ProxyDefaultsSpec. @@ -1449,13 +1392,6 @@ func (in *ServiceDefaultsSpec) DeepCopyInto(out *ServiceDefaultsSpec) { *out = new(ServiceDefaultsDestination) (*in).DeepCopyInto(*out) } - if in.EnvoyExtensions != nil { - in, out := &in.EnvoyExtensions, &out.EnvoyExtensions - *out = make(EnvoyExtensions, len(*in)) - for i := range *in { - (*in)[i].DeepCopyInto(&(*out)[i]) - } - } } // DeepCopy is an autogenerated deepcopy function, copying the receiver, creating a new ServiceDefaultsSpec. diff --git a/control-plane/cni/go.mod b/control-plane/cni/go.mod index aabc1ceaf0..686a391a78 100644 --- a/control-plane/cni/go.mod +++ b/control-plane/cni/go.mod @@ -3,9 +3,9 @@ module github.com/hashicorp/consul-k8s/control-plane/cni require ( github.com/containernetworking/cni v1.1.1 github.com/containernetworking/plugins v1.1.1 - github.com/hashicorp/consul/sdk v0.13.1 - github.com/hashicorp/go-hclog v1.2.1 - github.com/stretchr/testify v1.7.2 + github.com/hashicorp/consul/sdk v0.13.0 + github.com/hashicorp/go-hclog v0.16.1 + github.com/stretchr/testify v1.7.1 k8s.io/api v0.22.2 k8s.io/apimachinery v0.22.2 k8s.io/client-go v0.22.2 @@ -14,7 +14,7 @@ require ( require ( github.com/davecgh/go-spew v1.1.1 // indirect github.com/evanphx/json-patch v5.6.0+incompatible // indirect - github.com/fatih/color v1.13.0 // indirect + github.com/fatih/color v1.12.0 // indirect github.com/go-logr/logr v0.4.0 // indirect github.com/gogo/protobuf v1.3.2 // indirect github.com/golang/protobuf v1.5.2 // indirect @@ -23,24 +23,24 @@ require ( github.com/googleapis/gnostic v0.5.5 // indirect github.com/imdario/mergo v0.3.12 // indirect github.com/json-iterator/go v1.1.11 // indirect - github.com/mattn/go-colorable v0.1.12 // indirect - github.com/mattn/go-isatty v0.0.14 // indirect + github.com/mattn/go-colorable v0.1.8 // indirect + github.com/mattn/go-isatty v0.0.13 // indirect github.com/modern-go/concurrent v0.0.0-20180306012644-bacd9c7ef1dd // indirect github.com/modern-go/reflect2 v1.0.1 // indirect github.com/pkg/errors v0.9.1 // indirect github.com/pmezard/go-difflib v1.0.0 // indirect github.com/spf13/pflag v1.0.5 // indirect - golang.org/x/net v0.0.0-20211216030914-fe4d6282115f // indirect + golang.org/x/net v0.7.0 // indirect golang.org/x/oauth2 v0.0.0-20200107190931-bf48bf16ab8d // indirect - golang.org/x/sys v0.0.0-20220728004956-3c1f35247d10 // indirect - golang.org/x/term v0.0.0-20210220032956-6a3ed077a48d // indirect - golang.org/x/text v0.3.7 // indirect + golang.org/x/sys v0.5.0 // indirect + golang.org/x/term v0.5.0 // indirect + golang.org/x/text v0.7.0 // indirect golang.org/x/time v0.0.0-20210723032227-1f47c861a9ac // indirect google.golang.org/appengine v1.6.7 // indirect - google.golang.org/protobuf v1.27.1 // indirect + google.golang.org/protobuf v1.26.0 // indirect gopkg.in/inf.v0 v0.9.1 // indirect gopkg.in/yaml.v2 v2.4.0 // indirect - gopkg.in/yaml.v3 v3.0.1 // indirect + gopkg.in/yaml.v3 v3.0.0-20210107192922-496545a6307b // indirect k8s.io/klog/v2 v2.9.0 // indirect k8s.io/kube-openapi v0.0.0-20210421082810-95288971da7e // indirect k8s.io/utils v0.0.0-20210819203725-bdf08cb9a70a // indirect @@ -50,4 +50,4 @@ require ( replace github.com/hashicorp/consul/sdk => github.com/hashicorp/consul/sdk v0.4.1-0.20221021205723-cc843c4be892 -go 1.20 +go 1.19 diff --git a/control-plane/cni/go.sum b/control-plane/cni/go.sum index ec1e322cf3..f5c4f60ecb 100644 --- a/control-plane/cni/go.sum +++ b/control-plane/cni/go.sum @@ -57,8 +57,8 @@ github.com/evanphx/json-patch v5.6.0+incompatible h1:jBYDEEiFBPxA0v50tFdvOzQQTCv github.com/evanphx/json-patch v5.6.0+incompatible/go.mod h1:50XU6AFN0ol/bzJsmQLiYLvXMP4fmwYFNcr97nuDLSk= github.com/fatih/color v1.7.0/go.mod h1:Zm6kSWBoL9eyXnKyktHP6abPY2pDugNf5KwzbycvMj4= github.com/fatih/color v1.9.0/go.mod h1:eQcE1qtQxscV5RaZvpXrrb8Drkc3/DdQ+uUYCNjL+zU= -github.com/fatih/color v1.13.0 h1:8LOYc1KYPPmyKMuN8QV2DNRWNbLo6LZ0iLs8+mlH53w= -github.com/fatih/color v1.13.0/go.mod h1:kLAiJbzzSOZDVNGyDpeOxJ47H46qBXwg5ILebYFFOfk= +github.com/fatih/color v1.12.0 h1:mRhaKNwANqRgUBGKmnI5ZxEk7QXmjQeCcuYFMX2bfcc= +github.com/fatih/color v1.12.0/go.mod h1:ELkj/draVOlAH/xkhN6mQ50Qd0MPOk5AAr3maGEBuJM= github.com/form3tech-oss/jwt-go v3.2.2+incompatible/go.mod h1:pbq4aXjuKjdthFRnoDwaVPLA+WlJuPGy+QneDUgJi2k= github.com/form3tech-oss/jwt-go v3.2.3+incompatible/go.mod h1:pbq4aXjuKjdthFRnoDwaVPLA+WlJuPGy+QneDUgJi2k= github.com/fsnotify/fsnotify v1.4.7/go.mod h1:jwhsz4b93w/PPRr/qN1Yymfu8t87LnFCMoQvtojpjFo= @@ -135,8 +135,8 @@ github.com/hashicorp/consul/sdk v0.4.1-0.20221021205723-cc843c4be892 h1:jw0NwPmN github.com/hashicorp/consul/sdk v0.4.1-0.20221021205723-cc843c4be892/go.mod h1:yPkX5Q6CsxTFMjQQDJwzeNmUUF5NUGGbrDsv9wTb8cw= github.com/hashicorp/go-cleanhttp v0.5.1/go.mod h1:JpRdi6/HCYpAwUzNwuwqhbovhLtngrth3wmdIIUrZ80= github.com/hashicorp/go-hclog v0.12.0/go.mod h1:whpDNt7SSdeAju8AWKIWsul05p54N/39EeqMAyrmvFQ= -github.com/hashicorp/go-hclog v1.2.1 h1:YQsLlGDJgwhXFpucSPyVbCBviQtjlHv3jLTlp8YmtEw= -github.com/hashicorp/go-hclog v1.2.1/go.mod h1:W4Qnvbt70Wk/zYJryRzDRU/4r0kIg0PVHBcfoyhpF5M= +github.com/hashicorp/go-hclog v0.16.1 h1:IVQwpTGNRRIHafnTs2dQLIk4ENtneRIEEJWOVDqz99o= +github.com/hashicorp/go-hclog v0.16.1/go.mod h1:whpDNt7SSdeAju8AWKIWsul05p54N/39EeqMAyrmvFQ= github.com/hashicorp/go-uuid v1.0.1/go.mod h1:6SBZvOh/SIDV7/2o3Jml5SYk/TvGqwFJ/bN7x4byOro= github.com/hashicorp/golang-lru v0.5.0/go.mod h1:/m3WP610KZHVQ1SGc6re/UDhFvYD7pJ4Ao+sR/qLZy8= github.com/hashicorp/golang-lru v0.5.1/go.mod h1:/m3WP610KZHVQ1SGc6re/UDhFvYD7pJ4Ao+sR/qLZy8= @@ -162,15 +162,14 @@ github.com/kr/text v0.2.0/go.mod h1:eLer722TekiGuMkidMxC/pM04lWEeraHUUmBw8l2grE= github.com/mailru/easyjson v0.0.0-20190614124828-94de47d64c63/go.mod h1:C1wdFJiN94OJF2b5HbByQZoLdCWB1Yqtg26g4irojpc= github.com/mailru/easyjson v0.0.0-20190626092158-b2ccc519800e/go.mod h1:C1wdFJiN94OJF2b5HbByQZoLdCWB1Yqtg26g4irojpc= github.com/mattn/go-colorable v0.1.4/go.mod h1:U0ppj6V5qS13XJ6of8GYAs25YV2eR4EVcfRqFIhoBtE= -github.com/mattn/go-colorable v0.1.9/go.mod h1:u6P/XSegPjTcexA+o6vUJrdnUu04hMope9wVRipJSqc= -github.com/mattn/go-colorable v0.1.12 h1:jF+Du6AlPIjs2BiUiQlKOX0rt3SujHxPnksPKZbaA40= -github.com/mattn/go-colorable v0.1.12/go.mod h1:u5H1YNBxpqRaxsYJYSkiCWKzEfiAb1Gb520KVy5xxl4= +github.com/mattn/go-colorable v0.1.8 h1:c1ghPdyEDarC70ftn0y+A/Ee++9zz8ljHG1b13eJ0s8= +github.com/mattn/go-colorable v0.1.8/go.mod h1:u6P/XSegPjTcexA+o6vUJrdnUu04hMope9wVRipJSqc= github.com/mattn/go-isatty v0.0.8/go.mod h1:Iq45c/XA43vh69/j3iqttzPXn0bhXyGjM0Hdxcsrc5s= github.com/mattn/go-isatty v0.0.10/go.mod h1:qgIWMr58cqv1PHHyhnkY9lrL7etaEgOFcMEpPG5Rm84= github.com/mattn/go-isatty v0.0.11/go.mod h1:PhnuNfih5lzO57/f3n+odYbM4JtupLOxQOAqxQCu2WE= github.com/mattn/go-isatty v0.0.12/go.mod h1:cbi8OIDigv2wuxKPP5vlRcQ1OAZbq2CE4Kysco4FUpU= -github.com/mattn/go-isatty v0.0.14 h1:yVuAays6BHfxijgZPzw+3Zlu5yQgKGP2/hcQbHb7S9Y= -github.com/mattn/go-isatty v0.0.14/go.mod h1:7GGIvUiUoEMVVmxf/4nioHXj79iQHKdU27kJ6hsGG94= +github.com/mattn/go-isatty v0.0.13 h1:qdl+GuBjcsKKDco5BsxPJlId98mSWNKqYA+Co0SC1yA= +github.com/mattn/go-isatty v0.0.13/go.mod h1:cbi8OIDigv2wuxKPP5vlRcQ1OAZbq2CE4Kysco4FUpU= github.com/mitchellh/mapstructure v1.1.2/go.mod h1:FVVH3fgwuzCH5S8UJGiWEs2h04kUh9fWfEaFds41c1Y= github.com/moby/spdystream v0.2.0/go.mod h1:f7i0iNDQJ059oMTcWxx8MA/zKFIuD/lY+0GqbN2Wy8c= github.com/modern-go/concurrent v0.0.0-20180228061459-e0a39a4cb421/go.mod h1:6dJC0mAP4ikYIbvyc7fijjWJddQyLn8Ig3JB5CqoB9Q= @@ -218,8 +217,8 @@ github.com/stretchr/testify v1.3.0/go.mod h1:M5WIy9Dh21IEIfnGCwXGc5bZfKNJtfHm1UV github.com/stretchr/testify v1.4.0/go.mod h1:j7eGeouHqKxXV5pUuKE4zz7dFj8WfuZ+81PSLYec5m4= github.com/stretchr/testify v1.5.1/go.mod h1:5W2xD1RspED5o8YsWQXVCued0rvSQ+mT+I5cxcmMvtA= github.com/stretchr/testify v1.7.0/go.mod h1:6Fq8oRcR53rry900zMqJjRRixrwX3KX962/h/Wwjteg= -github.com/stretchr/testify v1.7.2 h1:4jaiDzPyXQvSd7D0EjG45355tLlV3VOECpq10pLC+8s= -github.com/stretchr/testify v1.7.2/go.mod h1:R6va5+xMeoiuVRoj+gSkQ7d3FALtqAAGI1FQKckRals= +github.com/stretchr/testify v1.7.1 h1:5TQK59W5E3v0r2duFAb7P95B6hEeOyEnHRa8MjYSMTY= +github.com/stretchr/testify v1.7.1/go.mod h1:6Fq8oRcR53rry900zMqJjRRixrwX3KX962/h/Wwjteg= github.com/yuin/goldmark v1.1.27/go.mod h1:3hX8gzYuyVAZsxl0MRgGTJEmQBFcNTphYh9decYSb74= github.com/yuin/goldmark v1.2.1/go.mod h1:3hX8gzYuyVAZsxl0MRgGTJEmQBFcNTphYh9decYSb74= go.opencensus.io v0.21.0/go.mod h1:mSImk1erAIZhrmZN+AvHh14ztQfjbGwt4TtuofqLduU= @@ -287,8 +286,8 @@ golang.org/x/net v0.0.0-20200520004742-59133d7f0dd7/go.mod h1:qpuaurCH72eLCgpAm/ golang.org/x/net v0.0.0-20201021035429-f5854403a974/go.mod h1:sp8m0HH+o8qH0wwXwYZr8TS3Oi6o0r6Gce1SSxlDquU= golang.org/x/net v0.0.0-20210428140749-89ef3d95e781/go.mod h1:OJAsFXCWl8Ukc7SiCT/9KSuxbyM7479/AVlXFRxuMCk= golang.org/x/net v0.0.0-20210520170846-37e1c6afe023/go.mod h1:9nx3DQGgdP8bBQD5qxJ1jj9UTztislL4KSBs9R2vV5Y= -golang.org/x/net v0.0.0-20211216030914-fe4d6282115f h1:hEYJvxw1lSnWIl8X9ofsYMklzaDs90JI2az5YMd4fPM= -golang.org/x/net v0.0.0-20211216030914-fe4d6282115f/go.mod h1:9nx3DQGgdP8bBQD5qxJ1jj9UTztislL4KSBs9R2vV5Y= +golang.org/x/net v0.7.0 h1:rJrUqqhjsgNp7KqAIc25s9pZnjU7TUcSY7HcVZjdn1g= +golang.org/x/net v0.7.0/go.mod h1:2Tu9+aMcznHK/AK1HMvgo6xiTLG5rD5rZLDS+rp2Bjs= golang.org/x/oauth2 v0.0.0-20180821212333-d2e6202438be/go.mod h1:N/0e6XlmueqKjAGxoOufVs8QHGRruUQn6yWY3a++T0U= golang.org/x/oauth2 v0.0.0-20190226205417-e64efc72b421/go.mod h1:gOpvHmFTYa4IltrdGE7lF6nIHvwfUNPOp7c8zoXwtLw= golang.org/x/oauth2 v0.0.0-20190604053449-0f29369cfe45/go.mod h1:gOpvHmFTYa4IltrdGE7lF6nIHvwfUNPOp7c8zoXwtLw= @@ -335,24 +334,22 @@ golang.org/x/sys v0.0.0-20201119102817-f84b799fce68/go.mod h1:h1NjWce9XRLGQEsW7w golang.org/x/sys v0.0.0-20210112080510-489259a85091/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= golang.org/x/sys v0.0.0-20210423082822-04245dca01da/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= golang.org/x/sys v0.0.0-20210616094352-59db8d763f22/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg= -golang.org/x/sys v0.0.0-20210630005230-0f9fa26af87c/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg= -golang.org/x/sys v0.0.0-20210927094055-39ccf1dd6fa6/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg= golang.org/x/sys v0.0.0-20220412211240-33da011f77ad/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg= -golang.org/x/sys v0.0.0-20220503163025-988cb79eb6c6/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg= -golang.org/x/sys v0.0.0-20220728004956-3c1f35247d10 h1:WIoqL4EROvwiPdUtaip4VcDdpZ4kha7wBWZrbVKCIZg= -golang.org/x/sys v0.0.0-20220728004956-3c1f35247d10/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg= +golang.org/x/sys v0.5.0 h1:MUK/U/4lj1t1oPg0HfuXDN/Z1wv31ZJ/YcPiGccS4DU= +golang.org/x/sys v0.5.0/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg= golang.org/x/term v0.0.0-20201117132131-f5c789dd3221/go.mod h1:Nr5EML6q2oocZ2LXRh80K7BxOlk5/8JxuGnuhpl+muw= golang.org/x/term v0.0.0-20201126162022-7de9c90e9dd1/go.mod h1:bj7SfCRtBDWHUb9snDiAeCFNEtKQo2Wmx5Cou7ajbmo= -golang.org/x/term v0.0.0-20210220032956-6a3ed077a48d h1:SZxvLBoTP5yHO3Frd4z4vrF+DBX9vMVanchswa69toE= golang.org/x/term v0.0.0-20210220032956-6a3ed077a48d/go.mod h1:bj7SfCRtBDWHUb9snDiAeCFNEtKQo2Wmx5Cou7ajbmo= +golang.org/x/term v0.5.0 h1:n2a8QNdAb0sZNpU9R1ALUXBbY+w51fCQDN+7EdxNBsY= +golang.org/x/term v0.5.0/go.mod h1:jMB1sMXY+tzblOD4FWmEbocvup2/aLOaQEp7JmGp78k= golang.org/x/text v0.0.0-20170915032832-14c0d48ead0c/go.mod h1:NqM8EUOU14njkJ3fqMW+pc6Ldnwhi/IjpwHt7yyuwOQ= golang.org/x/text v0.3.0/go.mod h1:NqM8EUOU14njkJ3fqMW+pc6Ldnwhi/IjpwHt7yyuwOQ= golang.org/x/text v0.3.1-0.20180807135948-17ff2d5776d2/go.mod h1:NqM8EUOU14njkJ3fqMW+pc6Ldnwhi/IjpwHt7yyuwOQ= golang.org/x/text v0.3.2/go.mod h1:bEr9sfX3Q8Zfm5fL9x+3itogRgK3+ptLWKqgva+5dAk= golang.org/x/text v0.3.3/go.mod h1:5Zoc/QRtKVWzQhOtBMvqHzDpF6irO9z98xDceosuGiQ= golang.org/x/text v0.3.6/go.mod h1:5Zoc/QRtKVWzQhOtBMvqHzDpF6irO9z98xDceosuGiQ= -golang.org/x/text v0.3.7 h1:olpwvP2KacW1ZWvsR7uQhoyTYvKAupfQrRGBFM352Gk= -golang.org/x/text v0.3.7/go.mod h1:u+2+/6zg+i71rQMx5EYifcz6MCKuco9NR6JIITiCfzQ= +golang.org/x/text v0.7.0 h1:4BRB4x83lYWy72KwLD/qYDuTu7q9PjSagHvijDw7cLo= +golang.org/x/text v0.7.0/go.mod h1:mrYo+phRRbMaCq/xk9113O4dZlRixOauAjOtrjsXDZ8= golang.org/x/time v0.0.0-20181108054448-85acf8d2951c/go.mod h1:tRJNPiyCQ0inRvYxbN9jk5I+vvW/OXSQhTDSoE431IQ= golang.org/x/time v0.0.0-20190308202827-9d24e82272b4/go.mod h1:tRJNPiyCQ0inRvYxbN9jk5I+vvW/OXSQhTDSoE431IQ= golang.org/x/time v0.0.0-20191024005414-555d28b269f0/go.mod h1:tRJNPiyCQ0inRvYxbN9jk5I+vvW/OXSQhTDSoE431IQ= @@ -450,9 +447,8 @@ google.golang.org/protobuf v1.23.0/go.mod h1:EGpADcykh3NcUnDUJcl1+ZksZNG86OlYog2 google.golang.org/protobuf v1.23.1-0.20200526195155-81db48ad09cc/go.mod h1:EGpADcykh3NcUnDUJcl1+ZksZNG86OlYog2l/sGQquU= google.golang.org/protobuf v1.24.0/go.mod h1:r/3tXBNzIEhYS9I1OUVjXDlt8tc493IdKGjtUeSXeh4= google.golang.org/protobuf v1.26.0-rc.1/go.mod h1:jlhhOSvTdKEhbULTjvd4ARK9grFBp09yW+WbY/TyQbw= +google.golang.org/protobuf v1.26.0 h1:bxAC2xTBsZGibn2RTntX0oH50xLsqy1OxA9tTL3p/lk= google.golang.org/protobuf v1.26.0/go.mod h1:9q0QmTI4eRPtz6boOQmLYwt+qCgq0jsYwAQnmE0givc= -google.golang.org/protobuf v1.27.1 h1:SnqbnDw1V7RiZcXPx5MEeqPv2s79L9i7BJUlG/+RurQ= -google.golang.org/protobuf v1.27.1/go.mod h1:9q0QmTI4eRPtz6boOQmLYwt+qCgq0jsYwAQnmE0givc= gopkg.in/check.v1 v0.0.0-20161208181325-20d25e280405/go.mod h1:Co6ibVJAznAaIkqp8huTwlJQCZ016jof/cbN4VW5Yz0= gopkg.in/check.v1 v1.0.0-20180628173108-788fd7840127/go.mod h1:Co6ibVJAznAaIkqp8huTwlJQCZ016jof/cbN4VW5Yz0= gopkg.in/check.v1 v1.0.0-20190902080502-41f04d3bba15/go.mod h1:Co6ibVJAznAaIkqp8huTwlJQCZ016jof/cbN4VW5Yz0= @@ -473,9 +469,8 @@ gopkg.in/yaml.v2 v2.4.0 h1:D8xgwECY7CYvx+Y2n4sBz93Jn9JRvxdiyyo8CTfuKaY= gopkg.in/yaml.v2 v2.4.0/go.mod h1:RDklbk79AGWmwhnvt/jBztapEOGDOx6ZbXqjP6csGnQ= gopkg.in/yaml.v3 v3.0.0-20200313102051-9f266ea9e77c/go.mod h1:K4uyk7z7BCEPqu6E+C64Yfv1cQ7kz7rIZviUmN+EgEM= gopkg.in/yaml.v3 v3.0.0-20200615113413-eeeca48fe776/go.mod h1:K4uyk7z7BCEPqu6E+C64Yfv1cQ7kz7rIZviUmN+EgEM= +gopkg.in/yaml.v3 v3.0.0-20210107192922-496545a6307b h1:h8qDotaEPuJATrMmW04NCwg7v22aHH28wwpauUhK9Oo= gopkg.in/yaml.v3 v3.0.0-20210107192922-496545a6307b/go.mod h1:K4uyk7z7BCEPqu6E+C64Yfv1cQ7kz7rIZviUmN+EgEM= -gopkg.in/yaml.v3 v3.0.1 h1:fxVm/GzAzEWqLHuvctI91KS9hhNmmWOoWu0XTYJS7CA= -gopkg.in/yaml.v3 v3.0.1/go.mod h1:K4uyk7z7BCEPqu6E+C64Yfv1cQ7kz7rIZviUmN+EgEM= honnef.co/go/tools v0.0.0-20190102054323-c2f93a96b099/go.mod h1:rf3lG4BRIbNafJWhAfAdb/ePZxsR/4RtNHQocxwk9r4= honnef.co/go/tools v0.0.0-20190106161140-3f1c8253044a/go.mod h1:rf3lG4BRIbNafJWhAfAdb/ePZxsR/4RtNHQocxwk9r4= honnef.co/go/tools v0.0.0-20190418001031-e561f6794a2a/go.mod h1:rf3lG4BRIbNafJWhAfAdb/ePZxsR/4RtNHQocxwk9r4= diff --git a/control-plane/config/crd/bases/consul.hashicorp.com_proxydefaults.yaml b/control-plane/config/crd/bases/consul.hashicorp.com_proxydefaults.yaml index 2563cbcf77..6b9628cd74 100644 --- a/control-plane/config/crd/bases/consul.hashicorp.com_proxydefaults.yaml +++ b/control-plane/config/crd/bases/consul.hashicorp.com_proxydefaults.yaml @@ -50,60 +50,12 @@ spec: spec: description: ProxyDefaultsSpec defines the desired state of ProxyDefaults. properties: - accessLogs: - description: AccessLogs controls all envoy instances' access logging - configuration. - properties: - disableListenerLogs: - description: DisableListenerLogs turns off just listener logs - for connections rejected by Envoy because they don't have a - matching listener filter. - type: boolean - enabled: - description: Enabled turns on all access logging - type: boolean - jsonFormat: - description: 'JSONFormat is a JSON-formatted string of an Envoy - access log format dictionary. See for more info on formatting: - https://www.envoyproxy.io/docs/envoy/latest/configuration/observability/access_log/usage#format-dictionaries - Defining JSONFormat and TextFormat is invalid.' - type: string - path: - description: Path is the output file to write logs for file-type - logging - type: string - textFormat: - description: 'TextFormat is a representation of Envoy access logs - format. See for more info on formatting: https://www.envoyproxy.io/docs/envoy/latest/configuration/observability/access_log/usage#format-strings - Defining JSONFormat and TextFormat is invalid.' - type: string - type: - description: Type selects the output for logs one of "file", "stderr". - "stdout" - type: string - type: object config: description: Config is an arbitrary map of configuration values used by Connect proxies. Any values that your proxy allows can be configured globally here. Supports JSON config values. See https://www.consul.io/docs/connect/proxies/envoy#configuration-formatting type: object x-kubernetes-preserve-unknown-fields: true - envoyExtensions: - description: EnvoyExtensions are a list of extensions to modify Envoy - proxy configuration. - items: - description: EnvoyExtension has configuration for an extension that - patches Envoy resources. - properties: - arguments: - type: object - x-kubernetes-preserve-unknown-fields: true - name: - type: string - required: - type: boolean - type: object - type: array expose: description: Expose controls the default expose path configuration for Envoy. diff --git a/control-plane/config/crd/bases/consul.hashicorp.com_servicedefaults.yaml b/control-plane/config/crd/bases/consul.hashicorp.com_servicedefaults.yaml index 4f335a923d..769316397b 100644 --- a/control-plane/config/crd/bases/consul.hashicorp.com_servicedefaults.yaml +++ b/control-plane/config/crd/bases/consul.hashicorp.com_servicedefaults.yaml @@ -50,12 +50,6 @@ spec: spec: description: ServiceDefaultsSpec defines the desired state of ServiceDefaults. properties: - balanceInboundConnections: - description: BalanceInboundConnections sets the strategy for allocating - inbound connections to the service across proxy threads. The only - supported value is exact_balance. By default, no connection balancing - is used. Refer to the Envoy Connection Balance config for details. - type: string destination: description: Destination is an address(es)/port combination that represents an endpoint outside the mesh. This is only valid when the mesh is @@ -75,22 +69,6 @@ spec: format: int32 type: integer type: object - envoyExtensions: - description: EnvoyExtensions are a list of extensions to modify Envoy - proxy configuration. - items: - description: EnvoyExtension has configuration for an extension that - patches Envoy resources. - properties: - arguments: - type: object - x-kubernetes-preserve-unknown-fields: true - name: - type: string - required: - type: boolean - type: object - type: array expose: description: Expose controls the default expose path configuration for Envoy. @@ -129,15 +107,15 @@ spec: with an external system. type: string localConnectTimeoutMs: - description: LocalConnectTimeoutMs is the number of milliseconds allowed - to make connections to the local application instance before timing - out. Defaults to 5000. + description: The number of milliseconds allowed to make connections + to the local application instance before timing out. Defaults to + 5000. type: integer localRequestTimeoutMs: - description: LocalRequestTimeoutMs is the timeout for HTTP requests - to the local application instance in milliseconds. Applies to HTTP-based - protocols only. If not specified, inherits the Envoy default for - route timeouts (15s). + description: In milliseconds, the timeout for HTTP requests to the + local application instance. Applies to HTTP-based protocols only. + If not specified, inherits the Envoy default for route timeouts + (15s). type: integer maxInboundConnections: description: MaxInboundConnections is the maximum number of concurrent @@ -251,15 +229,15 @@ spec: type: string type: object name: - description: Name is only accepted within service ServiceDefaultsSpec.UpstreamConfig.Overrides + description: Name is only accepted within a service-defaults config entry. type: string namespace: - description: Namespace is only accepted within service ServiceDefaultsSpec.UpstreamConfig.Overrides + description: Namespace is only accepted within a service-defaults config entry. type: string partition: - description: Partition is only accepted within service ServiceDefaultsSpec.UpstreamConfig.Overrides + description: Partition is only accepted within a service-defaults config entry. type: string passiveHealthCheck: @@ -267,6 +245,12 @@ spec: upstream proxy instances will be monitored for removal from the load balancing pool. properties: + baseEjectionTime: + description: The base time that a host is ejected for. The + real time is equal to the base time multiplied by the number + of times the host has been ejected and is capped by + max_ejection_time (Default 300s). Defaults to 30s. + type: string enforcing_consecutive_5xx: description: EnforcingConsecutive5xx is the % chance that a host will be actually ejected when an outlier status @@ -278,16 +262,18 @@ spec: description: Interval between health check analysis sweeps. Each sweep may remove hosts or return hosts to the pool. type: string + maxEjectionPercent: + description: The maximum % of an upstream cluster that + can be ejected due to outlier detection. Defaults to + 10% but will eject at least one host regardless of the value. + format: int32 + type: integer maxFailures: description: MaxFailures is the count of consecutive failures that results in a host being removed from the pool. format: int32 type: integer type: object - peer: - description: Peer is only accepted within service ServiceDefaultsSpec.UpstreamConfig.Overrides - config entry. - type: string protocol: description: Protocol describes the upstream's service protocol. Valid values are "tcp", "http" and "grpc". Anything else @@ -354,15 +340,15 @@ spec: type: string type: object name: - description: Name is only accepted within service ServiceDefaultsSpec.UpstreamConfig.Overrides + description: Name is only accepted within a service-defaults config entry. type: string namespace: - description: Namespace is only accepted within service ServiceDefaultsSpec.UpstreamConfig.Overrides + description: Namespace is only accepted within a service-defaults config entry. type: string partition: - description: Partition is only accepted within service ServiceDefaultsSpec.UpstreamConfig.Overrides + description: Partition is only accepted within a service-defaults config entry. type: string passiveHealthCheck: @@ -370,6 +356,12 @@ spec: how upstream proxy instances will be monitored for removal from the load balancing pool. properties: + baseEjectionTime: + description: The base time that a host is ejected for. The + real time is equal to the base time multiplied by the number + of times the host has been ejected and is capped by + max_ejection_time (Default 300s). Defaults to 30s. + type: string enforcing_consecutive_5xx: description: EnforcingConsecutive5xx is the % chance that a host will be actually ejected when an outlier @@ -382,6 +374,12 @@ spec: sweeps. Each sweep may remove hosts or return hosts to the pool. type: string + maxEjectionPercent: + description: The maximum % of an upstream cluster that + can be ejected due to outlier detection. Defaults to + 10% but will eject at least one host regardless of the value. + format: int32 + type: integer maxFailures: description: MaxFailures is the count of consecutive failures that results in a host being removed from @@ -389,10 +387,6 @@ spec: format: int32 type: integer type: object - peer: - description: Peer is only accepted within service ServiceDefaultsSpec.UpstreamConfig.Overrides - config entry. - type: string protocol: description: Protocol describes the upstream's service protocol. Valid values are "tcp", "http" and "grpc". Anything else diff --git a/control-plane/go.mod b/control-plane/go.mod index b0d67085ec..04a13c1ebb 100644 --- a/control-plane/go.mod +++ b/control-plane/go.mod @@ -6,11 +6,11 @@ require ( github.com/deckarep/golang-set v1.7.1 github.com/fsnotify/fsnotify v1.5.4 github.com/go-logr/logr v0.4.0 - github.com/google/go-cmp v0.5.7 + github.com/google/go-cmp v0.5.8 github.com/google/shlex v0.0.0-20191202100458-e7afc7fbc510 github.com/hashicorp/consul-k8s/control-plane/cni v0.0.0-20220831174802-b8af65262de8 github.com/hashicorp/consul-server-connection-manager v0.1.0 - github.com/hashicorp/consul/api v1.20.0 + github.com/hashicorp/consul/api v1.10.1-0.20230426225948-5eaeb7b8e563 github.com/hashicorp/consul/sdk v0.13.1 github.com/hashicorp/go-discover v0.0.0-20200812215701-c4b85f6ed31f github.com/hashicorp/go-hclog v1.2.2 @@ -19,15 +19,14 @@ require ( github.com/hashicorp/go-rootcerts v1.0.2 github.com/hashicorp/go-version v1.6.0 github.com/hashicorp/serf v0.10.1 - github.com/hashicorp/vault/api v1.8.3 github.com/kr/text v0.2.0 github.com/miekg/dns v1.1.41 github.com/mitchellh/cli v1.1.0 github.com/mitchellh/go-homedir v1.1.0 - github.com/mitchellh/mapstructure v1.5.0 + github.com/mitchellh/mapstructure v1.4.1 github.com/stretchr/testify v1.7.2 go.uber.org/zap v1.19.0 - golang.org/x/text v0.3.8 + golang.org/x/text v0.7.0 golang.org/x/time v0.0.0-20220210224613-90d013bbcef8 gomodules.xyz/jsonpatch/v2 v2.2.0 k8s.io/api v0.22.2 @@ -56,7 +55,6 @@ require ( github.com/aws/aws-sdk-go v1.25.41 // indirect github.com/beorn7/perks v1.0.1 // indirect github.com/bgentry/speakeasy v0.1.0 // indirect - github.com/cenkalti/backoff/v3 v3.0.0 // indirect github.com/cenkalti/backoff/v4 v4.1.3 // indirect github.com/cespare/xxhash/v2 v2.1.1 // indirect github.com/davecgh/go-spew v1.1.1 // indirect @@ -70,7 +68,6 @@ require ( github.com/gogo/protobuf v1.3.2 // indirect github.com/golang/groupcache v0.0.0-20210331224755-41bb18bfe9da // indirect github.com/golang/protobuf v1.5.2 // indirect - github.com/golang/snappy v0.0.4 // indirect github.com/google/go-querystring v1.0.0 // indirect github.com/google/gofuzz v1.1.0 // indirect github.com/google/uuid v1.1.2 // indirect @@ -78,22 +75,13 @@ require ( github.com/googleapis/gnostic v0.5.5 // indirect github.com/gophercloud/gophercloud v0.1.0 // indirect github.com/hashicorp/consul/proto-public v0.1.0 // indirect - github.com/hashicorp/errwrap v1.1.0 // indirect + github.com/hashicorp/errwrap v1.0.0 // indirect github.com/hashicorp/go-cleanhttp v0.5.2 // indirect - github.com/hashicorp/go-immutable-radix v1.3.1 // indirect - github.com/hashicorp/go-plugin v1.4.5 // indirect - github.com/hashicorp/go-retryablehttp v0.6.6 // indirect - github.com/hashicorp/go-secure-stdlib/mlock v0.1.1 // indirect - github.com/hashicorp/go-secure-stdlib/parseutil v0.1.6 // indirect - github.com/hashicorp/go-secure-stdlib/strutil v0.1.2 // indirect - github.com/hashicorp/go-sockaddr v1.0.2 // indirect + github.com/hashicorp/go-immutable-radix v1.3.0 // indirect github.com/hashicorp/go-uuid v1.0.2 // indirect github.com/hashicorp/golang-lru v0.5.4 // indirect - github.com/hashicorp/hcl v1.0.0 // indirect github.com/hashicorp/mdns v1.0.4 // indirect - github.com/hashicorp/vault/sdk v0.7.0 // indirect github.com/hashicorp/vic v1.5.1-0.20190403131502-bbfe86ec9443 // indirect - github.com/hashicorp/yamux v0.0.0-20180604194846-3520598351bb // indirect github.com/imdario/mergo v0.3.12 // indirect github.com/jmespath/go-jmespath v0.0.0-20180206201540-c2b33e8439af // indirect github.com/joyent/triton-go v1.7.1-0.20200416154420-6801d15b779f // indirect @@ -102,15 +90,10 @@ require ( github.com/mattn/go-colorable v0.1.12 // indirect github.com/mattn/go-isatty v0.0.14 // indirect github.com/matttproud/golang_protobuf_extensions v1.0.2-0.20181231171920-c182affec369 // indirect - github.com/mitchellh/copystructure v1.0.0 // indirect - github.com/mitchellh/go-testing-interface v1.0.0 // indirect - github.com/mitchellh/reflectwalk v1.0.0 // indirect github.com/modern-go/concurrent v0.0.0-20180306012644-bacd9c7ef1dd // indirect github.com/modern-go/reflect2 v1.0.2 // indirect github.com/nicolai86/scaleway-sdk v1.10.2-0.20180628010248-798f60e20bb2 // indirect - github.com/oklog/run v1.0.0 // indirect github.com/packethost/packngo v0.1.1-0.20180711074735-b9cb5096f54c // indirect - github.com/pierrec/lz4 v2.5.2+incompatible // indirect github.com/pkg/errors v0.9.1 // indirect github.com/pmezard/go-difflib v1.0.0 // indirect github.com/posener/complete v1.2.3 // indirect @@ -119,7 +102,6 @@ require ( github.com/prometheus/common v0.26.0 // indirect github.com/prometheus/procfs v0.6.0 // indirect github.com/renier/xmlrpc v0.0.0-20170708154548-ce4a1a486c03 // indirect - github.com/ryanuber/go-glob v1.0.0 // indirect github.com/sirupsen/logrus v1.8.1 // indirect github.com/softlayer/softlayer-go v0.0.0-20180806151055-260589d94c7d // indirect github.com/spf13/pflag v1.0.5 // indirect @@ -127,15 +109,15 @@ require ( github.com/tencentcloud/tencentcloud-sdk-go v3.0.83+incompatible // indirect github.com/vmware/govmomi v0.18.0 // indirect go.opencensus.io v0.23.0 // indirect - go.uber.org/atomic v1.9.0 // indirect + go.uber.org/atomic v1.7.0 // indirect go.uber.org/multierr v1.6.0 // indirect golang.org/x/crypto v0.0.0-20220411220226-7b82a4e95df4 // indirect - golang.org/x/net v0.0.0-20220127200216-cd36cc0744dd // indirect + golang.org/x/exp v0.0.0-20230321023759-10a507213a29 // indirect + golang.org/x/net v0.7.0 // indirect golang.org/x/oauth2 v0.0.0-20211104180415-d3ed0bb246c8 // indirect golang.org/x/sync v0.0.0-20210220032951-036812b2e83c // indirect - golang.org/x/sys v0.0.0-20220728004956-3c1f35247d10 // indirect - golang.org/x/term v0.0.0-20220526004731-065cf7ba2467 // indirect - golang.org/x/xerrors v0.0.0-20200804184101-5ec99f83aff1 // indirect + golang.org/x/sys v0.5.0 // indirect + golang.org/x/term v0.5.0 // indirect google.golang.org/api v0.43.0 // indirect google.golang.org/appengine v1.6.7 // indirect google.golang.org/genproto v0.0.0-20210602131652-f16073e35f0c // indirect @@ -143,7 +125,6 @@ require ( google.golang.org/protobuf v1.28.1 // indirect gopkg.in/inf.v0 v0.9.1 // indirect gopkg.in/resty.v1 v1.12.0 // indirect - gopkg.in/square/go-jose.v2 v2.5.1 // indirect gopkg.in/yaml.v2 v2.4.0 // indirect gopkg.in/yaml.v3 v3.0.1 // indirect k8s.io/apiextensions-apiserver v0.22.2 // indirect @@ -153,4 +134,6 @@ require ( sigs.k8s.io/yaml v1.2.0 // indirect ) -go 1.20 +replace github.com/hashicorp/consul/sdk => github.com/hashicorp/consul/sdk v0.4.1-0.20221021205723-cc843c4be892 + +go 1.19 diff --git a/control-plane/go.sum b/control-plane/go.sum index 06dfbb8b10..c6c3dcf6b6 100644 --- a/control-plane/go.sum +++ b/control-plane/go.sum @@ -117,8 +117,6 @@ github.com/bketelsen/crypt v0.0.3-0.20200106085610-5cbc8cc4026c/go.mod h1:MKsuJm github.com/blang/semver v3.5.1+incompatible/go.mod h1:kRBLl5iJ+tD4TcOOxsy/0fnwebNt5EWlYSAyrTnjyyk= github.com/cenkalti/backoff v2.2.1+incompatible h1:tNowT99t7UNflLxfYYSlKYsBpXdEet03Pg2g16Swow4= github.com/cenkalti/backoff v2.2.1+incompatible/go.mod h1:90ReRw6GdpyfrHakVjL/QHaoyV4aDUVVkXQJJJ3NXXM= -github.com/cenkalti/backoff/v3 v3.0.0 h1:ske+9nBpD9qZsTBoF41nW5L+AIuFBKMeze18XQ3eG1c= -github.com/cenkalti/backoff/v3 v3.0.0/go.mod h1:cIeZDE3IrqwwJl6VUwCN6trj1oXrTS4rc0ij+ULvLYs= github.com/cenkalti/backoff/v4 v4.1.3 h1:cFAlzYUlVYDysBEH2T5hyJZMh3+5+WCBvSnK6Q8UtC4= github.com/cenkalti/backoff/v4 v4.1.3/go.mod h1:scbssz8iZGpm3xbr14ovlUdkxfGXNInqkPWOWmG2CLw= github.com/census-instrumentation/opencensus-proto v0.2.1/go.mod h1:f6KPmirojxKA12rnyqOA5BBL4O983OfeGPqjHWSTneU= @@ -199,12 +197,10 @@ github.com/fatih/color v1.7.0/go.mod h1:Zm6kSWBoL9eyXnKyktHP6abPY2pDugNf5Kwzbycv github.com/fatih/color v1.9.0/go.mod h1:eQcE1qtQxscV5RaZvpXrrb8Drkc3/DdQ+uUYCNjL+zU= github.com/fatih/color v1.13.0 h1:8LOYc1KYPPmyKMuN8QV2DNRWNbLo6LZ0iLs8+mlH53w= github.com/fatih/color v1.13.0/go.mod h1:kLAiJbzzSOZDVNGyDpeOxJ47H46qBXwg5ILebYFFOfk= -github.com/fatih/structs v1.1.0 h1:Q7juDM0QtcnhCpeyLGQKyg4TOIghuNXrkL32pHAUMxo= github.com/felixge/httpsnoop v1.0.1/go.mod h1:m8KPJKqk1gH5J9DgRY2ASl2lWCfGKXixSwevea8zH2U= github.com/form3tech-oss/jwt-go v3.2.2+incompatible/go.mod h1:pbq4aXjuKjdthFRnoDwaVPLA+WlJuPGy+QneDUgJi2k= github.com/form3tech-oss/jwt-go v3.2.3+incompatible h1:7ZaBxOI7TMoYBfyA3cQHErNNyAWIKUMIwqxEtgHOs5c= github.com/form3tech-oss/jwt-go v3.2.3+incompatible/go.mod h1:pbq4aXjuKjdthFRnoDwaVPLA+WlJuPGy+QneDUgJi2k= -github.com/frankban/quicktest v1.13.0 h1:yNZif1OkDfNoDfb9zZa9aXIpejNR4F23Wely0c+Qdqk= github.com/fsnotify/fsnotify v1.4.7/go.mod h1:jwhsz4b93w/PPRr/qN1Yymfu8t87LnFCMoQvtojpjFo= github.com/fsnotify/fsnotify v1.4.9/go.mod h1:znqG4EE+3YCdAaPaxE2ZRY/06pZUdp0tY4IgpuI1SZQ= github.com/fsnotify/fsnotify v1.5.4 h1:jRbGcIw6P2Meqdwuo0H1p6JVLbL5DHKAKlYndzMwVZI= @@ -239,7 +235,6 @@ github.com/go-openapi/swag v0.19.5/go.mod h1:POnQmlKehdgb5mhVOsnJFsivZCEZ/vjK9gh github.com/go-openapi/swag v0.19.14/go.mod h1:QYRuS/SOXUCsnplDa677K7+DxSOj6IPNl/eQntq43wQ= 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-test/deep v1.0.2 h1:onZX1rnHT3Wv6cqNgYyFOOlgVKJrksuCMCRvJStbMYw= github.com/godbus/dbus/v5 v5.0.4/go.mod h1:xhWf0FNVPg57R7Z0UbKHbJfkEywrmjJnf7w5xrFpKfA= github.com/gogo/protobuf v1.1.1/go.mod h1:r8qH/GZQm5c6nD/R0oafs1akxWv10x8SbQlK7atdtwQ= github.com/gogo/protobuf v1.2.1/go.mod h1:hp+jE20tsWTFYpLwKvXlhS1hjn+gTNwPg2I6zVXpSg4= @@ -281,8 +276,6 @@ github.com/golang/protobuf v1.5.0/go.mod h1:FsONVRAS9T7sI+LIUmWTfcYkHO4aIWwzhcaS github.com/golang/protobuf v1.5.1/go.mod h1:DopwsBzvsk0Fs44TXzsVbJyPhcCPeIwnvohx4u74HPM= github.com/golang/protobuf v1.5.2 h1:ROPKBNFfQgOUMifHyP+KYbvpjbdoFNs+aK7DXlji0Tw= github.com/golang/protobuf v1.5.2/go.mod h1:XVQd3VNwM+JqD3oG2Ue2ip4fOMUkwXdXDdiuN0vRsmY= -github.com/golang/snappy v0.0.4 h1:yAGX7huGHXlcLOEtBnF4w7FQwA26wojNCwOYAEhLjQM= -github.com/golang/snappy v0.0.4/go.mod h1:/XxbfmMg8lxefKM7IXC3fBNl/7bRcc72aCRzEWrmP2Q= github.com/google/btree v0.0.0-20180813153112-4030bb1f1f0c/go.mod h1:lNA+9X1NB3Zf8V7Ke586lFgjr2dZNuvo3lPJSGZ5JPQ= github.com/google/btree v1.0.0/go.mod h1:lNA+9X1NB3Zf8V7Ke586lFgjr2dZNuvo3lPJSGZ5JPQ= github.com/google/btree v1.0.1 h1:gK4Kx5IaGY9CD5sPJ36FHiBJ6ZXl0kilRiiCj+jdYp4= @@ -299,8 +292,8 @@ github.com/google/go-cmp v0.5.3/go.mod h1:v8dTdLbMG2kIc/vJvl+f65V22dbkXbowE6jgT/ github.com/google/go-cmp v0.5.4/go.mod h1:v8dTdLbMG2kIc/vJvl+f65V22dbkXbowE6jgT/gNBxE= github.com/google/go-cmp v0.5.5/go.mod h1:v8dTdLbMG2kIc/vJvl+f65V22dbkXbowE6jgT/gNBxE= github.com/google/go-cmp v0.5.6/go.mod h1:v8dTdLbMG2kIc/vJvl+f65V22dbkXbowE6jgT/gNBxE= -github.com/google/go-cmp v0.5.7 h1:81/ik6ipDQS2aGcBfIN5dHDB36BwrStyeAQquSYCV4o= -github.com/google/go-cmp v0.5.7/go.mod h1:n+brtR0CgQNWTVd5ZUFpTBC8YFBDLK/h/bpaJ8/DtOE= +github.com/google/go-cmp v0.5.8 h1:e6P7q2lk1O+qJJb4BtCQXlK8vWEO8V1ZeuEdJNOqZyg= +github.com/google/go-cmp v0.5.8/go.mod h1:17dUlkBOakJ0+DkrSSNjCkIjxS6bF9zb3elmeNGIjoY= github.com/google/go-querystring v0.0.0-20170111101155-53e6ce116135/go.mod h1:odCYkC5MyYFN7vkCjXpyrEuKhc/BUO6wN/zVPAxq5ck= github.com/google/go-querystring v1.0.0 h1:Xkwi/a1rcvNg1PPYe5vI8GbeBY/jrVuDX5ASuANWTrk= github.com/google/go-querystring v1.0.0/go.mod h1:odCYkC5MyYFN7vkCjXpyrEuKhc/BUO6wN/zVPAxq5ck= @@ -353,28 +346,26 @@ github.com/hashicorp/consul-k8s/control-plane/cni v0.0.0-20220831174802-b8af6526 github.com/hashicorp/consul-server-connection-manager v0.1.0 h1:XCweGvMHzra88rYv2zxwwuUOjBUdcQmNKVrnQmt/muo= github.com/hashicorp/consul-server-connection-manager v0.1.0/go.mod h1:XVVlO+Yk7aiRpspiHZkrrFVn9BJIiOPnQIzqytPxGaU= github.com/hashicorp/consul/api v1.1.0/go.mod h1:VmuI/Lkw1nC05EYQWNKwWGbkg+FbDBtguAZLlVdkD9Q= -github.com/hashicorp/consul/api v1.20.0 h1:9IHTjNVSZ7MIwjlW3N3a7iGiykCMDpxZu8jsxFJh0yc= -github.com/hashicorp/consul/api v1.20.0/go.mod h1:nR64eD44KQ59Of/ECwt2vUmIK2DKsDzAwTmwmLl8Wpo= +github.com/hashicorp/consul/api v1.10.1-0.20230426225948-5eaeb7b8e563 h1:C34qTESgxbiqkhK9ydoRmC+5CcaP6eW5wS9at+Jw5X0= +github.com/hashicorp/consul/api v1.10.1-0.20230426225948-5eaeb7b8e563/go.mod h1:tXfrC6o0yFTgAW46xd5Ic8STHc9oIBcRVBcwhX5KNCQ= github.com/hashicorp/consul/proto-public v0.1.0 h1:O0LSmCqydZi363hsqc6n2v5sMz3usQMXZF6ziK3SzXU= github.com/hashicorp/consul/proto-public v0.1.0/go.mod h1:vs2KkuWwtjkIgA5ezp4YKPzQp4GitV+q/+PvksrA92k= -github.com/hashicorp/consul/sdk v0.1.1/go.mod h1:VKf9jXwCTEY1QZP2MOLRhb5i/I/ssyNV1vwHyQBF0x8= -github.com/hashicorp/consul/sdk v0.13.1 h1:EygWVWWMczTzXGpO93awkHFzfUka6hLYJ0qhETd+6lY= -github.com/hashicorp/consul/sdk v0.13.1/go.mod h1:SW/mM4LbKfqmMvcFu8v+eiQQ7oitXEFeiBe9StxERb0= +github.com/hashicorp/consul/sdk v0.4.1-0.20221021205723-cc843c4be892 h1:jw0NwPmNPr5CxAU04hACdj61JSaJBKZ0FdBo+kwfNp4= +github.com/hashicorp/consul/sdk v0.4.1-0.20221021205723-cc843c4be892/go.mod h1:yPkX5Q6CsxTFMjQQDJwzeNmUUF5NUGGbrDsv9wTb8cw= +github.com/hashicorp/errwrap v1.0.0 h1:hLrqtEDnRye3+sgx6z4qVLNuviH3MR5aQ0ykNJa/UYA= github.com/hashicorp/errwrap v1.0.0/go.mod h1:YH+1FKiLXxHSkmPseP+kNlulaMuP3n2brvKWEqk/Jc4= -github.com/hashicorp/errwrap v1.1.0 h1:OxrOeh75EUXMY8TBjag2fzXGZ40LB6IKw45YeGUDY2I= -github.com/hashicorp/errwrap v1.1.0/go.mod h1:YH+1FKiLXxHSkmPseP+kNlulaMuP3n2brvKWEqk/Jc4= github.com/hashicorp/go-cleanhttp v0.5.0/go.mod h1:JpRdi6/HCYpAwUzNwuwqhbovhLtngrth3wmdIIUrZ80= github.com/hashicorp/go-cleanhttp v0.5.1/go.mod h1:JpRdi6/HCYpAwUzNwuwqhbovhLtngrth3wmdIIUrZ80= github.com/hashicorp/go-cleanhttp v0.5.2 h1:035FKYIWjmULyFRBKPs8TBQoi0x6d9G4xc9neXJWAZQ= github.com/hashicorp/go-cleanhttp v0.5.2/go.mod h1:kO/YDlP8L1346E6Sodw+PrpBSV4/SoxCXGY6BqNFT48= github.com/hashicorp/go-discover v0.0.0-20200812215701-c4b85f6ed31f h1:7WFMVeuJQp6BkzuTv9O52pzwtEFVUJubKYN+zez8eTI= github.com/hashicorp/go-discover v0.0.0-20200812215701-c4b85f6ed31f/go.mod h1:D4eo8/CN92vm9/9UDG+ldX1/fMFa4kpl8qzyTolus8o= -github.com/hashicorp/go-hclog v0.9.2/go.mod h1:5CU+agLiy3J7N7QjHK5d05KxGsuXiQLrjA0H7acj2lQ= +github.com/hashicorp/go-hclog v0.12.0/go.mod h1:whpDNt7SSdeAju8AWKIWsul05p54N/39EeqMAyrmvFQ= github.com/hashicorp/go-hclog v1.2.2 h1:ihRI7YFwcZdiSD7SIenIhHfQH3OuDvWerAUBZbeQS3M= github.com/hashicorp/go-hclog v1.2.2/go.mod h1:W4Qnvbt70Wk/zYJryRzDRU/4r0kIg0PVHBcfoyhpF5M= github.com/hashicorp/go-immutable-radix v1.0.0/go.mod h1:0y9vanUI8NX6FsYoO3zeMjhV/C5i9g4Q3DwcSNZ4P60= -github.com/hashicorp/go-immutable-radix v1.3.1 h1:DKHmCUm2hRBK510BaiZlwvpD40f8bJFeZnpfm2KLowc= -github.com/hashicorp/go-immutable-radix v1.3.1/go.mod h1:0y9vanUI8NX6FsYoO3zeMjhV/C5i9g4Q3DwcSNZ4P60= +github.com/hashicorp/go-immutable-radix v1.3.0 h1:8exGP7ego3OmkfksihtSouGMZ+hQrhxx+FVELeXpVPE= +github.com/hashicorp/go-immutable-radix v1.3.0/go.mod h1:0y9vanUI8NX6FsYoO3zeMjhV/C5i9g4Q3DwcSNZ4P60= github.com/hashicorp/go-msgpack v0.5.3 h1:zKjpN5BK/P5lMYrLmBHdBULWbJ0XpYR+7NGzqkZzoD4= github.com/hashicorp/go-msgpack v0.5.3/go.mod h1:ahLV/dePpqEmjfWmKiqvPkv/twdG7iPBM1vqhUKIvfM= github.com/hashicorp/go-multierror v1.0.0/go.mod h1:dHtQlpGsu+cZNNAkkCN/P3hoUDHhCYQXV3UM06sGGrk= @@ -383,24 +374,12 @@ github.com/hashicorp/go-multierror v1.1.1 h1:H5DkEtf6CXdFp0N0Em5UCwQpXMWke8IA0+l github.com/hashicorp/go-multierror v1.1.1/go.mod h1:iw975J/qwKPdAO1clOe2L8331t/9/fmwbPZ6JB6eMoM= github.com/hashicorp/go-netaddrs v0.1.0 h1:TnlYvODD4C/wO+j7cX1z69kV5gOzI87u3OcUinANaW8= github.com/hashicorp/go-netaddrs v0.1.0/go.mod h1:33+a/emi5R5dqRspOuZKO0E+Tuz5WV1F84eRWALkedA= -github.com/hashicorp/go-plugin v1.4.5 h1:oTE/oQR4eghggRg8VY7PAz3dr++VwDNBGCcOfIvHpBo= -github.com/hashicorp/go-plugin v1.4.5/go.mod h1:viDMjcLJuDui6pXb8U4HVfb8AamCWhHGUjr2IrTF67s= github.com/hashicorp/go-retryablehttp v0.5.3/go.mod h1:9B5zBasrRhHXnJnui7y6sL7es7NDiJgTc6Er0maI1Xs= -github.com/hashicorp/go-retryablehttp v0.6.6 h1:HJunrbHTDDbBb/ay4kxa1n+dLmttUlnP3V9oNE4hmsM= -github.com/hashicorp/go-retryablehttp v0.6.6/go.mod h1:vAew36LZh98gCBJNLH42IQ1ER/9wtLZZ8meHqQvEYWY= github.com/hashicorp/go-rootcerts v1.0.0/go.mod h1:K6zTfqpRlCUIjkwsN4Z+hiSfzSTQa6eBIzfwKfwNnHU= github.com/hashicorp/go-rootcerts v1.0.2 h1:jzhAVGtqPKbwpyCPELlgNWhE1znq+qwJtW5Oi2viEzc= github.com/hashicorp/go-rootcerts v1.0.2/go.mod h1:pqUvnprVnM5bf7AOirdbb01K4ccR319Vf4pU3K5EGc8= -github.com/hashicorp/go-secure-stdlib/mlock v0.1.1 h1:cCRo8gK7oq6A2L6LICkUZ+/a5rLiRXFMf1Qd4xSwxTc= -github.com/hashicorp/go-secure-stdlib/mlock v0.1.1/go.mod h1:zq93CJChV6L9QTfGKtfBxKqD7BqqXx5O04A/ns2p5+I= -github.com/hashicorp/go-secure-stdlib/parseutil v0.1.6 h1:om4Al8Oy7kCm/B86rLCLah4Dt5Aa0Fr5rYBG60OzwHQ= -github.com/hashicorp/go-secure-stdlib/parseutil v0.1.6/go.mod h1:QmrqtbKuxxSWTN3ETMPuB+VtEiBJ/A9XhoYGv8E1uD8= -github.com/hashicorp/go-secure-stdlib/strutil v0.1.1/go.mod h1:gKOamz3EwoIoJq7mlMIRBpVTAUn8qPCrEclOKKWhD3U= -github.com/hashicorp/go-secure-stdlib/strutil v0.1.2 h1:kes8mmyCpxJsI7FTwtzRqEy9CdjCtrXrXGuOpxEA7Ts= -github.com/hashicorp/go-secure-stdlib/strutil v0.1.2/go.mod h1:Gou2R9+il93BqX25LAKCLuM+y9U2T4hlwvT1yprcna4= github.com/hashicorp/go-sockaddr v1.0.0/go.mod h1:7Xibr9yA9JjQq1JpNB2Vw7kxv8xerXegt+ozgdvDeDU= github.com/hashicorp/go-sockaddr v1.0.2 h1:ztczhD1jLxIRjVejw8gFomI1BQZOe2WoVOu0SyteCQc= -github.com/hashicorp/go-sockaddr v1.0.2/go.mod h1:rB4wwRAUzs07qva3c5SdrY/NEtAUjGlgmH/UkBUC97A= github.com/hashicorp/go-syslog v1.0.0/go.mod h1:qPfqrKkXGihmCqbJM2mZgkZGvKG1dFdvsLplgctolz4= github.com/hashicorp/go-uuid v1.0.0/go.mod h1:6SBZvOh/SIDV7/2o3Jml5SYk/TvGqwFJ/bN7x4byOro= github.com/hashicorp/go-uuid v1.0.1/go.mod h1:6SBZvOh/SIDV7/2o3Jml5SYk/TvGqwFJ/bN7x4byOro= @@ -413,7 +392,6 @@ github.com/hashicorp/golang-lru v0.5.0/go.mod h1:/m3WP610KZHVQ1SGc6re/UDhFvYD7pJ github.com/hashicorp/golang-lru v0.5.1/go.mod h1:/m3WP610KZHVQ1SGc6re/UDhFvYD7pJ4Ao+sR/qLZy8= github.com/hashicorp/golang-lru v0.5.4 h1:YDjusn29QI/Das2iO9M0BHnIbxPeyuCHsjMW+lJfyTc= github.com/hashicorp/golang-lru v0.5.4/go.mod h1:iADmTwqILo4mZ8BN3D2Q6+9jd8WM5uGBxy+E8yxSoD4= -github.com/hashicorp/hcl v1.0.0 h1:0Anlzjpi4vEasTeNFn2mLJgTSwt0+6sfsiTG8qcWGx4= github.com/hashicorp/hcl v1.0.0/go.mod h1:E5yfLk+7swimpb2L/Alb/PJmXilQ/rhwaUYs4T20WEQ= github.com/hashicorp/logutils v1.0.0/go.mod h1:QIAnNjmIWmVIIkWDTG1z5v++HQmx9WQRO+LraFDTW64= github.com/hashicorp/mdns v1.0.0/go.mod h1:tL+uN++7HEJ6SQLQ2/p+z2pH24WQKWjBPkE0mNTz8vQ= @@ -426,14 +404,8 @@ github.com/hashicorp/memberlist v0.5.0/go.mod h1:yvyXLpo0QaGE59Y7hDTsTzDD25JYBZ4 github.com/hashicorp/serf v0.8.2/go.mod h1:6hOLApaqBFA1NXqRQAsxw9QxuDEvNxSQRwA/JwenrHc= github.com/hashicorp/serf v0.10.1 h1:Z1H2J60yRKvfDYAOZLd2MU0ND4AH/WDz7xYHDWQsIPY= github.com/hashicorp/serf v0.10.1/go.mod h1:yL2t6BqATOLGc5HF7qbFkTfXoPIY0WZdWHfEvMqbG+4= -github.com/hashicorp/vault/api v1.8.3 h1:cHQOLcMhBR+aVI0HzhPxO62w2+gJhIrKguQNONPzu6o= -github.com/hashicorp/vault/api v1.8.3/go.mod h1:4g/9lj9lmuJQMtT6CmVMHC5FW1yENaVv+Nv4ZfG8fAg= -github.com/hashicorp/vault/sdk v0.7.0 h1:2pQRO40R1etpKkia5fb4kjrdYMx3BHklPxl1pxpxDHg= -github.com/hashicorp/vault/sdk v0.7.0/go.mod h1:KyfArJkhooyba7gYCKSq8v66QdqJmnbAxtV/OX1+JTs= github.com/hashicorp/vic v1.5.1-0.20190403131502-bbfe86ec9443 h1:O/pT5C1Q3mVXMyuqg7yuAWUg/jMZR1/0QTzTRdNR6Uw= github.com/hashicorp/vic v1.5.1-0.20190403131502-bbfe86ec9443/go.mod h1:bEpDU35nTu0ey1EXjwNwPjI9xErAsoOCmcMb9GKvyxo= -github.com/hashicorp/yamux v0.0.0-20180604194846-3520598351bb h1:b5rjCoWHc7eqmAS4/qyk21ZsHyb6Mxv/jykxvNTkU4M= -github.com/hashicorp/yamux v0.0.0-20180604194846-3520598351bb/go.mod h1:+NfK9FKeTrX5uv1uIXGdwYDTeHna2qgaIlx54MXqjAM= github.com/hpcloud/tail v1.0.0/go.mod h1:ab1qPbhIpdTxEkNHXyeSf5vhxWSCs/tWer42PpOxQnU= github.com/ianlancetaylor/demangle v0.0.0-20181102032728-5e5cf60278f6/go.mod h1:aSSvb/t6k1mPoxDqO4vJh6VOCGPwU4O0C2/Eqndh1Sc= github.com/ianlancetaylor/demangle v0.0.0-20200824232613-28f6c0f3b639/go.mod h1:aSSvb/t6k1mPoxDqO4vJh6VOCGPwU4O0C2/Eqndh1Sc= @@ -447,7 +419,6 @@ github.com/jackc/pgx v3.3.0+incompatible/go.mod h1:0ZGrqGqkRlliWnWB4zKnWtjbSWbGk github.com/jarcoal/httpmock v0.0.0-20180424175123-9c70cfe4a1da h1:FjHUJJ7oBW4G/9j1KzlHaXL09LyMVM9rupS39lncbXk= github.com/jarcoal/httpmock v0.0.0-20180424175123-9c70cfe4a1da/go.mod h1:ks+b9deReOc7jgqp+e7LuFiCBH6Rm5hL32cLcEAArb4= github.com/jessevdk/go-flags v1.4.0/go.mod h1:4FA24M0QyGHXBuZZK/XkWh8h0e1EYbRYJSGM75WSRxI= -github.com/jhump/protoreflect v1.6.0 h1:h5jfMVslIg6l29nsMs0D8Wj17RDVdNYti0vDN/PZZoE= github.com/jmespath/go-jmespath v0.0.0-20180206201540-c2b33e8439af h1:pmfjZENx5imkbgOkpRUYLnmbU7UEFbjtDA2hxJ1ichM= github.com/jmespath/go-jmespath v0.0.0-20180206201540-c2b33e8439af/go.mod h1:Nht3zPeWKUH0NzdCt2Blrr5ys8VGpn0CEB0cQHVjt7k= github.com/jonboulle/clockwork v0.1.0/go.mod h1:Ii8DK3G1RaLaWxj9trq07+26W01tbo22gdxWY5EU2bo= @@ -478,7 +449,6 @@ github.com/konsorten/go-windows-terminal-sequences v1.0.3/go.mod h1:T0+1ngSBFLxv github.com/kr/logfmt v0.0.0-20140226030751-b84e30acd515/go.mod h1:+0opPa2QZZtGFBFZlji/RkVcI2GknAs/DXo4wKdlNEc= github.com/kr/pretty v0.1.0/go.mod h1:dAy3ld7l9f0ibDNOQOHHMYYIIbhfbHSm3C4ZsoJORNo= github.com/kr/pretty v0.2.0/go.mod h1:ipq/a2n7PKx3OHsz4KJII5eveXtPO4qwEXGdVfWzfnI= -github.com/kr/pretty v0.2.1 h1:Fmg33tUaq4/8ym9TJN1x7sLJnHVwhP33CNkpYV/7rwI= github.com/kr/pty v1.1.1/go.mod h1:pFQYn66WHrOpPYNljwOMqo10TkYh1fy3cYio2l3bCsQ= github.com/kr/text v0.1.0/go.mod h1:4Jbv+DJW3UT/LiOwJeYQe1efqtUx/iVham/4vfdArNI= github.com/kr/text v0.2.0 h1:5Nx0Ya0ZqY2ygV366QzturHI13Jq95ApcVaJBhpS+AY= @@ -500,6 +470,7 @@ github.com/mattn/go-colorable v0.1.12 h1:jF+Du6AlPIjs2BiUiQlKOX0rt3SujHxPnksPKZb github.com/mattn/go-colorable v0.1.12/go.mod h1:u5H1YNBxpqRaxsYJYSkiCWKzEfiAb1Gb520KVy5xxl4= github.com/mattn/go-isatty v0.0.3/go.mod h1:M+lRXTBqGeGNdLjl/ufCoiOlB5xdOkqRJdNxMWT7Zi4= github.com/mattn/go-isatty v0.0.8/go.mod h1:Iq45c/XA43vh69/j3iqttzPXn0bhXyGjM0Hdxcsrc5s= +github.com/mattn/go-isatty v0.0.10/go.mod h1:qgIWMr58cqv1PHHyhnkY9lrL7etaEgOFcMEpPG5Rm84= github.com/mattn/go-isatty v0.0.11/go.mod h1:PhnuNfih5lzO57/f3n+odYbM4JtupLOxQOAqxQCu2WE= github.com/mattn/go-isatty v0.0.12/go.mod h1:cbi8OIDigv2wuxKPP5vlRcQ1OAZbq2CE4Kysco4FUpU= github.com/mattn/go-isatty v0.0.14 h1:yVuAays6BHfxijgZPzw+3Zlu5yQgKGP2/hcQbHb7S9Y= @@ -515,23 +486,15 @@ github.com/miekg/dns v1.1.41/go.mod h1:p6aan82bvRIyn+zDIv9xYNUpwa73JcSh9BKwknJys github.com/mitchellh/cli v1.0.0/go.mod h1:hNIlj7HEI86fIcpObd7a0FcrxTWetlwJDGcceTlRvqc= github.com/mitchellh/cli v1.1.0 h1:tEElEatulEHDeedTxwckzyYMA5c86fbmNIUL1hBIiTg= github.com/mitchellh/cli v1.1.0/go.mod h1:xcISNoH86gajksDmfB23e/pu+B+GeFRMYmoHXxx3xhI= -github.com/mitchellh/copystructure v1.0.0 h1:Laisrj+bAB6b/yJwB5Bt3ITZhGJdqmxquMKeZ+mmkFQ= -github.com/mitchellh/copystructure v1.0.0/go.mod h1:SNtv71yrdKgLRyLFxmLdkAbkKEFWgYaq1OVrnRcwhnw= github.com/mitchellh/go-homedir v1.0.0/go.mod h1:SfyaCUpYCn1Vlf4IUYiD9fPX4A5wJrkLzIz1N1q0pr0= github.com/mitchellh/go-homedir v1.1.0 h1:lukF9ziXFxDFPkA1vsr5zpc1XuPDn/wFntq5mG+4E0Y= github.com/mitchellh/go-homedir v1.1.0/go.mod h1:SfyaCUpYCn1Vlf4IUYiD9fPX4A5wJrkLzIz1N1q0pr0= -github.com/mitchellh/go-testing-interface v1.0.0 h1:fzU/JVNcaqHQEcVFAKeR41fkiLdIPrefOvVG1VZ96U0= -github.com/mitchellh/go-testing-interface v1.0.0/go.mod h1:kRemZodwjscx+RGhAo8eIhFbs2+BFgRtFPeD/KE+zxI= -github.com/mitchellh/go-wordwrap v1.0.0/go.mod h1:ZXFpozHsX6DPmq2I0TCekCxypsnAUbP2oI0UX1GXzOo= github.com/mitchellh/gox v0.4.0/go.mod h1:Sd9lOJ0+aimLBi73mGofS1ycjY8lL3uZM3JPS42BGNg= github.com/mitchellh/iochan v1.0.0/go.mod h1:JwYml1nuB7xOzsp52dPpHFffvOCDupsG0QubkSMEySY= github.com/mitchellh/mapstructure v0.0.0-20160808181253-ca63d7c062ee/go.mod h1:FVVH3fgwuzCH5S8UJGiWEs2h04kUh9fWfEaFds41c1Y= github.com/mitchellh/mapstructure v1.1.2/go.mod h1:FVVH3fgwuzCH5S8UJGiWEs2h04kUh9fWfEaFds41c1Y= +github.com/mitchellh/mapstructure v1.4.1 h1:CpVNEelQCZBooIPDn+AR3NpivK/TIKU8bDxdASFVQag= github.com/mitchellh/mapstructure v1.4.1/go.mod h1:bFUtVrKA4DC2yAKiSyO/QUcy7e+RRV2QTWOzhPopBRo= -github.com/mitchellh/mapstructure v1.5.0 h1:jeMsZIYE/09sWLaz43PL7Gy6RuMjD2eJVyuac5Z2hdY= -github.com/mitchellh/mapstructure v1.5.0/go.mod h1:bFUtVrKA4DC2yAKiSyO/QUcy7e+RRV2QTWOzhPopBRo= -github.com/mitchellh/reflectwalk v1.0.0 h1:9D+8oIskB4VJBN5SFlmc27fSlIBZaov1Wpk/IfikLNY= -github.com/mitchellh/reflectwalk v1.0.0/go.mod h1:mSTlrgnPZtwu0c4WaC2kGObEpuNDbx0jmZXqmk4esnw= github.com/moby/spdystream v0.2.0/go.mod h1:f7i0iNDQJ059oMTcWxx8MA/zKFIuD/lY+0GqbN2Wy8c= github.com/moby/term v0.0.0-20210610120745-9d4ed1856297/go.mod h1:vgPCkQMyxTZ7IDy8SXRufE172gr8+K/JE/7hHFxHW3A= github.com/modern-go/concurrent v0.0.0-20180228061459-e0a39a4cb421/go.mod h1:6dJC0mAP4ikYIbvyc7fijjWJddQyLn8Ig3JB5CqoB9Q= @@ -553,8 +516,6 @@ github.com/niemeyer/pretty v0.0.0-20200227124842-a10e7caefd8e/go.mod h1:zD1mROLA github.com/nxadm/tail v1.4.4/go.mod h1:kenIhsEOeOJmVchQTgglprH7qJGnHDVpk1VPCcaMI8A= github.com/nxadm/tail v1.4.8 h1:nPr65rt6Y5JFSKQO7qToXr7pePgD6Gwiw05lkbyAQTE= github.com/nxadm/tail v1.4.8/go.mod h1:+ncqLTQzXmGhMZNUePPaPqPvBxHAIsmXswZKocGu+AU= -github.com/oklog/run v1.0.0 h1:Ru7dDtJNOyC66gQ5dQmaCa0qIsAUFY3sFpK1Xk8igrw= -github.com/oklog/run v1.0.0/go.mod h1:dlhp/R75TPv97u0XWUtDeV/lRKWPKSdTuV0TZvrmrQA= github.com/oklog/ulid v1.3.1/go.mod h1:CirwcVhetQ6Lv90oh/F+FBtV6XMibvdAFo93nm5qn4U= github.com/olekukonko/tablewriter v0.0.0-20180130162743-b8a9be070da4/go.mod h1:vsDQFd/mU46D+Z4whnwzcISnGGzXWMclvtLoiIKAKIo= github.com/onsi/ginkgo v0.0.0-20170829012221-11459a886d9c/go.mod h1:lLunBs/Ym6LB5Z9jYTR76FiuTmxDTDusOGeTQH+WWjE= @@ -581,8 +542,6 @@ github.com/pascaldekloe/goe v0.1.0 h1:cBOtyMzM9HTpWjXfbbunk26uA6nG3a8n06Wieeh0Mw github.com/pascaldekloe/goe v0.1.0/go.mod h1:lzWF7FIEvWOWxwDKqyGYQf6ZUaNfKdP144TG7ZOy1lc= github.com/pelletier/go-toml v1.2.0/go.mod h1:5z9KED0ma1S8pY6P1sdut58dfprrGBbd/94hg7ilaic= github.com/peterbourgon/diskv v2.0.1+incompatible/go.mod h1:uqqh8zWWbv1HBMNONnaR/tNboyR3/BZd58JJSHlUSCU= -github.com/pierrec/lz4 v2.5.2+incompatible h1:WCjObylUIOlKy/+7Abdn34TLIkXiA4UWUMhxq9m9ZXI= -github.com/pierrec/lz4 v2.5.2+incompatible/go.mod h1:pdkljMzZIN41W+lC3N2tnIh5sFi+IEE17M5jbnwPHcY= github.com/pkg/errors v0.8.0/go.mod h1:bwawxfHBFNV+L2hUp1rHADufV3IMtnDRdf1r5NINEl0= github.com/pkg/errors v0.8.1/go.mod h1:bwawxfHBFNV+L2hUp1rHADufV3IMtnDRdf1r5NINEl0= github.com/pkg/errors v0.9.1 h1:FEBLx1zS214owpjy7qsBeixbURkuhQAwrK5UwLGTwt4= @@ -629,9 +588,6 @@ github.com/rs/zerolog v1.4.0/go.mod h1:YbFCdg8HfsridGWAh22vktObvhZbQsZXe4/zB0OKk github.com/russross/blackfriday v1.5.2/go.mod h1:JO/DiYxRf+HjHt06OyowR9PTA263kcR/rfWxYHBV53g= github.com/russross/blackfriday/v2 v2.0.1/go.mod h1:+Rmxgy9KzJVeS9/2gXHxylqXiyQDYRxCVz55jmeOWTM= github.com/ryanuber/columnize v0.0.0-20160712163229-9b3edd62028f/go.mod h1:sm1tb6uqfes/u+d4ooFouqFdy9/2g9QGwK3SQygK0Ts= -github.com/ryanuber/columnize v2.1.0+incompatible/go.mod h1:sm1tb6uqfes/u+d4ooFouqFdy9/2g9QGwK3SQygK0Ts= -github.com/ryanuber/go-glob v1.0.0 h1:iQh3xXAumdQ+4Ufa5b25cRpC5TYKlno6hsv6Cb3pkBk= -github.com/ryanuber/go-glob v1.0.0/go.mod h1:807d1WSdnB0XRJzKNil9Om6lcp/3a0v4qIHxIXzX/Yc= github.com/satori/go.uuid v1.2.0/go.mod h1:dA0hQrYB0VpLJoorglMZABFdXlWrHn1NEOzdhQKdks0= github.com/sean-/conswriter v0.0.0-20180208195008-f5ae3917a627/go.mod h1:7zjs06qF79/FKAJpBvFx3P8Ww4UTIMAe+lpNXDHziac= github.com/sean-/pager v0.0.0-20180208200047-666be9bf53b5/go.mod h1:BeybITEsBEg6qbIiqJ6/Bqeq25bCLbL7YFmpaFfJDuM= @@ -727,9 +683,8 @@ go.opentelemetry.io/otel/sdk/metric v0.20.0/go.mod h1:knxiS8Xd4E/N+ZqKmUPf3gTTZ4 go.opentelemetry.io/otel/trace v0.20.0/go.mod h1:6GjCW8zgDjwGHGa6GkyeB8+/5vjT16gUEi0Nf1iBdgw= go.opentelemetry.io/proto/otlp v0.7.0/go.mod h1:PqfVotwruBrMGOCsRd/89rSnXhoiJIqeYNgFYFoEGnI= go.uber.org/atomic v1.4.0/go.mod h1:gD2HeocX3+yG+ygLZcrzQJaqmWj9AIm7n08wl/qW/PE= +go.uber.org/atomic v1.7.0 h1:ADUqmZGgLDDfbSL9ZmPxKTybcoEYHgpYfELNoN+7hsw= go.uber.org/atomic v1.7.0/go.mod h1:fEN4uk6kAWBTFdckzkM89CLk9XfWZrxpCo0nPH17wJc= -go.uber.org/atomic v1.9.0 h1:ECmE8Bn/WFTYwEW/bpKD3M8VtR/zQVbavAoalC1PYyE= -go.uber.org/atomic v1.9.0/go.mod h1:fEN4uk6kAWBTFdckzkM89CLk9XfWZrxpCo0nPH17wJc= go.uber.org/goleak v1.1.10 h1:z+mqJhf6ss6BSfSM671tgKyZBFPTTJM+HLxnhPC3wu0= go.uber.org/goleak v1.1.10/go.mod h1:8a7PlsEVH3e/a/GLqe5IIrQx6GzcnRmZEufDUTk4A7A= go.uber.org/multierr v1.1.0/go.mod h1:wR5kodmAFQ0UK8QlbwjlSNy0Z68gJhDJUG5sjR94q/0= @@ -765,6 +720,8 @@ golang.org/x/exp v0.0.0-20191227195350-da58074b4299/go.mod h1:2RIsYlXP63K8oxa1u0 golang.org/x/exp v0.0.0-20200119233911-0405dc783f0a/go.mod h1:2RIsYlXP63K8oxa1u096TMicItID8zy7Y6sNkU49FU4= golang.org/x/exp v0.0.0-20200207192155-f17229e696bd/go.mod h1:J/WKrq2StrnmMY6+EHIKF9dgMWnmCNThgcyBT1FY9mM= golang.org/x/exp v0.0.0-20200224162631-6cc2880d07d6/go.mod h1:3jZMyOhIsHpP37uCMkUooju7aAi5cS1Q23tOzKc+0MU= +golang.org/x/exp v0.0.0-20230321023759-10a507213a29 h1:ooxPy7fPvB4kwsA2h+iBNHkAbp/4JxTSwCmvdjEYmug= +golang.org/x/exp v0.0.0-20230321023759-10a507213a29/go.mod h1:CxIveKay+FTh1D0yPZemJVgC/95VzuuOLq5Qi4xnoYc= golang.org/x/image v0.0.0-20190227222117-0694c2d4d067/go.mod h1:kZ7UVZpmo3dzQBMxlp+ypCbDeSB+sBbTgSJuh5dn5js= golang.org/x/image v0.0.0-20190802002840-cff245a6509b/go.mod h1:FeLwcggjj3mMvU+oOTbSwawSJRM1uh48EjtB4UJZlP0= golang.org/x/lint v0.0.0-20181026193005-c67002cb31c3/go.mod h1:UVdnD1Gm6xHRNCYTkRU2/jEulfH38KcIWyp/GAMgvoE= @@ -841,8 +798,8 @@ golang.org/x/net v0.0.0-20210405180319-a5a99cb37ef4/go.mod h1:p54w0d4576C0XHj96b golang.org/x/net v0.0.0-20210410081132-afb366fc7cd1/go.mod h1:9tjilg8BloeKEkVJvy7fQ90B1CfIiPueXVOjqfkSzI8= golang.org/x/net v0.0.0-20210428140749-89ef3d95e781/go.mod h1:OJAsFXCWl8Ukc7SiCT/9KSuxbyM7479/AVlXFRxuMCk= golang.org/x/net v0.0.0-20210520170846-37e1c6afe023/go.mod h1:9nx3DQGgdP8bBQD5qxJ1jj9UTztislL4KSBs9R2vV5Y= -golang.org/x/net v0.0.0-20220127200216-cd36cc0744dd h1:O7DYs+zxREGLKzKoMQrtrEacpb0ZVXA5rIwylE2Xchk= -golang.org/x/net v0.0.0-20220127200216-cd36cc0744dd/go.mod h1:CfG3xpIq0wQ8r1q4Su4UZFWDARRcnwPjda9FqA0JpMk= +golang.org/x/net v0.7.0 h1:rJrUqqhjsgNp7KqAIc25s9pZnjU7TUcSY7HcVZjdn1g= +golang.org/x/net v0.7.0/go.mod h1:2Tu9+aMcznHK/AK1HMvgo6xiTLG5rD5rZLDS+rp2Bjs= golang.org/x/oauth2 v0.0.0-20180821212333-d2e6202438be/go.mod h1:N/0e6XlmueqKjAGxoOufVs8QHGRruUQn6yWY3a++T0U= golang.org/x/oauth2 v0.0.0-20190226205417-e64efc72b421/go.mod h1:gOpvHmFTYa4IltrdGE7lF6nIHvwfUNPOp7c8zoXwtLw= golang.org/x/oauth2 v0.0.0-20190604053449-0f29369cfe45/go.mod h1:gOpvHmFTYa4IltrdGE7lF6nIHvwfUNPOp7c8zoXwtLw= @@ -894,6 +851,7 @@ golang.org/x/sys v0.0.0-20190922100055-0a153f010e69/go.mod h1:h1NjWce9XRLGQEsW7w golang.org/x/sys v0.0.0-20190924154521-2837fb4f24fe/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= golang.org/x/sys v0.0.0-20191001151750-bb3f8db39f24/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= golang.org/x/sys v0.0.0-20191005200804-aed5e4c7ecf9/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= +golang.org/x/sys v0.0.0-20191008105621-543471e840be/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= golang.org/x/sys v0.0.0-20191022100944-742c48ecaeb7/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= golang.org/x/sys v0.0.0-20191026070338-33540a1f6037/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= golang.org/x/sys v0.0.0-20191120155948-bd437916bb0e/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= @@ -943,13 +901,14 @@ golang.org/x/sys v0.0.0-20210817190340-bfb29a6856f2/go.mod h1:oPkhp1MJrh7nUepCBc golang.org/x/sys v0.0.0-20210927094055-39ccf1dd6fa6/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg= golang.org/x/sys v0.0.0-20220412211240-33da011f77ad/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg= golang.org/x/sys v0.0.0-20220503163025-988cb79eb6c6/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg= -golang.org/x/sys v0.0.0-20220728004956-3c1f35247d10 h1:WIoqL4EROvwiPdUtaip4VcDdpZ4kha7wBWZrbVKCIZg= golang.org/x/sys v0.0.0-20220728004956-3c1f35247d10/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg= +golang.org/x/sys v0.5.0 h1:MUK/U/4lj1t1oPg0HfuXDN/Z1wv31ZJ/YcPiGccS4DU= +golang.org/x/sys v0.5.0/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg= golang.org/x/term v0.0.0-20201117132131-f5c789dd3221/go.mod h1:Nr5EML6q2oocZ2LXRh80K7BxOlk5/8JxuGnuhpl+muw= golang.org/x/term v0.0.0-20201126162022-7de9c90e9dd1/go.mod h1:bj7SfCRtBDWHUb9snDiAeCFNEtKQo2Wmx5Cou7ajbmo= golang.org/x/term v0.0.0-20210220032956-6a3ed077a48d/go.mod h1:bj7SfCRtBDWHUb9snDiAeCFNEtKQo2Wmx5Cou7ajbmo= -golang.org/x/term v0.0.0-20220526004731-065cf7ba2467 h1:CBpWXWQpIRjzmkkA+M7q9Fqnwd2mZr3AFqexg8YTfoM= -golang.org/x/term v0.0.0-20220526004731-065cf7ba2467/go.mod h1:jbD1KX2456YbFQfuXm/mYQcufACuNUgVhRMnK/tPxf8= +golang.org/x/term v0.5.0 h1:n2a8QNdAb0sZNpU9R1ALUXBbY+w51fCQDN+7EdxNBsY= +golang.org/x/term v0.5.0/go.mod h1:jMB1sMXY+tzblOD4FWmEbocvup2/aLOaQEp7JmGp78k= golang.org/x/text v0.0.0-20160726164857-2910a502d2bf/go.mod h1:NqM8EUOU14njkJ3fqMW+pc6Ldnwhi/IjpwHt7yyuwOQ= golang.org/x/text v0.0.0-20170915032832-14c0d48ead0c/go.mod h1:NqM8EUOU14njkJ3fqMW+pc6Ldnwhi/IjpwHt7yyuwOQ= golang.org/x/text v0.3.0/go.mod h1:NqM8EUOU14njkJ3fqMW+pc6Ldnwhi/IjpwHt7yyuwOQ= @@ -959,8 +918,8 @@ golang.org/x/text v0.3.3/go.mod h1:5Zoc/QRtKVWzQhOtBMvqHzDpF6irO9z98xDceosuGiQ= golang.org/x/text v0.3.4/go.mod h1:5Zoc/QRtKVWzQhOtBMvqHzDpF6irO9z98xDceosuGiQ= golang.org/x/text v0.3.5/go.mod h1:5Zoc/QRtKVWzQhOtBMvqHzDpF6irO9z98xDceosuGiQ= golang.org/x/text v0.3.6/go.mod h1:5Zoc/QRtKVWzQhOtBMvqHzDpF6irO9z98xDceosuGiQ= -golang.org/x/text v0.3.8 h1:nAL+RVCQ9uMn3vJZbV+MRnydTJFPf8qqY42YiA6MrqY= -golang.org/x/text v0.3.8/go.mod h1:E6s5w1FMmriuDzIBO73fBruAKo1PCIq6d2Q6DHfQ8WQ= +golang.org/x/text v0.7.0 h1:4BRB4x83lYWy72KwLD/qYDuTu7q9PjSagHvijDw7cLo= +golang.org/x/text v0.7.0/go.mod h1:mrYo+phRRbMaCq/xk9113O4dZlRixOauAjOtrjsXDZ8= golang.org/x/time v0.0.0-20181108054448-85acf8d2951c/go.mod h1:tRJNPiyCQ0inRvYxbN9jk5I+vvW/OXSQhTDSoE431IQ= golang.org/x/time v0.0.0-20190308202827-9d24e82272b4/go.mod h1:tRJNPiyCQ0inRvYxbN9jk5I+vvW/OXSQhTDSoE431IQ= golang.org/x/time v0.0.0-20191024005414-555d28b269f0/go.mod h1:tRJNPiyCQ0inRvYxbN9jk5I+vvW/OXSQhTDSoE431IQ= @@ -1027,11 +986,10 @@ golang.org/x/tools v0.0.0-20210105154028-b0ab187a4818/go.mod h1:emZCQorbCU4vsT4f golang.org/x/tools v0.0.0-20210106214847-113979e3529a/go.mod h1:emZCQorbCU4vsT4fOWvOPXz4eW1wZW4PmDk9uLelYpA= golang.org/x/tools v0.1.0/go.mod h1:xkSsbof2nBLbhDlRMhhhyNLN/zl3eTqcnHD5viDpcZ0= golang.org/x/tools v0.1.2/go.mod h1:o0xws9oXOQQZyjljx8fwUC0k7L1pTE6eaCbjGeHmOkk= -golang.org/x/tools v0.1.12 h1:VveCTK38A2rkS8ZqFY25HIDFscX5X9OoEhJd3quQmXU= +golang.org/x/tools v0.2.0 h1:G6AHpWxTMGY1KyEYoAQ5WTtIekUUvDNjan3ugu60JvE= 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= -golang.org/x/xerrors v0.0.0-20200804184101-5ec99f83aff1 h1:go1bK/D/BFZV2I8cIQd1NKEZ+0owSTG1fDTci4IqFcE= golang.org/x/xerrors v0.0.0-20200804184101-5ec99f83aff1/go.mod h1:I/5z698sn9Ka8TeJc9MKroUUfqBBauWjQqLJ2OPfmY0= gomodules.xyz/jsonpatch/v2 v2.2.0 h1:4pT439QV83L+G9FkcCriY6EkpcK6r6bK+A5FBUMI7qY= gomodules.xyz/jsonpatch/v2 v2.2.0/go.mod h1:WXp+iVDkoLQqPudfQ9GBlwB2eZ5DKOnjQZCYdOS8GPY= @@ -1165,8 +1123,6 @@ gopkg.in/natefinch/lumberjack.v2 v2.0.0/go.mod h1:l0ndWWf7gzL7RNwBG7wST/UCcT4T24 gopkg.in/resty.v1 v1.12.0 h1:CuXP0Pjfw9rOuY6EP+UvtNvt5DSqHpIxILZKT/quCZI= gopkg.in/resty.v1 v1.12.0/go.mod h1:mDo4pnntr5jdWRML875a/NmxYqAlA73dVijT2AXvQQo= gopkg.in/square/go-jose.v2 v2.2.2/go.mod h1:M9dMgbHiYLoDGQrXy7OpJDJWiKiU//h+vD76mk0e1AI= -gopkg.in/square/go-jose.v2 v2.5.1 h1:7odma5RETjNHWJnR32wx8t+Io4djHE1PqxCFx3iiZ2w= -gopkg.in/square/go-jose.v2 v2.5.1/go.mod h1:M9dMgbHiYLoDGQrXy7OpJDJWiKiU//h+vD76mk0e1AI= gopkg.in/tomb.v1 v1.0.0-20141024135613-dd632973f1e7 h1:uRGJdciOHaEIrze2W8Q3AKkepLTh2hOroT7a+7czfdQ= gopkg.in/tomb.v1 v1.0.0-20141024135613-dd632973f1e7/go.mod h1:dt/ZhP58zS4L8KSrWDmTeBkI65Dw0HsyUHuEVlX15mw= gopkg.in/yaml.v2 v2.0.0-20170812160011-eb3733d160e7/go.mod h1:JAlM8MvJe8wmxCU4Bli9HhUf9+ttbYbLASfIpnQbh74= diff --git a/control-plane/subcommand/common/common_test.go b/control-plane/subcommand/common/common_test.go index 6021bd0b49..bce90d6b76 100644 --- a/control-plane/subcommand/common/common_test.go +++ b/control-plane/subcommand/common/common_test.go @@ -8,6 +8,7 @@ import ( "net/url" "os" "testing" + "time" "github.com/hashicorp/consul-k8s/control-plane/helper/go-discover/mocks" "github.com/hashicorp/consul/api" @@ -162,33 +163,36 @@ func TestConsulLogin_TokenNotReplicated(t *testing.T) { func TestConsulLogin_EmptyBearerTokenFile(t *testing.T) { t.Parallel() + require := require.New(t) bearerTokenFile := WriteTempFile(t, "") params := LoginParams{ BearerTokenFile: bearerTokenFile, } _, err := ConsulLogin(nil, params, hclog.NewNullLogger()) - require.EqualError(t, err, fmt.Sprintf("no bearer token found in %q", bearerTokenFile)) + require.EqualError(err, fmt.Sprintf("no bearer token found in %q", bearerTokenFile)) } func TestConsulLogin_BearerTokenFileDoesNotExist(t *testing.T) { t.Parallel() + require := require.New(t) randFileName := fmt.Sprintf("/foo/%d/%d", rand.Int(), rand.Int()) params := LoginParams{ BearerTokenFile: randFileName, } _, err := ConsulLogin(nil, params, hclog.NewNullLogger()) - require.Error(t, err) - require.Contains(t, err.Error(), "unable to read bearer token file") + require.Error(err) + require.Contains(err.Error(), "unable to read bearer token file") } func TestConsulLogin_TokenFileUnwritable(t *testing.T) { t.Parallel() + require := require.New(t) bearerTokenFile := WriteTempFile(t, "foo") client := startMockServer(t) // This is a common.Logger. log, err := Logger("INFO", false) - require.NoError(t, err) + require.NoError(err) randFileName := fmt.Sprintf("/foo/%d/%d", rand.Int(), rand.Int()) params := LoginParams{ AuthMethod: testAuthMethod, @@ -197,12 +201,13 @@ func TestConsulLogin_TokenFileUnwritable(t *testing.T) { NumRetries: 2, } _, err = ConsulLogin(client, params, log) - require.Error(t, err) - require.Contains(t, err.Error(), "error writing token to file sink") + require.Error(err) + require.Contains(err.Error(), "error writing token to file sink") } func TestWriteFileWithPerms_InvalidOutputFile(t *testing.T) { t.Parallel() + rand.New(rand.NewSource(time.Now().UnixNano())) randFileName := fmt.Sprintf("/tmp/tmp/tmp/%d", rand.Int()) t.Cleanup(func() { os.RemoveAll(randFileName) @@ -213,6 +218,7 @@ func TestWriteFileWithPerms_InvalidOutputFile(t *testing.T) { func TestWriteFileWithPerms_OutputFileExists(t *testing.T) { t.Parallel() + rand.New(rand.NewSource(time.Now().UnixNano())) randFileName := fmt.Sprintf("/tmp/%d", rand.Int()) err := os.WriteFile(randFileName, []byte("foo"), os.FileMode(0444)) require.NoError(t, err) @@ -230,6 +236,7 @@ func TestWriteFileWithPerms_OutputFileExists(t *testing.T) { func TestWriteFileWithPerms(t *testing.T) { t.Parallel() payload := "foo-foo-foo-foo" + rand.New(rand.NewSource(time.Now().UnixNano())) randFileName := fmt.Sprintf("/tmp/%d", rand.Int()) t.Cleanup(func() { os.RemoveAll(randFileName) diff --git a/control-plane/subcommand/inject-connect/command.go b/control-plane/subcommand/inject-connect/command.go index 93566387cd..5cbd2abdee 100644 --- a/control-plane/subcommand/inject-connect/command.go +++ b/control-plane/subcommand/inject-connect/command.go @@ -35,6 +35,7 @@ import ( "k8s.io/klog/v2" ctrl "sigs.k8s.io/controller-runtime" ctrlRuntimeWebhook "sigs.k8s.io/controller-runtime/pkg/webhook" + ctrlwebhook "sigs.k8s.io/controller-runtime/pkg/webhook" ) const WebhookCAFilename = "ca.crt" @@ -644,61 +645,61 @@ func (c *Command) Run(args []string) int { // Note: The path here should be identical to the one on the kubebuilder // annotation in each webhook file. mgr.GetWebhookServer().Register("/mutate-v1alpha1-servicedefaults", - &ctrlRuntimeWebhook.Admission{Handler: &v1alpha1.ServiceDefaultsWebhook{ + &ctrlwebhook.Admission{Handler: &v1alpha1.ServiceDefaultsWebhook{ Client: mgr.GetClient(), Logger: ctrl.Log.WithName("webhooks").WithName(apicommon.ServiceDefaults), ConsulMeta: consulMeta, }}) mgr.GetWebhookServer().Register("/mutate-v1alpha1-serviceresolver", - &ctrlRuntimeWebhook.Admission{Handler: &v1alpha1.ServiceResolverWebhook{ + &ctrlwebhook.Admission{Handler: &v1alpha1.ServiceResolverWebhook{ Client: mgr.GetClient(), Logger: ctrl.Log.WithName("webhooks").WithName(apicommon.ServiceResolver), ConsulMeta: consulMeta, }}) mgr.GetWebhookServer().Register("/mutate-v1alpha1-proxydefaults", - &ctrlRuntimeWebhook.Admission{Handler: &v1alpha1.ProxyDefaultsWebhook{ + &ctrlwebhook.Admission{Handler: &v1alpha1.ProxyDefaultsWebhook{ Client: mgr.GetClient(), Logger: ctrl.Log.WithName("webhooks").WithName(apicommon.ProxyDefaults), ConsulMeta: consulMeta, }}) mgr.GetWebhookServer().Register("/mutate-v1alpha1-mesh", - &ctrlRuntimeWebhook.Admission{Handler: &v1alpha1.MeshWebhook{ + &ctrlwebhook.Admission{Handler: &v1alpha1.MeshWebhook{ Client: mgr.GetClient(), Logger: ctrl.Log.WithName("webhooks").WithName(apicommon.Mesh), ConsulMeta: consulMeta, }}) mgr.GetWebhookServer().Register("/mutate-v1alpha1-exportedservices", - &ctrlRuntimeWebhook.Admission{Handler: &v1alpha1.ExportedServicesWebhook{ + &ctrlwebhook.Admission{Handler: &v1alpha1.ExportedServicesWebhook{ Client: mgr.GetClient(), Logger: ctrl.Log.WithName("webhooks").WithName(apicommon.ExportedServices), ConsulMeta: consulMeta, }}) mgr.GetWebhookServer().Register("/mutate-v1alpha1-servicerouter", - &ctrlRuntimeWebhook.Admission{Handler: &v1alpha1.ServiceRouterWebhook{ + &ctrlwebhook.Admission{Handler: &v1alpha1.ServiceRouterWebhook{ Client: mgr.GetClient(), Logger: ctrl.Log.WithName("webhooks").WithName(apicommon.ServiceRouter), ConsulMeta: consulMeta, }}) mgr.GetWebhookServer().Register("/mutate-v1alpha1-servicesplitter", - &ctrlRuntimeWebhook.Admission{Handler: &v1alpha1.ServiceSplitterWebhook{ + &ctrlwebhook.Admission{Handler: &v1alpha1.ServiceSplitterWebhook{ Client: mgr.GetClient(), Logger: ctrl.Log.WithName("webhooks").WithName(apicommon.ServiceSplitter), ConsulMeta: consulMeta, }}) mgr.GetWebhookServer().Register("/mutate-v1alpha1-serviceintentions", - &ctrlRuntimeWebhook.Admission{Handler: &v1alpha1.ServiceIntentionsWebhook{ + &ctrlwebhook.Admission{Handler: &v1alpha1.ServiceIntentionsWebhook{ Client: mgr.GetClient(), Logger: ctrl.Log.WithName("webhooks").WithName(apicommon.ServiceIntentions), ConsulMeta: consulMeta, }}) mgr.GetWebhookServer().Register("/mutate-v1alpha1-ingressgateway", - &ctrlRuntimeWebhook.Admission{Handler: &v1alpha1.IngressGatewayWebhook{ + &ctrlwebhook.Admission{Handler: &v1alpha1.IngressGatewayWebhook{ Client: mgr.GetClient(), Logger: ctrl.Log.WithName("webhooks").WithName(apicommon.IngressGateway), ConsulMeta: consulMeta, }}) mgr.GetWebhookServer().Register("/mutate-v1alpha1-terminatinggateway", - &ctrlRuntimeWebhook.Admission{Handler: &v1alpha1.TerminatingGatewayWebhook{ + &ctrlwebhook.Admission{Handler: &v1alpha1.TerminatingGatewayWebhook{ Client: mgr.GetClient(), Logger: ctrl.Log.WithName("webhooks").WithName(apicommon.TerminatingGateway), ConsulMeta: consulMeta, diff --git a/control-plane/subcommand/server-acl-init/command.go b/control-plane/subcommand/server-acl-init/command.go index a444f65aaa..698da2a25c 100644 --- a/control-plane/subcommand/server-acl-init/command.go +++ b/control-plane/subcommand/server-acl-init/command.go @@ -22,11 +22,12 @@ import ( "github.com/hashicorp/consul/api" "github.com/hashicorp/go-hclog" "github.com/hashicorp/go-netaddrs" - vaultApi "github.com/hashicorp/vault/api" "github.com/mitchellh/cli" "github.com/mitchellh/mapstructure" "golang.org/x/text/cases" "golang.org/x/text/language" + k8serrors "k8s.io/apimachinery/pkg/api/errors" + metav1 "k8s.io/apimachinery/pkg/apis/meta/v1" "k8s.io/client-go/kubernetes" ) @@ -85,10 +86,8 @@ type Command struct { flagEnableInjectK8SNSMirroring bool // Enables mirroring of k8s namespaces into Consul for Connect inject flagInjectK8SNSMirroringPrefix string // Prefix added to Consul namespaces created when mirroring injected services - // Flags for the secrets backend. - flagSecretsBackend SecretsBackendType - flagBootstrapTokenSecretName string - flagBootstrapTokenSecretKey string + // Flag to support a custom bootstrap token. + flagBootstrapTokenFile string flagLogLevel string flagLogJSON bool @@ -99,9 +98,7 @@ type Command struct { // flagFederation indicates if federation has been enabled in the cluster. flagFederation bool - backend SecretsBackend // for unit testing. - clientset kubernetes.Interface - vaultClient *vaultApi.Client + clientset kubernetes.Interface watcher consul.ServerConnectionManager @@ -197,14 +194,9 @@ func (c *Command) init() { c.flags.BoolVar(&c.flagFederation, "federation", false, "Toggle for when federation has been enabled.") - c.flags.StringVar((*string)(&c.flagSecretsBackend), "secrets-backend", "kubernetes", - `The secrets backend to use. Either "vault" or "kubernetes". Defaults to "kubernetes"`) - c.flags.StringVar(&c.flagBootstrapTokenSecretName, "bootstrap-token-secret-name", "", - "The name of the Vault or Kuberenetes secret for the bootstrap token. This token must have `ac::write` permission "+ - "in order to create policies and tokens. If not provided or if the secret is empty, then this command will "+ - "bootstrap ACLs and write the bootstrap token to this secret.") - c.flags.StringVar(&c.flagBootstrapTokenSecretKey, "bootstrap-token-secret-key", "", - "The key within the Vault or Kuberenetes secret containing the bootstrap token.") + c.flags.StringVar(&c.flagBootstrapTokenFile, "bootstrap-token-file", "", + "Path to file containing ACL token for creating policies and tokens. This token must have 'acl:write' permissions."+ + "When provided, servers will not be bootstrapped and their policies and tokens will not be updated.") c.flags.DurationVar(&c.flagTimeout, "timeout", 10*time.Minute, "How long we'll try to bootstrap ACLs for before timing out, e.g. 1ms, 2s, 3m") @@ -239,7 +231,6 @@ func (c *Command) Help() string { // The function will retry its tasks indefinitely until they are complete. func (c *Command) Run(args []string) int { c.once.Do(c.init) - defer c.quitVaultAgent() if err := c.flags.Parse(args); err != nil { return 1 } @@ -273,6 +264,16 @@ func (c *Command) Run(args []string) int { } } + var providedBootstrapToken string + if c.flagBootstrapTokenFile != "" { + var err error + providedBootstrapToken, err = loadTokenFromFile(c.flagBootstrapTokenFile) + if err != nil { + c.UI.Error(err.Error()) + return 1 + } + } + var cancel context.CancelFunc c.ctx, cancel = context.WithTimeout(context.Background(), c.flagTimeout) // The context will only ever be intentionally ended by the timeout. @@ -305,12 +306,8 @@ func (c *Command) Run(args []string) int { c.UI.Error(err.Error()) } - if err := c.configureSecretsBackend(); err != nil { - c.log.Error(err.Error()) - return 1 - } - var bootstrapToken string + if c.flagACLReplicationTokenFile != "" && !c.flagCreateACLReplicationToken { // If ACL replication is enabled, we don't need to ACL bootstrap the servers // since they will be performing replication. @@ -319,7 +316,21 @@ func (c *Command) Run(args []string) int { c.log.Info("ACL replication is enabled so skipping Consul server ACL bootstrapping") bootstrapToken = aclReplicationToken } else { - bootstrapToken, err = c.bootstrapServers(ipAddrs, c.backend) + // Check if we've already been bootstrapped. + var bootTokenSecretName string + if providedBootstrapToken != "" { + c.log.Info("Using provided bootstrap token") + bootstrapToken = providedBootstrapToken + } else { + bootTokenSecretName = c.withPrefix("bootstrap-acl-token") + bootstrapToken, err = c.getBootstrapToken(bootTokenSecretName) + if err != nil { + c.log.Error(fmt.Sprintf("Unexpected error looking for preexisting bootstrap Secret: %s", err)) + return 1 + } + } + + bootstrapToken, err = c.bootstrapServers(ipAddrs, bootstrapToken, bootTokenSecretName) if err != nil { c.log.Error(err.Error()) return 1 @@ -795,6 +806,24 @@ func (c *Command) configureGateway(gatewayParams ConfigureGatewayParams, consulC return nil } +// getBootstrapToken returns the existing bootstrap token if there is one by +// reading the Kubernetes Secret with name secretName. +// If there is no bootstrap token yet, then it returns an empty string (not an error). +func (c *Command) getBootstrapToken(secretName string) (string, error) { + secret, err := c.clientset.CoreV1().Secrets(c.flagK8sNamespace).Get(c.ctx, secretName, metav1.GetOptions{}) + if err != nil { + if k8serrors.IsNotFound(err) { + return "", nil + } + return "", err + } + token, ok := secret.Data[common.ACLTokenSecretKey] + if !ok { + return "", fmt.Errorf("secret %q does not have data key 'token'", secretName) + } + return string(token), nil +} + func (c *Command) configureKubeClient() error { config, err := subcommand.K8SConfig(c.k8s.KubeConfig()) if err != nil { @@ -807,55 +836,6 @@ func (c *Command) configureKubeClient() error { return nil } -// configureSecretsBackend configures either the Kubernetes or Vault -// secrets backend based on flags. -func (c *Command) configureSecretsBackend() error { - if c.backend != nil { - // support a fake backend in unit tests - return nil - } - secretName := c.flagBootstrapTokenSecretName - if secretName == "" { - secretName = c.withPrefix("bootstrap-acl-token") - } - - secretKey := c.flagBootstrapTokenSecretKey - if secretKey == "" { - secretKey = common.ACLTokenSecretKey - } - - switch c.flagSecretsBackend { - case SecretsBackendTypeKubernetes: - c.backend = &KubernetesSecretsBackend{ - ctx: c.ctx, - clientset: c.clientset, - k8sNamespace: c.flagK8sNamespace, - secretName: secretName, - secretKey: secretKey, - } - return nil - case SecretsBackendTypeVault: - cfg := vaultApi.DefaultConfig() - cfg.Address = "" - cfg.AgentAddress = "http://127.0.0.1:8200" - vaultClient, err := vaultApi.NewClient(cfg) - if err != nil { - return fmt.Errorf("Error initializing Vault client: %w", err) - } - - c.vaultClient = vaultClient // must set this for c.quitVaultAgent. - c.backend = &VaultSecretsBackend{ - vaultClient: c.vaultClient, - secretName: secretName, - secretKey: secretKey, - } - return nil - default: - validValues := []SecretsBackendType{SecretsBackendTypeKubernetes, SecretsBackendTypeVault} - return fmt.Errorf("Invalid value for -secrets-backend: %q. Valid values are %v.", c.flagSecretsBackend, validValues) - } -} - // untilSucceeds runs op until it returns a nil error. // If c.cmdTimeout is cancelled it will exit. func (c *Command) untilSucceeds(opName string, op func() error) error { @@ -982,10 +962,6 @@ func (c *Command) validateFlags() error { return errors.New("-consul-api-timeout must be set to a value greater than 0") } - //if c.flagVaultNamespace != "" && c.flagSecretsBackend != SecretsBackendTypeVault { - // return fmt.Errorf("-vault-namespace not supported for -secrets-backend=%q", c.flagSecretsBackend) - //} - return nil } @@ -1001,28 +977,6 @@ func loadTokenFromFile(tokenFile string) (string, error) { return strings.TrimSpace(string(tokenBytes)), nil } -func (c *Command) quitVaultAgent() { - if c.vaultClient == nil { - return - } - - // Tell the Vault agent sidecar to quit. Without this, the Job does not - // complete because the Vault agent does not stop. This retries because it - // does not know exactly when the Vault agent sidecar will start. - err := c.untilSucceeds("tell Vault agent to quit", func() error { - // TODO: RawRequest is deprecated, but there is also not a high level - // method for this in the Vault client. - // nolint:staticcheck // SA1004 ignore - _, err := c.vaultClient.RawRequest( - c.vaultClient.NewRequest("POST", "/agent/v1/quit"), - ) - return err - }) - if err != nil { - c.log.Error("Error telling Vault agent to quit", "error", err) - } -} - const ( consulDefaultNamespace = "default" consulDefaultPartition = "default" diff --git a/control-plane/subcommand/server-acl-init/command_ent_test.go b/control-plane/subcommand/server-acl-init/command_ent_test.go index fa56f3bb3a..e31b787e4b 100644 --- a/control-plane/subcommand/server-acl-init/command_ent_test.go +++ b/control-plane/subcommand/server-acl-init/command_ent_test.go @@ -222,6 +222,7 @@ func TestRun_ConnectInject_NamespaceMirroring(t *testing.T) { // a non-default partition. func TestRun_AnonymousToken_CreatedFromNonDefaultPartition(t *testing.T) { bootToken := "aaaaaaaa-bbbb-cccc-dddd-eeeeeeeeeeee" + tokenFile := common.WriteTempFile(t, bootToken) server := partitionedSetup(t, bootToken, "test") k8s := fake.NewSimpleClientset() setUpK8sServiceAccount(t, k8s, ns) @@ -230,7 +231,6 @@ func TestRun_AnonymousToken_CreatedFromNonDefaultPartition(t *testing.T) { cmd := Command{ UI: ui, clientset: k8s, - backend: &FakeSecretsBackend{bootstrapToken: bootToken}, } cmd.init() args := []string{ @@ -239,6 +239,7 @@ func TestRun_AnonymousToken_CreatedFromNonDefaultPartition(t *testing.T) { "-grpc-port=" + strings.Split(server.GRPCAddr, ":")[1], "-resource-prefix=" + resourcePrefix, "-k8s-namespace=" + ns, + "-bootstrap-token-file", tokenFile, "-allow-dns", "-partition=test", "-enable-namespaces", diff --git a/control-plane/subcommand/server-acl-init/command_test.go b/control-plane/subcommand/server-acl-init/command_test.go index ffe60af593..3111f58820 100644 --- a/control-plane/subcommand/server-acl-init/command_test.go +++ b/control-plane/subcommand/server-acl-init/command_test.go @@ -60,6 +60,13 @@ func TestRun_FlagValidation(t *testing.T) { "-resource-prefix=prefix"}, ExpErr: "unable to read token from file \"/notexist\": open /notexist: no such file or directory", }, + { + Flags: []string{ + "-bootstrap-token-file=/notexist", + "-addresses=localhost", + "-resource-prefix=prefix"}, + ExpErr: "unable to read token from file \"/notexist\": open /notexist: no such file or directory", + }, { Flags: []string{ "-addresses=localhost", @@ -400,6 +407,7 @@ func TestRun_TokensWithProvidedBootstrapToken(t *testing.T) { for _, c := range cases { t.Run(c.TestName, func(t *testing.T) { bootToken := "aaaaaaaa-bbbb-cccc-dddd-eeeeeeeeeeee" + tokenFile := common.WriteTempFile(t, bootToken) k8s, testAgent := completeBootstrappedSetup(t, bootToken) setUpK8sServiceAccount(t, k8s, ns) @@ -409,11 +417,11 @@ func TestRun_TokensWithProvidedBootstrapToken(t *testing.T) { cmd := Command{ UI: ui, clientset: k8s, - backend: &FakeSecretsBackend{bootstrapToken: bootToken}, } cmdArgs := append([]string{ "-timeout=1m", "-k8s-namespace", ns, + "-bootstrap-token-file", tokenFile, "-addresses", strings.Split(testAgent.TestServer.HTTPAddr, ":")[0], "-http-port", strings.Split(testAgent.TestServer.HTTPAddr, ":")[1], "-grpc-port", strings.Split(testAgent.TestServer.GRPCAddr, ":")[1], @@ -907,6 +915,7 @@ func TestRun_ErrorsOnDuplicateACLPolicy(t *testing.T) { // Create Consul with ACLs already bootstrapped so that we can // then seed it with our manually created policy. bootToken := "aaaaaaaa-bbbb-cccc-dddd-eeeeeeeeeeee" + tokenFile := common.WriteTempFile(t, bootToken) k8s, testAgent := completeBootstrappedSetup(t, bootToken) setUpK8sServiceAccount(t, k8s, ns) @@ -929,11 +938,11 @@ func TestRun_ErrorsOnDuplicateACLPolicy(t *testing.T) { cmd := Command{ UI: ui, clientset: k8s, - backend: &FakeSecretsBackend{bootstrapToken: bootToken}, } cmdArgs := []string{ "-timeout=1s", "-k8s-namespace", ns, + "-bootstrap-token-file", tokenFile, "-resource-prefix=" + resourcePrefix, "-k8s-namespace=" + ns, "-addresses", strings.Split(testAgent.TestServer.HTTPAddr, ":")[0], @@ -1444,223 +1453,272 @@ func TestRun_ClientPolicyAndBindingRuleRetry(t *testing.T) { // Test if there is an old bootstrap Secret we still try to create and set // server tokens. func TestRun_AlreadyBootstrapped(t *testing.T) { - k8s := fake.NewSimpleClientset() - - type APICall struct { - Method string - Path string + t.Parallel() + cases := map[string]bool{ + "token saved in k8s secret": true, + "token provided via file": false, } - var consulAPICalls []APICall - // Start the Consul server. - consulServer := httptest.NewServer(http.HandlerFunc(func(w http.ResponseWriter, r *http.Request) { - // Record all the API calls made. - consulAPICalls = append(consulAPICalls, APICall{ - Method: r.Method, - Path: r.URL.Path, - }) - switch r.URL.Path { - case "/v1/agent/self": - fmt.Fprintln(w, `{"Config": {"Datacenter": "dc1", "PrimaryDatacenter": "dc1"}}`) - case "/v1/acl/tokens": - fmt.Fprintln(w, `[]`) - case "/v1/acl/token": - fmt.Fprintln(w, `{}`) - case "/v1/acl/policy": - fmt.Fprintln(w, `{}`) - case "/v1/agent/token/acl_agent_token": - fmt.Fprintln(w, `{}`) - case "/v1/acl/auth-method": - fmt.Fprintln(w, `{}`) - case "/v1/acl/role/name/release-name-consul-client-acl-role": - w.WriteHeader(404) - case "/v1/acl/role": - fmt.Fprintln(w, `{}`) - case "/v1/acl/binding-rules": - fmt.Fprintln(w, `[]`) - case "/v1/acl/binding-rule": - fmt.Fprintln(w, `{}`) - default: - w.WriteHeader(500) - fmt.Fprintln(w, "Mock Server not configured for this route: "+r.URL.Path) - } - })) - defer consulServer.Close() + for name, tokenFromK8sSecret := range cases { + t.Run(name, func(t *testing.T) { + k8s := fake.NewSimpleClientset() - serverURL, err := url.Parse(consulServer.URL) - require.NoError(t, err) - port, err := strconv.Atoi(serverURL.Port()) - require.NoError(t, err) - setUpK8sServiceAccount(t, k8s, ns) + type APICall struct { + Method string + Path string + } + var consulAPICalls []APICall - cmdArgs := []string{ - "-timeout=500ms", - "-resource-prefix=" + resourcePrefix, - "-k8s-namespace=" + ns, - "-addresses=" + serverURL.Hostname(), - "-http-port=" + serverURL.Port(), - } + // Start the Consul server. + consulServer := httptest.NewServer(http.HandlerFunc(func(w http.ResponseWriter, r *http.Request) { + // Record all the API calls made. + consulAPICalls = append(consulAPICalls, APICall{ + Method: r.Method, + Path: r.URL.Path, + }) + switch r.URL.Path { + case "/v1/agent/self": + fmt.Fprintln(w, `{"Config": {"Datacenter": "dc1", "PrimaryDatacenter": "dc1"}}`) + case "/v1/acl/tokens": + fmt.Fprintln(w, `[]`) + case "/v1/acl/token": + fmt.Fprintln(w, `{}`) + case "/v1/acl/policy": + fmt.Fprintln(w, `{}`) + case "/v1/agent/token/acl_agent_token": + fmt.Fprintln(w, `{}`) + case "/v1/acl/auth-method": + fmt.Fprintln(w, `{}`) + case "/v1/acl/role/name/release-name-consul-client-acl-role": + w.WriteHeader(404) + case "/v1/acl/role": + fmt.Fprintln(w, `{}`) + case "/v1/acl/binding-rules": + fmt.Fprintln(w, `[]`) + case "/v1/acl/binding-rule": + fmt.Fprintln(w, `{}`) + default: + w.WriteHeader(500) + fmt.Fprintln(w, "Mock Server not configured for this route: "+r.URL.Path) + } + })) + defer consulServer.Close() - // Create the bootstrap secret. - _, err = k8s.CoreV1().Secrets(ns).Create( - context.Background(), - &v1.Secret{ - ObjectMeta: metav1.ObjectMeta{ - Name: resourcePrefix + "-bootstrap-acl-token", - Labels: map[string]string{common.CLILabelKey: common.CLILabelValue}, - }, - Data: map[string][]byte{ - "token": []byte("old-token"), - }, - }, - metav1.CreateOptions{}) - require.NoError(t, err) + serverURL, err := url.Parse(consulServer.URL) + require.NoError(t, err) + port, err := strconv.Atoi(serverURL.Port()) + require.NoError(t, err) + setUpK8sServiceAccount(t, k8s, ns) - // Run the command. - ui := cli.NewMockUi() - cmd := Command{ - UI: ui, - clientset: k8s, - watcher: test.MockConnMgrForIPAndPort(serverURL.Hostname(), port), - } + cmdArgs := []string{ + "-timeout=500ms", + "-resource-prefix=" + resourcePrefix, + "-k8s-namespace=" + ns, + "-addresses=" + serverURL.Hostname(), + "-http-port=" + serverURL.Port(), + } - responseCode := cmd.Run(cmdArgs) - require.Equal(t, 0, responseCode, ui.ErrorWriter.String()) + // Create the bootstrap secret. + if tokenFromK8sSecret { + _, err = k8s.CoreV1().Secrets(ns).Create( + context.Background(), + &v1.Secret{ + ObjectMeta: metav1.ObjectMeta{ + Name: resourcePrefix + "-bootstrap-acl-token", + Labels: map[string]string{common.CLILabelKey: common.CLILabelValue}, + }, + Data: map[string][]byte{ + "token": []byte("old-token"), + }, + }, + metav1.CreateOptions{}) + require.NoError(t, err) + } else { + // Write token to a file. + bootTokenFile, err := os.CreateTemp("", "") + require.NoError(t, err) + defer os.RemoveAll(bootTokenFile.Name()) - // Test that the Secret is the same. - secret, err := k8s.CoreV1().Secrets(ns).Get(context.Background(), resourcePrefix+"-bootstrap-acl-token", metav1.GetOptions{}) - require.NoError(t, err) - require.Contains(t, secret.Data, "token") - require.Equal(t, "old-token", string(secret.Data["token"])) + _, err = bootTokenFile.WriteString("old-token") + require.NoError(t, err) - // Test that the expected API calls were made. - require.Equal(t, []APICall{ - // We expect calls for updating the server policy, setting server tokens, - // and updating client policy. - { - "PUT", - "/v1/acl/policy", - }, - { - "GET", - "/v1/acl/tokens", - }, - { - "PUT", - "/v1/acl/token", - }, - { - "PUT", - "/v1/agent/token/agent", - }, - { - "PUT", - "/v1/agent/token/acl_agent_token", - }, - { - "GET", - "/v1/agent/self", - }, - { - "PUT", - "/v1/acl/auth-method", - }, - { - "PUT", - "/v1/acl/policy", - }, - { - "GET", - "/v1/acl/role/name/release-name-consul-client-acl-role", - }, - { - "PUT", - "/v1/acl/role", - }, - { - "GET", - "/v1/acl/binding-rules", - }, - { - "PUT", - "/v1/acl/binding-rule", - }, - }, consulAPICalls) + require.NoError(t, err) + cmdArgs = append(cmdArgs, "-bootstrap-token-file", bootTokenFile.Name()) + } + + // Run the command. + ui := cli.NewMockUi() + cmd := Command{ + UI: ui, + clientset: k8s, + watcher: test.MockConnMgrForIPAndPort(serverURL.Hostname(), port), + } + + responseCode := cmd.Run(cmdArgs) + require.Equal(t, 0, responseCode, ui.ErrorWriter.String()) + + // Test that the Secret is the same. + if tokenFromK8sSecret { + secret, err := k8s.CoreV1().Secrets(ns).Get(context.Background(), resourcePrefix+"-bootstrap-acl-token", metav1.GetOptions{}) + require.NoError(t, err) + require.Contains(t, secret.Data, "token") + require.Equal(t, "old-token", string(secret.Data["token"])) + } + + // Test that the expected API calls were made. + require.Equal(t, []APICall{ + // We expect calls for updating the server policy, setting server tokens, + // and updating client policy. + { + "PUT", + "/v1/acl/policy", + }, + { + "GET", + "/v1/acl/tokens", + }, + { + "PUT", + "/v1/acl/token", + }, + { + "PUT", + "/v1/agent/token/agent", + }, + { + "PUT", + "/v1/agent/token/acl_agent_token", + }, + { + "GET", + "/v1/agent/self", + }, + { + "PUT", + "/v1/acl/auth-method", + }, + { + "PUT", + "/v1/acl/policy", + }, + { + "GET", + "/v1/acl/role/name/release-name-consul-client-acl-role", + }, + { + "PUT", + "/v1/acl/role", + }, + { + "GET", + "/v1/acl/binding-rules", + }, + { + "PUT", + "/v1/acl/binding-rule", + }, + }, consulAPICalls) + }) + } } // Test if there is an old bootstrap Secret and the server token exists // that we don't try and recreate the token. func TestRun_AlreadyBootstrapped_ServerTokenExists(t *testing.T) { - // First set everything up with ACLs bootstrapped. - bootToken := "aaaaaaaa-bbbb-cccc-dddd-eeeeeeeeeeee" - k8s, testAgent := completeBootstrappedSetup(t, bootToken) - setUpK8sServiceAccount(t, k8s, ns) - - cmdArgs := []string{ - "-timeout=1m", - "-k8s-namespace", ns, - "-addresses", strings.Split(testAgent.TestServer.HTTPAddr, ":")[0], - "-http-port", strings.Split(testAgent.TestServer.HTTPAddr, ":")[1], - "-grpc-port", strings.Split(testAgent.TestServer.GRPCAddr, ":")[1], - "-resource-prefix", resourcePrefix, + t.Parallel() + cases := map[string]bool{ + "token saved in k8s secret": true, + "token provided via file": false, } - _, err := k8s.CoreV1().Secrets(ns).Create(context.Background(), &v1.Secret{ - ObjectMeta: metav1.ObjectMeta{ - Name: resourcePrefix + "-bootstrap-acl-token", - }, - Data: map[string][]byte{ - "token": []byte(bootToken), - }, - }, metav1.CreateOptions{}) - require.NoError(t, err) + for name, tokenInK8sSecret := range cases { + t.Run(name, func(t *testing.T) { - consulClient, err := api.NewClient(&api.Config{ - Address: testAgent.TestServer.HTTPAddr, - Token: bootToken, - }) - require.NoError(t, err) - ui := cli.NewMockUi() - cmd := Command{ - UI: ui, - clientset: k8s, - } + // First set everything up with ACLs bootstrapped. + bootToken := "aaaaaaaa-bbbb-cccc-dddd-eeeeeeeeeeee" + k8s, testAgent := completeBootstrappedSetup(t, bootToken) + setUpK8sServiceAccount(t, k8s, ns) - cmd.init() - // Create the server policy and token _before_ we run the command. - agentPolicyRules, err := cmd.agentRules() - require.NoError(t, err) - policy, _, err := consulClient.ACL().PolicyCreate(&api.ACLPolicy{ - Name: "agent-token", - Description: "Agent Token Policy", - Rules: agentPolicyRules, - }, nil) - require.NoError(t, err) - _, _, err = consulClient.ACL().TokenCreate(&api.ACLToken{ - Description: fmt.Sprintf("Server Token for %s", strings.Split(testAgent.TestServer.HTTPAddr, ":")[0]), - Policies: []*api.ACLTokenPolicyLink{ - { - Name: policy.Name, - }, - }, - }, nil) - require.NoError(t, err) + cmdArgs := []string{ + "-timeout=1m", + "-k8s-namespace", ns, + "-addresses", strings.Split(testAgent.TestServer.HTTPAddr, ":")[0], + "-http-port", strings.Split(testAgent.TestServer.HTTPAddr, ":")[1], + "-grpc-port", strings.Split(testAgent.TestServer.GRPCAddr, ":")[1], + "-resource-prefix", resourcePrefix, + } - // Run the command. - responseCode := cmd.Run(cmdArgs) - require.Equal(t, 0, responseCode, ui.ErrorWriter.String()) + if tokenInK8sSecret { + _, err := k8s.CoreV1().Secrets(ns).Create(context.Background(), &v1.Secret{ + ObjectMeta: metav1.ObjectMeta{ + Name: resourcePrefix + "-bootstrap-acl-token", + }, + Data: map[string][]byte{ + "token": []byte(bootToken), + }, + }, metav1.CreateOptions{}) + require.NoError(t, err) + } else { + // Write token to a file. + bootTokenFile, err := os.CreateTemp("", "") + require.NoError(t, err) + defer os.RemoveAll(bootTokenFile.Name()) - // Check that only one server token exists, i.e. it didn't create an - // extra token. - tokens, _, err := consulClient.ACL().TokenList(nil) - require.NoError(t, err) - count := 0 - for _, token := range tokens { - if len(token.Policies) == 1 && token.Policies[0].Name == policy.Name { - count++ - } + _, err = bootTokenFile.WriteString(bootToken) + require.NoError(t, err) + + require.NoError(t, err) + cmdArgs = append(cmdArgs, "-bootstrap-token-file", bootTokenFile.Name()) + } + + consulClient, err := api.NewClient(&api.Config{ + Address: testAgent.TestServer.HTTPAddr, + Token: bootToken, + }) + require.NoError(t, err) + ui := cli.NewMockUi() + cmd := Command{ + UI: ui, + clientset: k8s, + } + + cmd.init() + // Create the server policy and token _before_ we run the command. + agentPolicyRules, err := cmd.agentRules() + require.NoError(t, err) + policy, _, err := consulClient.ACL().PolicyCreate(&api.ACLPolicy{ + Name: "agent-token", + Description: "Agent Token Policy", + Rules: agentPolicyRules, + }, nil) + require.NoError(t, err) + _, _, err = consulClient.ACL().TokenCreate(&api.ACLToken{ + Description: fmt.Sprintf("Server Token for %s", strings.Split(testAgent.TestServer.HTTPAddr, ":")[0]), + Policies: []*api.ACLTokenPolicyLink{ + { + Name: policy.Name, + }, + }, + }, nil) + require.NoError(t, err) + + // Run the command. + responseCode := cmd.Run(cmdArgs) + require.Equal(t, 0, responseCode, ui.ErrorWriter.String()) + + // Check that only one server token exists, i.e. it didn't create an + // extra token. + tokens, _, err := consulClient.ACL().TokenList(nil) + require.NoError(t, err) + count := 0 + for _, token := range tokens { + if len(token.Policies) == 1 && token.Policies[0].Name == policy.Name { + count++ + } + } + require.Equal(t, 1, count) + }) } - require.Equal(t, 1, count) } // Test if -set-server-tokens is false (i.e. servers are disabled), we skip bootstrapping of the servers @@ -1670,6 +1728,7 @@ func TestRun_SkipBootstrapping_WhenServersAreDisabled(t *testing.T) { k8s := fake.NewSimpleClientset() bootToken := "aaaaaaaa-bbbb-cccc-dddd-eeeeeeeeeeee" + tokenFile := common.WriteTempFile(t, bootToken) type APICall struct { Method string @@ -1707,7 +1766,6 @@ func TestRun_SkipBootstrapping_WhenServersAreDisabled(t *testing.T) { UI: ui, clientset: k8s, watcher: test.MockConnMgrForIPAndPort(serverURL.Hostname(), port), - backend: &FakeSecretsBackend{bootstrapToken: bootToken}, } responseCode := cmd.Run([]string{ "-timeout=500ms", @@ -1715,6 +1773,7 @@ func TestRun_SkipBootstrapping_WhenServersAreDisabled(t *testing.T) { "-k8s-namespace=" + ns, "-addresses=" + serverURL.Hostname(), "-http-port=" + serverURL.Port(), + "-bootstrap-token-file=" + tokenFile, "-set-server-tokens=false", "-client=false", // disable client token, so there are fewer calls }) diff --git a/control-plane/subcommand/server-acl-init/k8s_secrets_backend.go b/control-plane/subcommand/server-acl-init/k8s_secrets_backend.go deleted file mode 100644 index 4e3efcf65b..0000000000 --- a/control-plane/subcommand/server-acl-init/k8s_secrets_backend.go +++ /dev/null @@ -1,62 +0,0 @@ -package serveraclinit - -import ( - "context" - "fmt" - - "github.com/hashicorp/consul-k8s/control-plane/subcommand/common" - apiv1 "k8s.io/api/core/v1" - k8serrors "k8s.io/apimachinery/pkg/api/errors" - metav1 "k8s.io/apimachinery/pkg/apis/meta/v1" - "k8s.io/client-go/kubernetes" -) - -const SecretsBackendTypeKubernetes SecretsBackendType = "kubernetes" - -type KubernetesSecretsBackend struct { - ctx context.Context - clientset kubernetes.Interface - k8sNamespace string - secretName string - secretKey string -} - -var _ SecretsBackend = (*KubernetesSecretsBackend)(nil) - -// BootstrapToken returns the existing bootstrap token if there is one by -// reading the Kubernetes Secret. If there is no bootstrap token yet, then -// it returns an empty string (not an error). -func (b *KubernetesSecretsBackend) BootstrapToken() (string, error) { - secret, err := b.clientset.CoreV1().Secrets(b.k8sNamespace).Get(b.ctx, b.secretName, metav1.GetOptions{}) - if err != nil { - if k8serrors.IsNotFound(err) { - return "", nil - } - return "", err - } - token, ok := secret.Data[b.secretKey] - if !ok { - return "", fmt.Errorf("secret %q does not have data key %q", b.secretName, b.secretKey) - } - return string(token), nil - -} - -// WriteBootstrapToken writes the given bootstrap token to the Kubernetes Secret. -func (b *KubernetesSecretsBackend) WriteBootstrapToken(bootstrapToken string) error { - secret := &apiv1.Secret{ - ObjectMeta: metav1.ObjectMeta{ - Name: b.secretName, - Labels: map[string]string{common.CLILabelKey: common.CLILabelValue}, - }, - Data: map[string][]byte{ - b.secretKey: []byte(bootstrapToken), - }, - } - _, err := b.clientset.CoreV1().Secrets(b.k8sNamespace).Create(b.ctx, secret, metav1.CreateOptions{}) - return err -} - -func (b *KubernetesSecretsBackend) BootstrapTokenSecretName() string { - return b.secretName -} diff --git a/control-plane/subcommand/server-acl-init/secrets_backend.go b/control-plane/subcommand/server-acl-init/secrets_backend.go deleted file mode 100644 index 4b4d5c2fc4..0000000000 --- a/control-plane/subcommand/server-acl-init/secrets_backend.go +++ /dev/null @@ -1,18 +0,0 @@ -package serveraclinit - -type SecretsBackendType string - -type SecretsBackend interface { - // BootstrapToken fetches the bootstrap token from the backend. If the - // token is not found or empty, implementations should return an empty - // string (not an error). - BootstrapToken() (string, error) - - // WriteBootstrapToken writes the given bootstrap token to the backend. - // Implementations of this method do not need to retry the write until - // successful. - WriteBootstrapToken(string) error - - // BootstrapTokenSecretName returns the name of the bootstrap token secret. - BootstrapTokenSecretName() string -} diff --git a/control-plane/subcommand/server-acl-init/servers.go b/control-plane/subcommand/server-acl-init/servers.go index 01e9a58145..2dc8f8ab67 100644 --- a/control-plane/subcommand/server-acl-init/servers.go +++ b/control-plane/subcommand/server-acl-init/servers.go @@ -1,6 +1,7 @@ package serveraclinit import ( + "errors" "fmt" "net" "net/http" @@ -8,30 +9,29 @@ import ( "time" "github.com/hashicorp/consul/api" + apiv1 "k8s.io/api/core/v1" + metav1 "k8s.io/apimachinery/pkg/apis/meta/v1" "github.com/hashicorp/consul-k8s/control-plane/consul" + "github.com/hashicorp/consul-k8s/control-plane/subcommand/common" ) // bootstrapServers bootstraps ACLs and ensures each server has an ACL token. -// If a bootstrap is found in the secrets backend, then skip ACL bootstrapping. -// Otherwise, bootstrap ACLs and write the bootstrap token to the secrets backend. -func (c *Command) bootstrapServers(serverAddresses []net.IPAddr, backend SecretsBackend) (string, error) { +// If bootstrapToken is not empty then ACLs are already bootstrapped. +func (c *Command) bootstrapServers(serverAddresses []net.IPAddr, bootstrapToken, bootTokenSecretName string) (string, error) { // Pick the first server address to connect to for bootstrapping and set up connection. firstServerAddr := fmt.Sprintf("%s:%d", serverAddresses[0].IP.String(), c.consulFlags.HTTPPort) - bootstrapToken, err := backend.BootstrapToken() - if err != nil { - return "", fmt.Errorf("Unexpected error fetching bootstrap token secret: %w", err) - } + if bootstrapToken == "" { + c.log.Info("No bootstrap token from previous installation found, continuing on to bootstrapping") - if bootstrapToken != "" { - c.log.Info("Found bootstrap token in secrets backend", "secret", backend.BootstrapTokenSecretName()) - } else { - c.log.Info("No bootstrap token found in secrets backend, continuing to ACL bootstrapping", "secret", backend.BootstrapTokenSecretName()) - bootstrapToken, err = c.bootstrapACLs(firstServerAddr, backend) + var err error + bootstrapToken, err = c.bootstrapACLs(firstServerAddr, bootTokenSecretName) if err != nil { return "", err } + } else { + c.log.Info(fmt.Sprintf("ACLs already bootstrapped - retrieved bootstrap token from Secret %q", bootTokenSecretName)) } // We should only create and set server tokens when servers are running within this cluster. @@ -47,7 +47,7 @@ func (c *Command) bootstrapServers(serverAddresses []net.IPAddr, backend Secrets // bootstrapACLs makes the ACL bootstrap API call and writes the bootstrap token // to a kube secret. -func (c *Command) bootstrapACLs(firstServerAddr string, backend SecretsBackend) (string, error) { +func (c *Command) bootstrapACLs(firstServerAddr, bootTokenSecretName string) (string, error) { config := c.consulFlags.ConsulClientConfig().APIClientConfig config.Address = firstServerAddr // Exempting this particular use of the http client from using global.consulAPITimeout @@ -78,12 +78,9 @@ func (c *Command) bootstrapACLs(firstServerAddr string, backend SecretsBackend) // Check if already bootstrapped. if strings.Contains(err.Error(), "Unexpected response code: 403") { - unrecoverableErr = fmt.Errorf( - "ACLs already bootstrapped but unable to find the bootstrap token in the secrets backend."+ - " We can't proceed without a bootstrap token."+ - " Store a token with `acl:write` permission in the secret %q.", - backend.BootstrapTokenSecretName(), - ) + unrecoverableErr = errors.New("ACLs already bootstrapped but the ACL token was not written to a Kubernetes secret." + + " We can't proceed because the bootstrap token is lost." + + " You must reset ACLs.") return nil } @@ -101,12 +98,21 @@ func (c *Command) bootstrapACLs(firstServerAddr string, backend SecretsBackend) return "", err } - // Write bootstrap token to the secrets backend. - err = c.untilSucceeds(fmt.Sprintf("writing bootstrap Secret %q", backend.BootstrapTokenSecretName()), + // Write bootstrap token to a Kubernetes secret. + err = c.untilSucceeds(fmt.Sprintf("writing bootstrap Secret %q", bootTokenSecretName), func() error { - return backend.WriteBootstrapToken(bootstrapToken) - }, - ) + secret := &apiv1.Secret{ + ObjectMeta: metav1.ObjectMeta{ + Name: bootTokenSecretName, + Labels: map[string]string{common.CLILabelKey: common.CLILabelValue}, + }, + Data: map[string][]byte{ + common.ACLTokenSecretKey: []byte(bootstrapToken), + }, + } + _, err := c.clientset.CoreV1().Secrets(c.flagK8sNamespace).Create(c.ctx, secret, metav1.CreateOptions{}) + return err + }) return bootstrapToken, err } diff --git a/control-plane/subcommand/server-acl-init/test_fake_secrets_backend.go b/control-plane/subcommand/server-acl-init/test_fake_secrets_backend.go deleted file mode 100644 index 5c9a63f1a5..0000000000 --- a/control-plane/subcommand/server-acl-init/test_fake_secrets_backend.go +++ /dev/null @@ -1,20 +0,0 @@ -package serveraclinit - -type FakeSecretsBackend struct { - bootstrapToken string -} - -func (b *FakeSecretsBackend) BootstrapToken() (string, error) { - return b.bootstrapToken, nil -} - -func (*FakeSecretsBackend) BootstrapTokenSecretName() string { - return "fake-bootstrap-token" -} - -func (b *FakeSecretsBackend) WriteBootstrapToken(token string) error { - b.bootstrapToken = token - return nil -} - -var _ SecretsBackend = (*FakeSecretsBackend)(nil) diff --git a/control-plane/subcommand/server-acl-init/vault_secrets_backend.go b/control-plane/subcommand/server-acl-init/vault_secrets_backend.go deleted file mode 100644 index 2706567878..0000000000 --- a/control-plane/subcommand/server-acl-init/vault_secrets_backend.go +++ /dev/null @@ -1,66 +0,0 @@ -package serveraclinit - -import ( - "fmt" - - "github.com/hashicorp/vault/api" -) - -const SecretsBackendTypeVault SecretsBackendType = "vault" - -type VaultSecretsBackend struct { - vaultClient *api.Client - secretName string - secretKey string -} - -var _ SecretsBackend = (*VaultSecretsBackend)(nil) - -// BootstrapToken returns the bootstrap token stored in Vault. -// If not found this returns an empty string (not an error). -func (b *VaultSecretsBackend) BootstrapToken() (string, error) { - secret, err := b.vaultClient.Logical().Read(b.secretName) - if err != nil { - return "", err - } - if secret == nil || secret.Data == nil { - // secret not found or empty. - return "", nil - } - // Grab secret.Data["data"][secretKey]. - dataRaw, found := secret.Data["data"] - if !found { - return "", nil - } - data, ok := dataRaw.(map[string]interface{}) - if !ok { - return "", nil - } - tokRaw, found := data[b.secretKey] - if !found { - return "", nil - } - if tok, ok := tokRaw.(string); ok { - return tok, nil - } - return "", fmt.Errorf("Unexpected data. To resolve this, "+ - "`vault kv put %[1]s=` if Consul is already ACL bootstrapped. "+ - "If not ACL bootstrapped, `vault kv put %[1]s=\"\"`", b.secretKey, b.secretKey) -} - -// BootstrapTokenSecretName returns the name of the bootstrap token secret. -func (b *VaultSecretsBackend) BootstrapTokenSecretName() string { - return b.secretName -} - -// WriteBootstrapToken writes the bootstrap token to Vault. -func (b *VaultSecretsBackend) WriteBootstrapToken(bootstrapToken string) error { - _, err := b.vaultClient.Logical().Write(b.secretName, - map[string]interface{}{ - "data": map[string]interface{}{ - b.secretKey: bootstrapToken, - }, - }, - ) - return err -} diff --git a/control-plane/version/version.go b/control-plane/version/version.go index 8ae06829bb..19d9b3f112 100644 --- a/control-plane/version/version.go +++ b/control-plane/version/version.go @@ -14,12 +14,12 @@ var ( // // Version must conform to the format expected by // github.com/hashicorp/go-version for tests to work. - Version = "1.2.0" + Version = "1.0.6" // A pre-release marker for the version. If this is "" (empty string) // then it means that it is a final release. Otherwise, this is a pre-release // such as "dev" (in development), "beta", "rc1", etc. - VersionPrerelease = "dev" + VersionPrerelease = "" ) // GetHumanVersion composes the parts of the version in a way that's suitable diff --git a/docs/admin-partitions-with-acls.md b/docs/admin-partitions-with-acls.md new file mode 100644 index 0000000000..fb282fa38d --- /dev/null +++ b/docs/admin-partitions-with-acls.md @@ -0,0 +1,98 @@ +## Installing Admin Partitions with ACLs enabled + +To enable ACLs on the server cluster use the following config: +```yaml +global: + enableConsulNamespaces: true + tls: + enabled: true + image: hashicorp/consul-enterprise:1.11.1 + adminPartitions: + enabled: true + acls: + manageSystemACLs: true +server: + exposeGossipAndRPCPorts: true + enterpriseLicense: + secretName: license + secretKey: key + replicas: 1 +connectInject: + enabled: true + transparentProxy: + defaultEnabled: false + consulNamespaces: + mirroringK8S: true +controller: + enabled: true +meshGateway: + enabled: true +``` + +Identify the LoadBalancer External IP of the `partition-service` +```bash +kubectl get svc consul-consul-partition-service -o json | jq -r '.status.loadBalancer.ingress[0].ip' +``` + +Migrate the TLS CA credentials from the server cluster to the workload clusters +```bash +kubectl get secret consul-consul-ca-key --context "server-context" -o json | kubectl apply --context "workload-context" -f - +kubectl get secret consul-consul-ca-cert --context "server-context" -o json | kubectl apply --context "workload-context" -f - +``` + +Migrate the Partition token from the server cluster to the workload clusters +```bash +kubectl get secret consul-consul-partitions-acl-token --context "server-context" -o json | kubectl apply --context "workload-context" -f - +``` + +Identify the Kubernetes AuthMethod URL of the workload cluster to use as the `k8sAuthMethodHost`: +```bash +kubectl config view -o "jsonpath={.clusters[?(@.name=='workload-cluster-name')].cluster.server}" +``` + +Configure the workload cluster using the following: + +```yaml +global: + enabled: false + enableConsulNamespaces: true + image: hashicorp/consul-enterprise:1.11.1 + adminPartitions: + enabled: true + name: "partition-name" + tls: + enabled: true + caCert: + secretName: consul-consul-ca-cert + secretKey: tls.crt + caKey: + secretName: consul-consul-ca-key + secretKey: tls.key + acls: + manageSystemACLs: true + bootstrapToken: + secretName: consul-consul-partitions-acl-token + secretKey: token +server: + enterpriseLicense: + secretName: license + secretKey: key +externalServers: + enabled: true + hosts: [ "loadbalancer IP" ] + tlsServerName: server.dc1.consul + k8sAuthMethodHost: "authmethod-host IP" +client: + enabled: true + exposeGossipPorts: true + join: [ "loadbalancer IP" ] +connectInject: + enabled: true + consulNamespaces: + mirroringK8S: true +controller: + enabled: true +meshGateway: + enabled: true +``` +This should create clusters that have Admin Partitions deployed on them with ACLs enabled. diff --git a/hack/aws-acceptance-test-cleanup/go.mod b/hack/aws-acceptance-test-cleanup/go.mod index ac4f7b0d1a..13e8f48909 100644 --- a/hack/aws-acceptance-test-cleanup/go.mod +++ b/hack/aws-acceptance-test-cleanup/go.mod @@ -1,6 +1,6 @@ module github.com/hashicorp/consul-helm/hack/aws-acceptance-test-cleanup -go 1.20 +go 1.19 require ( github.com/aws/aws-sdk-go v1.38.63 diff --git a/hack/copy-crds-to-chart/go.mod b/hack/copy-crds-to-chart/go.mod index c224f8f244..73b1f10306 100644 --- a/hack/copy-crds-to-chart/go.mod +++ b/hack/copy-crds-to-chart/go.mod @@ -1,3 +1,3 @@ module github.com/hashicorp/consul-k8s/hack/copy-crds-to-chart -go 1.20 +go 1.19 diff --git a/hack/copy-crds-to-chart/main.go b/hack/copy-crds-to-chart/main.go index 7085bdb9e6..7276c468f8 100644 --- a/hack/copy-crds-to-chart/main.go +++ b/hack/copy-crds-to-chart/main.go @@ -9,14 +9,6 @@ import ( "strings" ) -var ( - // HACK IT! - requiresPeering = map[string]struct{}{ - "consul.hashicorp.com_peeringacceptors.yaml": {}, - "consul.hashicorp.com_peeringdialers.yaml": {}, - } -) - func main() { if len(os.Args) != 1 { fmt.Println("Usage: go run ./...") @@ -51,13 +43,8 @@ func realMain(helmPath string) error { // Strip leading newline. contents = strings.TrimPrefix(contents, "\n") - if _, ok := requiresPeering[info.Name()]; ok { - // Add {{- if and .Values.connectInject.enabled .Values.global.peering.enabled }} {{- end }} wrapper. - contents = fmt.Sprintf("{{- if and .Values.connectInject.enabled .Values.global.peering.enabled }}\n%s{{- end }}\n", contents) - } else { - // Add {{- if .Values.connectInject.enabled }} {{- end }} wrapper. - contents = fmt.Sprintf("{{- if .Values.connectInject.enabled }}\n%s{{- end }}\n", contents) - } + // Add {{- if .Values.connectInject.enabled }} {{- end }} wrapper. + contents = fmt.Sprintf("{{- if .Values.connectInject.enabled }}\n%s{{- end }}\n", contents) // Add labels, this is hacky because we're relying on the line number // but it means we don't need to regex or yaml parse. diff --git a/hack/helm-reference-gen/go.mod b/hack/helm-reference-gen/go.mod index 36e1ff3a8d..7e41675f18 100644 --- a/hack/helm-reference-gen/go.mod +++ b/hack/helm-reference-gen/go.mod @@ -1,6 +1,6 @@ module github.com/hashicorp/consul-k8s/hack/helm-reference-gen -go 1.20 +go 1.19 require ( github.com/stretchr/testify v1.6.1 diff --git a/hack/helm-reference-gen/main.go b/hack/helm-reference-gen/main.go index ae9b17610e..5f23143caa 100644 --- a/hack/helm-reference-gen/main.go +++ b/hack/helm-reference-gen/main.go @@ -159,14 +159,11 @@ func GenerateDocs(yamlStr string) (string, error) { return "", err } - docsStr := strings.Join(children, "\n\n") - docsStr = strings.ReplaceAll(docsStr, "[Enterprise Only]", "") - // Remove https://developer.hashicorp.com prefix from links because docs linting requires it. - docsStr = strings.ReplaceAll(docsStr, "https://developer.hashicorp.com/", "/") + enterpriseSubst := strings.ReplaceAll(strings.Join(children, "\n\n"), "[Enterprise Only]", "") // Add table of contents. toc := generateTOC(node) - return toc + "\n\n" + docsStr + "\n", nil + return toc + "\n\n" + enterpriseSubst + "\n", nil } // Parse parses yamlStr into a tree of DocNode's.