Configure a GCP Secret Manager Vault

Related Documentation
Related Resources
Minimum Version
Kong Ingress Controller - 3.1
TL;DR

Create a KongVault CRD and then use the vault:// reference in your plugin configuration

Prerequisites

If you don’t have a Konnect account, you can get started quickly with our onboarding wizard.

  1. The following Konnect items are required to complete this tutorial:
    • Personal access token (PAT): Create a new personal access token by opening the Konnect PAT page and selecting Generate Token.
  2. Set the personal access token as an environment variable:

    export KONNECT_TOKEN='YOUR KONNECT TOKEN'
    

To add Secret Manager as a Vault backend to Kong Gateway, you must configure the following:

  1. In the Google Cloud console, create a project and name it test-gateway-vault.
  2. On the Secret Manager page, create a secret called test-secret with the following JSON content:
     secret
    
  3. Create a service account key and grant IAM permissions:
    1. In the Service Account settings, click the test-gateway-vault project and then click the email address of the service account that you want to create a key for.
    2. From the Keys tab, create a new key from the add key menu and select JSON for the key type.
    3. Save the JSON file you downloaded.
    4. From the IAM & Admin settings, click the edit icon next to the service account to grant access to the Secret Manager Secret Accessor role for your service account. icon_url: /assets/icons/google-cloud.svg

Set the environment variables needed to authenticate to Google Cloud:

export GCP_SERVICE_ACCOUNT=$(cat /path/to/file/service-account.json | jq -c)
export KONG_LUA_SSL_TRUSTED_CERTIFICATE='system'

Note that these variables need to be passed when creating your Data Plane container.

Use the Konnect API to create a new CLUSTER_TYPE_K8S_INGRESS_CONTROLLER Control Plane:

CONTROL_PLANE_DETAILS=$(curl -X POST "https://us.api.konghq.com/v2/control-planes" \
     -H "Authorization: Bearer $KONNECT_TOKEN" \
     --json '{
       "name": "My KIC CP",
       "cluster_type": "CLUSTER_TYPE_K8S_INGRESS_CONTROLLER"
     }')

We’ll need the id and telemetry_endpoint for the values.yaml file later. Save them as environment variables:

CONTROL_PLANE_ID=$(echo $CONTROL_PLANE_DETAILS | jq -r .id)
CONTROL_PLANE_TELEMETRY=$(echo $CONTROL_PLANE_DETAILS | jq -r '.config.telemetry_endpoint | sub("https://";"")')

Create mTLS certificates

Kong Ingress Controller talks to Konnect over a connected secured with TLS certificates.

Generate a new certificate using openssl:

openssl req -new -x509 -nodes -newkey rsa:2048 -subj "/CN=kongdp/C=US" -keyout ./tls.key -out ./tls.crt

The certificate needs to be a single line string to send it to the Konnect API with curl. Use awk to format the certificate:

export CERT=$(awk 'NF {sub(/\r/, ""); printf "%s\\n",$0;}' tls.crt);

Next, upload the certificate to Konnect:

curl -X POST "https://us.api.konghq.com/v2/control-planes/$CONTROL_PLANE_ID/dp-client-certificates" \
     -H "Authorization: Bearer $KONNECT_TOKEN" \
     --json '{
       "cert": "'$CERT'"
     }'

Finally, store the certificate in a Kubernetes secret so that Kong Ingress Controller can read it:

kubectl create namespace kong -o yaml --dry-run=client | kubectl apply -f -
kubectl create secret tls konnect-client-tls -n kong --cert=./tls.crt --key=./tls.key
  1. Add the Kong Helm charts:

    helm repo add kong https://charts.konghq.com
    helm repo update
    
  2. Create a file named license.json containing your Kong Gateway Enterprise license and store it in a Kubernetes secret:

    kubectl create namespace kong --dry-run=client -o yaml | kubectl apply -f -
    kubectl create secret generic kong-enterprise-license --from-file=license=./license.json -n kong
    
  3. Create a values.yaml file:

    cat <<EOF > values.yaml
    gateway:
      image:
        repository: kong/kong-gateway
      env:
        LUA_SSL_TRUSTED_CERTIFICATE: 'system'
        LICENSE_DATA:
          valueFrom:
            secretKeyRef:
              name: kong-enterprise-license
              key: license
      customEnv:
        GCP_SERVICE_ACCOUNT: '$GCP_SERVICE_ACCOUNT'
    EOF
    
  4. Install Kong Ingress Controller using Helm:

    helm install kong kong/ingress -n kong --create-namespace --values ./values.yaml
    

Create a KongVault entity

Kong Ingress Controller uses the KongVault entity to configure the connection to a Vault. As we’re running Hashicorp Vault in dev mode, we can use the root token to access the Vault:

echo "
apiVersion: configuration.konghq.com/v1alpha1
kind: KongVault
metadata:
  name: gcp-vault
  namespace: kong
  annotations:
    kubernetes.io/ingress.class: kong
spec:
  backend: gcp
  prefix: gcp-vault
  description: Storing secrets in GCP Secrets Manager
  config:
    project_id: summit-demo-2022
" | kubectl apply -f -

We can now access secrets in this vault using the vault://gcp-vault/$KEY syntax. The gcp-vault prefix matches the prefix field in the KongVault resource.

Validate your configuration

To validate that the secret was stored correctly in AWS Secrets Manager, you can call a secret from your vault using the kong vault get command within the Data Plane Pod.

kubectl exec -n kong -it deployment/kong-gateway -c proxy -- kong vault get {vault://gcp-vault/test-secret}
kubectl exec -n kong -it deployment/kong-gateway -c proxy -- kong vault get {vault://gcp-vault/test-secret}

If the vault was configured correctly, this command should return the value of the secret. You can use {vault://gcp-vault/test-secret} to reference the secret in any referenceable field.

Cleanup

If you created new Google Cloud resources for this tutorial, make sure to delete them to avoid unnecessary charges.

helm uninstall kong -n kong
Something wrong?

Help us make these docs great!

Kong Developer docs are open source. If you find these useful and want to make them better, contribute today!