Both hold configuration outside the container image. A ConfigMap is for normal settings. A Secret is for sensitive values. A Secret is not secure by default.
You can give both to a Pod in two ways:
- as environment variables
- as files mounted into the container
This lets one image run in every environment (dev, staging, production). It is the same idea as Twelve-Factor config: keep config in the environment, not in the code.
Use a ConfigMap for non-sensitive settings, such as log levels, feature flags or service URLs. Use a Secret for sensitive values, such as passwords, tokens and keys.
A Secret is not encrypted just because it is a Secret. Its values are base64-encoded. Base64 is an encoding, not encryption: anyone can decode it. By default, Kubernetes stores Secrets unencrypted in etcd, its internal database.
To protect Secrets:
- turn on encryption at rest for etcd
- limit who can read them with RBAC (role-based access control: rules for who can do what)
- consider an external secret manager
Also note: anyone who can create Pods in the namespace can read its Secrets, because they can mount them into a Pod.
- Both give config to Pods as environment variables or files.
- Use a ConfigMap for non-sensitive settings.
- Use a Secret for sensitive values.
- Base64 is not encryption, and Secrets are stored unencrypted in etcd by default.
- Protect Secrets with encryption at rest and RBAC.