什么是 Secret
Secret 是 Kubernetes 中用于存储和管理敏感信息的对象,如密码、OAuth 令牌、SSH 密钥等。与 ConfigMap 不同,Secret 专门设计用于处理机密数据,提供了额外的安全保护。
Secret 的主要特性
1. 安全性
- Base64 编码:数据以 Base64 编码存储(注意:这不是加密)
- 内存存储:在节点上以 tmpfs 形式存储,不写入磁盘
- 访问控制:通过 RBAC 控制访问权限
- 静态加密:支持 etcd 静态数据加密
2. 大小限制
- 单个 Secret 最大 1MB
- 建议保持较小的 Secret 大小以提高性能
3. 作用域
- 命名空间级别的资源
- 只能在同一命名空间内的 Pod 中使用
Secret 的分类
1. Opaque(通用 Secret)
最常用的 Secret 类型,用于存储任意的用户定义数据。
yaml
apiVersion: v1
kind: Secret
metadata:
name: mysecret
type: Opaque
data:
username: YWRtaW4= # admin 的 base64 编码
password: MWYyZDFlMmU2N2Rm # 1f2d1e2e67df 的 base64 编码可以通过Linux的 base64 命令进行编码:
bash
echo -n "admin" | base64
echo -n "1f2d1e2e67df" | base642. kubernetes.io/service-account-token
用于 ServiceAccount 的身份验证令牌。
yaml
apiVersion: v1
kind: Secret
metadata:
name: sa-token
annotations:
kubernetes.io/service-account.name: my-service-account
type: kubernetes.io/service-account-token
data:
token: <base64-encoded-token>
ca.crt: <base64-encoded-ca-certificate>3. kubernetes.io/dockercfg 和 kubernetes.io/dockerconfigjson
用于存储 Docker 仓库的认证信息。
yaml
apiVersion: v1
kind: Secret
metadata:
name: docker-secret
type: kubernetes.io/dockercfg
data:
.dockercfg: <base64-encoded-dockercfg>
apiVersion: v1
kind: Secret
metadata:
name: docker-secret
type: kubernetes.io/dockerconfigjson
data:
.dockerconfigjson: <base64-encoded-docker-config>4. kubernetes.io/basic-auth
用于基本身份验证。
yaml
apiVersion: v1
kind: Secret
metadata:
name: basic-auth-secret
type: kubernetes.io/basic-auth
data:
username: YWRtaW4=
password: dGVzdA==5. kubernetes.io/ssh-auth
用于 SSH 身份验证。
yaml
apiVersion: v1
kind: Secret
metadata:
name: ssh-secret
type: kubernetes.io/ssh-auth
data:
ssh-privatekey: <base64-encoded-ssh-private-key>6. kubernetes.io/tls
用于存储 TLS 证书和私钥。
yaml
apiVersion: v1
kind: Secret
metadata:
name: tls-secret
type: kubernetes.io/tls
data:
tls.crt: <base64-encoded-certificate>
tls.key: <base64-encoded-private-key>7. bootstrap.kubernetes.io/token
用于节点引导过程中的令牌。
yaml
apiVersion: v1
kind: Secret
metadata:
name: bootstrap-token
type: bootstrap.kubernetes.io/token
data:
token-id: <base64-encoded-token-id>
token-secret: <base64-encoded-token-secret>创建 Secret 的方法
1. 通过命令行创建
创建通用 Secret
bash
kubectl create secret generic my-secret --from-literal=username=admin --from-literal=password=123456从文件创建
bash
kubectl create secret generic my-secret --from-file=username.txt --from-file=password.txt创建 Docker 仓库 Secret
bash
kubectl create secret docker-registry my-registry-secret \
--docker-server=myregistry.com \
--docker-username=admin \
--docker-password=mypassword \
--docker-email=admin@example.com创建 TLS Secret
bash
kubectl create secret tls my-tls-secret --cert=path/to/cert.crt --key=path/to/key.key2. 通过 YAML 文件创建
yaml
apiVersion: v1
kind: Secret
metadata:
name: app-secret
namespace: default
type: Opaque
data:
database_url: cG9zdGdyZXNxbDovL3VzZXI6cGFzc3dvcmRAaG9zdDpwb3J0L2RiX25hbWU=
api_key: bXktc2VjcmV0LWFwaS1rZXk=
stringData: # 使用 stringData 可以直接提供明文,系统会自动编码
debug_mode: "true"
log_level: "info"在 Pod 中使用 Secret
1. 作为环境变量
yaml
apiVersion: v1
kind: Pod
metadata:
name: secret-env-pod
spec:
containers:
- name: myapp
image: nginx
env:
- name: DB_USERNAME
valueFrom:
secretKeyRef:
name: app-secret
key: username
- name: DB_PASSWORD
valueFrom:
secretKeyRef:
name: app-secret
key: password
restartPolicy: Never2. 导入所有环境变量
yaml
apiVersion: v1
kind: Pod
metadata:
name: secret-envfrom-pod
spec:
containers:
- name: myapp
image: nginx
envFrom:
- secretRef:
name: app-secret
restartPolicy: Never3. 作为挂载卷
yaml
apiVersion: v1
kind: Pod
metadata:
name: secret-volume-pod
spec:
containers:
- name: myapp
image: nginx
volumeMounts:
- name: secret-volume
mountPath: /etc/secrets
readOnly: true
volumes:
- name: secret-volume
secret:
secretName: app-secret
restartPolicy: Never4. 指定特定文件和权限
yaml
apiVersion: v1
kind: Pod
metadata:
name: secret-volume-specific
spec:
containers:
- name: myapp
image: nginx
volumeMounts:
- name: secret-volume
mountPath: /etc/secrets
readOnly: true
volumes:
- name: secret-volume
secret:
secretName: app-secret
defaultMode: 0400 # 只读权限
items:
- key: username
path: db-username
mode: 0444
- key: password
path: db-password
mode: 0400
restartPolicy: NeverSecret 管理命令
查看 Secret
bash
kubectl get secrets
kubectl describe secret my-secret
kubectl get secret my-secret -o yaml
kubectl get secret my-secret -o jsonpath='{.data.username}' | base64 -d更新 Secret
bash
kubectl edit secret my-secret
kubectl patch secret my-secret -p='{"data":{"password":"bmV3LXBhc3N3b3Jk"}}'
kubectl create secret generic my-secret --from-literal=username=admin --from-literal=password=newpass --dry-run=client -o yaml | kubectl apply -f -删除 Secret
bash
kubectl delete secret my-secretSecret 与 ConfigMap 的对比
| 特性 | Secret | ConfigMap |
|---|---|---|
| 用途 | 敏感数据 | 非敏感配置 |
| 存储方式 | Base64 编码 | 明文 |
| 节点存储 | tmpfs(内存) | 普通文件系统 |
| 大小限制 | 1MB | 1MB |
| 安全性 | 高(支持加密) | 一般 |
| 访问控制 | 严格的 RBAC | 相对宽松 |
总结
Secret 是 Kubernetes 中处理敏感数据的核心机制,提供了多种类型来满足不同的使用场景。正确使用 Secret 可以提高应用的安全性,但需要注意其限制和最佳实践,特别是在生产环境中要启用适当的访问控制和加密措施。