13

I use one secret to store multiple data items like this:

apiVersion: v1
kind: Secret
metadata:
  name: my-certs
  namespace: my-namespace
data:
  keystore.p12: LMNOPQRSTUV
  truststore.p12: ABCDEFGHIJK

In my Deployment I mount them into files like this:

volumeMounts:
- mountPath: /app/truststore.p12
    name: truststore-secret
    subPath: truststore.p12
- mountPath: /app/keystore.p12
    name: keystore-secret
    subPath: keystore.p12
volumes:
- name: truststore-secret
secret:
    items:
    - key: truststore.p12
    path: truststore.p12
    secretName: my-certs
- name: keystore-secret
secret:
    items:
    - key: keystore.p12
    path: keystore.p12
    secretName: my-certs

This works as expected but I am wondering whether I can achieve the same result of mounting those two secret as files with less Yaml? For example volumes use items but I could not figure out how to use one volume with multiple items and mount those.

Hedge
  • 16,142
  • 42
  • 141
  • 246
  • Does this answer your question? [Kubernetes multiple secrets](https://stackoverflow.com/questions/31937955/kubernetes-multiple-secrets) – BMW Jan 22 '20 at 10:14

1 Answers1

8

Yes, you can reduce your yaml with Projected Volume.

Currently, secret, configMap, downwardAPI, and serviceAccountToken volumes can be projected.

TL;DR use this structure in your Deployment:

spec:
  containers:
  - name: {YOUR_CONTAINER_NAME}
    volumeMounts:
    - name: multiple-secrets-volume
      mountPath: "/app"
      readOnly: true
  volumes:
  - name: multiple-secrets-volume
    projected:
      sources:
      - secret:
          name: my-certs

And here's the full reproduction of your case, first I registered your my-certs secret:

user@minikube:~/secrets$ kubectl get secret my-certs -o yaml
apiVersion: v1
data:
  keystore.p12: TE1OT1BRUlNUVVY=
  truststore.p12: QUJDREVGR0hJSks=
kind: Secret
metadata:
  annotations:
    kubectl.kubernetes.io/last-applied-configuration: |
      {"apiVersion":"v1","data":{"keystore.p12":"TE1OT1BRUlNUVVY=","truststore.p12":"QUJDREVGR0hJSks="},"kind":"Secret","metadata":{"annotations":{},"name":"my-certs","namespace":"default"}}
  creationTimestamp: "2020-01-22T10:43:51Z"
  name: my-certs
  namespace: default
  resourceVersion: "2759005"
  selfLink: /api/v1/namespaces/default/secrets/my-certs
  uid: d785045c-2931-434e-b6e1-7e090fdd6ff4

Then created a pod to test the access to the secret, this is projected.yaml:

user@minikube:~/secrets$ cat projected.yaml 
apiVersion: v1
kind: Pod
metadata:
  name: test-projected-volume
spec:
  containers:
  - name: test-projected-volume
    image: busybox
    args:
    - sleep
    - "86400"
    volumeMounts:
    - name: multiple-secrets-volume
      mountPath: "/app"
      readOnly: true
  volumes:
  - name: multiple-secrets-volume
    projected:
      sources:
      - secret:
          name: my-certs

user@minikube:~/secrets$ kubectl apply -f projected.yaml 
pod/test-projected-volume created

Then tested the access to the keys:

user@minikube:~/secrets$ kubectl exec -it test-projected-volume -- /bin/sh
/ # ls
app   bin   dev   etc   home  proc  root  sys   tmp   usr   var
/ # cd app
/app # ls
keystore.p12    truststore.p12
/app # cat keystore.p12 
LMNOPQRSTUV/app # 
/app # cat truststore.p12 
ABCDEFGHIJK/app # 
/app # exit

You have the option to use a single secret with many data lines, as you requested or you can use many secrets from your base in your deployment in the following model:

    volumeMounts:
    - name: all-in-one
      mountPath: "/projected-volume"
      readOnly: true
  volumes:
  - name: all-in-one
    projected:
      sources:
      - secret:
          name: SECRET_1
      - secret:
          name: SECRET_2
Will R.O.F.
  • 3,814
  • 1
  • 9
  • 19
  • 1
    Thanks. That works for pod.yaml. But if we use it in deployment.yaml it is giving "error: error validating "test.yaml": error validating data: ValidationError(Deployment.spec.template.spec.volumes[0].projected.sources[0]): unknown field "name" in io.k8s.api.core.v1.VolumeProjection; if you choose to ignore these errors, turn validation off with --validate=false" Do you know how to handle that? – Alex Dec 18 '20 at 14:48
  • 1
    @YuraHoy I had the same issue. In case anyone else runs into it, my problem was that I had `secret:` and `name:` left aligned, so the `n` in `name:` was directly under the `s` in `secret:`. I fixed it by making it right aligned, so the `:` in `secret:` was directly under the `:` in `name:`. – Levi Noecker Nov 06 '21 at 14:57