Skip to content

How to Pass Kubernetes Secrets as Environment Variables

DodaTech 2 min read

In this tutorial, you'll learn about How to Pass Kubernetes Secrets as Environment Variables. We cover key concepts, practical examples, and best practices.

The Problem

Your pod needs database credentials, API keys, or other sensitive values, but hardcoding them in the pod spec or configmap exposes secrets in plain text. env entries with literal values are visible in kubectl describe pod.

Quick Fix

Step 1: Create a Secret

Store sensitive data as a Kubernetes Secret:

kubectl create secret generic db-credentials \
  --from-literal=DB_USER=admin \
  --from-literal=DB_PASSWORD=s3cret
secret/db-credentials created

Step 2: Inject all keys as environment variables

Use envFrom to load every key from the Secret:

apiVersion: v1
kind: Pod
metadata:
  name: app-pod
spec:
  containers:
    - name: app
      image: my-app:latest
      envFrom:
        - secretRef:
            name: db-credentials

Each key in the Secret becomes an environment variable in the container.

Step 3: Inject specific keys selectively

Use valueFrom to pick individual keys:

apiVersion: v1
kind: Pod
metadata:
  name: app-pod
spec:
  containers:
    - name: app
      image: my-app:latest
      env:
        - name: DATABASE_USER
          valueFrom:
            secretKeyRef:
              name: db-credentials
              key: DB_USER
        - name: DATABASE_PASSWORD
          valueFrom:
            secretKeyRef:
              name: db-credentials
              key: DB_PASSWORD

Step 4: Verify the variables in the pod

Check that the environment variables are set:

kubectl exec app-pod -- env | grep DB_
DB_USER=admin
DB_PASSWORD=s3cret

Step 5: Create Secret from a file

Store an entire file as a Secret value:

kubectl create secret generic tls-cert \
  --from-file=./tls.crt \
  --from-file=./tls.key

Alternative Solutions

Mount secrets as files instead of environment variables

Some applications prefer reading secrets from files:

spec:
  containers:
    - name: app
      volumeMounts:
        - name: secret-volume
          mountPath: /etc/secrets
          readOnly: true
  volumes:
    - name: secret-volume
      secret:
        secretName: db-credentials

Use external secrets operator

Sync secrets from AWS Secrets Manager or HashiCorp Vault:

kubectl apply -f https://raw.githubusercontent.com/external-secrets/main/deploy/crds.yaml

Common Mistakes to Avoid

Using secrets in environment variables for large values. Environment variables have size limits. Mount secrets as files for values over 1MB.

Checking secrets into version control. Never commit raw secret definitions. Use Sealed Secrets, External Secrets, or Helm with external values.

Not rotating secrets regularly. A leaked secret stays valid until changed. Use automated rotation with tools like External Secrets Operator.

Pro Tips

Use SealedSecrets for GitOps workflows. Encrypt secrets into SealedSecrets CRDs that can be safely stored in Git and decrypted only by the controller.

Use External Secrets Operator for cloud-native secrets. Sync secrets from AWS Secrets Manager, GCP Secret Manager, or Azure Key Vault directly into Kubernetes.

Use secrets store CSI driver for mounted secrets. The CSI driver mounts secrets from external stores as volumes without storing them in etcd.

Prevention

  • Never hardcode secrets in pod specs or ConfigMaps.
  • Use kubectl create secret instead of literal YAML to avoid base64-encoded secrets in version control.
  • Use a secrets management tool like HashiCorp Vault or Sealed Secrets for production workflows.

Built by the developers of DodaTech

Doda Browser, DodaZIP & Durga Antivirus Pro