Security Global Forum

 View Only

Secrets Store CSI Driver with external HashiCorp Vault and Kubernetes authentication

By Ewan Chalmers posted Tue October 08, 2024 07:57 AM

  

This post looks at how an integration of the Secrets Store CSI Driver in Kubernetes with a cluster-external HashiCorp Vault server can be configured to use the Vault Kubernetes auth method.

  • HashiCorp VaultA popular open source secrets store. 
  • Secrets Store CSI Driver: Integrates secrets stores with Kubernetes via a Container Storage Interface (CSI) volume.

Outline

In the Kubernetes cluster, a service account and service account token secret are created and linked to a ClusterRoleBinding granting access to the Token Review API.

In the Vault server, the details of the Kubernetes host and a token review JWT are configured in a Kubernetes authentication method.

Overview of integration elements

Set up

See this post for setup of Secrets Store CSI Driver and HashiCorp Vault.

That post was agnostic about the location of the Vault server. It could be in-cluster or external.  For the purpose of this post, the Vault server should be external to the Kubernetes cluster on which the CSI driver runs alongside your workloads. For example, you could run the server in dev mode on your workstation.

Kubernetes configuration

Creating Service Account, service account token Secret and ClusterRoleBinding.

vault-auth.yml

apiVersion: v1
kind: ServiceAccount
metadata:
  name: vault-auth
---
apiVersion: rbac.authorization.k8s.io/v1
kind: ClusterRoleBinding
metadata:
  name: role-tokenreview-binding
roleRef:
  apiGroup: rbac.authorization.k8s.io
  kind: ClusterRole
  name: system:auth-delegator
subjects:
- kind: ServiceAccount
  name: vault-auth
  namespace: default
---
apiVersion: v1
kind: Secret
metadata:
  name: vault-auth
  annotations:
    kubernetes.io/service-account.name: vault-auth
type: kubernetes.io/service-account-token

Everything above is standard/template apart from the name of the secret (here, 'vault-auth') and the namespace of the workload and service account (here, 'default').

kubectl apply -f ./vault-auth.yml

Vault configuration

Configuring an authentication method to use the Kubernetes cluster's JWT Verifier.

TOKEN_REVIEW_JWT=$(kubectl get secret vault-auth -o 'go-template={{ .data.token }}' | base64 --decode)

KUBE_CA_CERT=$(kubectl config view --raw --minify --flatten \
  --output='jsonpath={.clusters[].cluster.certificate-authority-data}' | base64 --decode)

KUBE_HOST=$(kubectl config view --raw --minify --flatten \
  --output='jsonpath={.clusters[].cluster.server}')

KUBE_ISSUER=$(kubectl get --raw /.well-known/openid-configuration | jq -r .issuer)
    
vault write auth/kubernetes/config \
      token_reviewer_jwt="$TOKEN_REVIEW_JWT" \
      kubernetes_host="$KUBE_HOST" \
      kubernetes_ca_cert="$KUBE_CA_CERT" \
      issuer="$KUBE_ISSUER"

PS

Your Vault server can be configured to authenticate with multiple Kubernetes servers. You would write an authentication method configuration for each.

vault auth enable -path=kubernetes-mycluster kubernetes
vault write auth/kubernetes-mycluster/config ...

References

0 comments
15 views

Permalink