最推荐的做法是在 Kubernetes 集群中启用 Secret 静态加密存储,配合文件挂载权限控制和定期密钥轮换,适用于容器化部署场景。
先说结论:Secret 默认仅做 Base64 编码而非真正加密,需要结合集群加密配置、权限控制和密钥管理才能有效降低泄露风险。
- 先判断:确认你的集群是否启用了 Secret 静态加密存储功能
- 优先做:使用文件挂载方式替代环境变量,并设置严格的文件权限
- 再验证:检查 etcd 中 Secret 是否加密存储,容器内文件权限是否符合预期
命令速用版
创建 Secret 并验证编码方式:
kubectl create secret generic db-secret `--from-literal`=username=admin `--from-literal`=password=123456
查看 Secret 内容(显示为 Base64 编码):
kubectl get secret db-secret -o yaml
解码验证(确认只是编码而非加密):
echo '编码后的字符串' | base64 -d
配置文件挂载权限(defaultMode 256 对应八进制 0400):
volumes:
- name: secret-volume
secret:
secretName: mysecret
defaultMode: 256为什么会这样
很多新手误以为 Kubernetes Secret 默认就是加密的,实际上它只是做了 Base64 编码。编码和加密有本质区别:编码可以轻易还原,加密需要密钥才能解密。这意味着如果有人能访问 etcd 或 kubectl get secret 命令,就能直接获取敏感信息。
真正的安全需要多层防护:集群层面启用 etcd 静态加密,应用层面限制文件访问权限,管理层面做好密钥轮换和访问控制。单一措施无法完全避免泄露风险。
分步处理
第一步:确认集群加密状态
联系集群管理员确认是否启用了 Secret 静态加密。部分云厂商的托管集群(如 CCE)已默认配置 etcd 加密存储,但自建集群需要手动配置 EncryptionConfiguration。
检查点:查看集群配置文档或咨询运维团队,确认 etcd 中 Secret 数据是否加密。
第二步:创建 Secret 时预处理敏感信息
建议在创建 Secret 前对敏感信息进行额外加密,使用时再解密。这样可以增加一层保护,即使 Secret 被泄露,攻击者也无法直接使用。
配置示例:
apiVersion: v1 kind: Secret metadata: name: encrypted-secret type: Opaque data: db-password: <加密后的 Base64 字符串>
第三步:使用文件挂载替代环境变量
环境变量容易被所有进程访问,且可能出现在日志中。文件挂载方式更安全,可以控制文件权限。
挂载配置:
volumeMounts:
- name: secret-volume
mountPath: "/etc/secret"
readOnly: true
volumes:
- name: secret-volume
secret:
secretName: mysecret
defaultMode: 256注意:defaultMode 256 是十进制,对应八进制 0400,表示只有文件所有者可读取。
第四步:配置隐藏文件命名
通过给 Secret 中的键名添加点号前缀,可以在容器内实现文件"隐藏"效果(ls 命令默认不显示):
data: .secret-file:
验证:在容器内执行 ls -1 看不到,执行 ls -al 可以看到。
第五步:使用 Bound Service Account Token
对于 1.23 版本以上的集群,推荐使用 Bound Service Account Token 替代传统的 Secret 方式存储 ServiceAccount Token。这种方式支持设置过期时间,且与 Pod 生命周期一致,可减少凭据泄露风险。
怎么验证是否生效
检查容器内文件权限:
kubectl exec -it-- ls -l /etc/secret
确认文件权限显示为 0400 或更严格。
检查 Secret 是否被正确挂载:
kubectl exec -it-- cat /etc/secret/.secret-file
验证环境变量注入(如使用):
kubectl exec -it-- env | grep DB_
确认没有意外的日志泄露:检查应用日志中是否包含敏感信息。
常见坑
Base64 不是加密:这是最常见的误解。Base64 编码可以轻易解码,不要依赖它提供安全性。
环境变量泄露风险:通过环境变量注入的 Secret 可能被子进程继承,或在崩溃日志中暴露。优先使用文件挂载方式。
权限配置错误:defaultMode 使用十进制而非八进制,256 对应 0400,不是 755。
命名空间隔离:Deployment 和 Secret 必须位于同一命名空间,跨命名空间引用会失败。
Git 仓库存储:不要将包含 Secret 的 YAML 文件直接提交到 Git 仓库。可以使用 git-secret 等工具对敏感文件进行 GPG 加密后再提交。
密钥轮换缺失:Secret 创建后长期不更新,一旦泄露影响范围大。建议建立定期轮换机制,每 3-6 个月更新一次。
参考来源
- 阿里云帮助中心 - 容器服务 Kubernetes 版 ACK 保密字典配置指南
- 华为云 CCE 文档 - 在 CCE 集群中使用密钥 Secret 的安全配置建议
- git-secret 官方文档 - 使用 git-secret 保护敏感数据
- Spring Cloud Config 官方文档 - 配置中心加密方案