Secrets
Secrets are similar to Config Maps but they are stored in an encoded format
Config Map
1apiVersion: v1
2kind: ConfigMap
3metadata:
4 name: app-config
5data:
6 APP_COLOR: pink
7 APP_MODE: prod
Secret
1apiVersion: v1
2kind: Secret
3metadata:
4 name: app-secret
5data:
6 APP_COLOR: pink
7 APP_MODE: prod
Creation
Imperative
Using the CLIFrom Literal
1kubectl create secret generic \
2 <secret-name> --from-literal=<key>=<value>
1kubectl create secret generic \
2 <secret-name> \
3 --from-literal=APP_COLOR=blue \
4 --from-literal=APP_COLOR_1=pink \
5 --from-literal=APP_COLOR_2=green \
From Path
1kubectl create secret generic \
2 <secret-name> --from-path=<path-to-file>
1kubectl create secret generic \
2 <secret-name> --from-path=app_secret.properties
Declaritive
Using Yaml Syntax
Secret
Fiels Available
1apiVersion: v1
2kind:
3metadata:
4
5data:
Secret
Example
1apiVersion: v1
2kind: Secret
3metadata:
4 name: app-secret
5data:
6 APP_COLOR: cGluaw== #pink
7 APP_MODE: cHJvZA== #prod
How to base64 encode
1echo -n "value" | base64
Examples
1echo -n "pink" | base64
2echo -n "prod" | base64
To Decode (ignore %)
echo -n "value" | base64 -d
Example
echo -n "cGluaw==" | base64 -d
pink%
DEBUG
Get Secrets
kubectl get secret
kubectl get secret
NAME TYPE DATA AGE
mantisd-io-staging-tls kubernetes.io/tls 2 7d17h
mantisd-io-tls kubernetes.io/tls 2 7d17h
Describe Secret
kubectl describe secret <secret-name>
kubectl describe secret mantisd-io-tls
Name: mantisd-io-tls
Namespace: default
Labels: <none>
Annotations: cert-manager.io/alt-names: *.mantisd.io,mantisd.io
cert-manager.io/certificate-name: mantisd-io
cert-manager.io/common-name: *.mantisd.io
cert-manager.io/ip-sans:
cert-manager.io/issuer-group:
cert-manager.io/issuer-kind: ClusterIssuer
cert-manager.io/issuer-name: letsencrypt-production
cert-manager.io/uri-sans:
Type: kubernetes.io/tls
Data
====
tls.key: 1679 bytes
tls.crt: 5599 bytes
Get Secret Yaml
kubectl get secret <secret-name> -o yaml
kubectl get secret mantisd-io-tls -o yaml
apiVersion: v1
data:
tls.crt: asdasdasdasdasdasdasdasd
tls.key: asdasdasdasdasdasdasdasd
kind: Secret
metadata:
annotations:
cert-manager.io/alt-names: '*.mantisd.io,mantisd.io'
cert-manager.io/certificate-name: mantisd-io
cert-manager.io/common-name: '*.mantisd.io'
cert-manager.io/ip-sans: ""
cert-manager.io/issuer-group: ""
cert-manager.io/issuer-kind: ClusterIssuer
cert-manager.io/issuer-name: letsencrypt-production
cert-manager.io/uri-sans: ""
creationTimestamp: "2022-10-30T02:09:48Z"
name: mantisd-io-tls
namespace: default
resourceVersion: "93005"
uid: 6520e20c-ad81-4020-ae57-fc3963a0202f
type: kubernetes.io/tls
Use Secret
Secret
1apiVersion: v1
2kind: Secret
3metadata:
4 name: app-secret
5data:
6 APP_COLOR: cGluaw== #pink
7 APP_MODE: cHJvZA== #prod
envFrom
1
2apiVersion:
3kind: Pod
4metadata:
5 name: simple-webapp-color
6spec:
7 containers:
8 - name: simple-webapp-color
9 image: simple-webapp-color
10 ports:
11 - containerPort: 8080
12
13 envFrom:
14 - secretRef:
15 name: app-config
env valueFrom
1
2apiVersion:
3kind: Pod
4metadata:
5 name: simple-webapp-color
6spec:
7 containers:
8 - name: simple-webapp-color
9 image: simple-webapp-color
10 ports:
11 - containerPort: 8080
12
13 env:
14 - name: APP_COLOR
15 valueFrom:
16 secretKeyRef:
17 name: app-secret
18 key: APP_COLOR
volume
1
2apiVersion:
3kind: Pod
4metadata:
5 name: simple-webapp-color
6spec:
7 containers:
8 - name: simple-webapp-color
9 image: simple-webapp-color
10 ports:
11 - containerPort: 8080
12
13 volumes:
14 - name: app-secret-volume
15 secret:
16 secretName: app-config
This will Add each secret as an individual file
Inside Container
ls /opt/app-secret-volumes
APP_COLOR APP_MODE
cat /opt/app-secret-volumes/APP_COLOR
pink
Tips
Remember that secrets encode data in base64 format. Anyone with the base64 encoded secret can easily decode it. As such the secrets can be considered as not very safe.
The concept of safety of the Secrets is a bit confusing in Kubernetes. The kubernetes documentation page and a lot of blogs out there refer to secrets as a "safer option" to store sensitive data. They are safer than storing in plain text as they reduce the risk of accidentally exposing passwords and other sensitive data. In my opinion it's not the secret itself that is safe, it is the practices around it.
Secrets are not encrypted, so it is not safer in that sense. However, some best practices around using secrets make it safer. As in best practices like:
Not checking-in secret object definition files to source code repositories.
Enabling Encryption at Rest for Secrets so they are stored encrypted in ETCD.
Also the way kubernetes handles secrets. Such as:
A secret is only sent to a node if a pod on that node requires it.
Kubelet stores the secret into a tmpfs so that the secret is not written to disk storage.
Once the Pod that depends on the secret is deleted, kubelet will delete its local copy of the secret data as well.
Read about the protections and risks of using secrets here
Having said that, there are other better ways of handling sensitive data like passwords in Kubernetes, such as using tools like Helm Secrets, HashiCorp Vault. I hope to make a lecture on these in the future.
- Secrets are not Encrypted. Only Encoded
- Do Not Check In Secret objects to SCM along with code
- Secrets are not Encrypted in ETCD
- Anyone who has access to to Namespace has access to all secrets in that Namespace
- Configure RBAC to Secrets
- Consider 3rd Party secret store Providers like Vault