kubernetes存储 -- Secret配置管理

简介

ConfigMap是用来存储一些非安全的配置信息,如果涉及到一些安全相关的数据的话用ConfigMap就非常不妥了,
因为ConfigMap明文存储的,这个时候j就应该使用Secret

  • Secret 对象类型用来保存敏感信息,例如密码、OAuth 令牌和 ssh key。

  • 敏感信息放在 secret 中比放在 Pod 的定义或者容器镜像中来说更加安全和灵活。

  • Pod 可以用两种方式使用 secret:

    • 作为 volume 中的文件被挂载到 pod 中的一个或者多个容器里。
    • 当 kubelet 为 pod 拉取镜像时使用(仓库认证信息)。
  • Secret的类型:

    • Service Account:Kubernetes 自动创建包含访问 API 凭据的 secret,并自动修改pod 以使用此类型的 secret。
    • Opaque:使用base64编码存储信息,可以通过base64 --decode解码获得原始数据,因此安全性弱。
    • kubernetes.io/dockerconfigjson:用于存储docker registry的认证信息。

Service Account

[root@server2 manifest]# kubectl get secrets 
NAME                  TYPE                                  DATA   AGE
basic-auth            Opaque                                1      7h52m
default-token-j7pl7   kubernetes.io/service-account-token   3      12d		/其实就是个token
tls-secret            kubernetes.io/tls                     2      26h

运行在pod里的进程需要调用Kubernetes API以及非Kubernetes API的其它服务。Service Account它并不是给kubernetes集群的用户使用的,而是给pod里面的进程使用的,它为pod提供必要的身份认证,让它可以通过apiserver获取信息。

  • 每个namespace下有一个名为default的默认的ServiceAccount对象:
[root@server2 manifest]# kubectl get sa --all-namespaces 
NAMESPACE         NAME                                 SECRETS   AGE
default           default                              1         12d
ingress-nginx     default                              1         29h
ingress-nginx     ingress-nginx                        1         29h
ingress-nginx     ingress-nginx-admission              1         29h
kube-node-lease   default                              1         12d
kube-public       default                              1         12d
kube-system       attachdetach-controller              1         12d

[root@server2 manifest]# kubectl describe sa default 
Name:                default
Namespace:           default
Labels:              <none>
Annotations:         <none>
Image pull secrets:  <none>
Mountable secrets:   default-token-j7pl7		/可以挂载的secret
Tokens:              default-token-j7pl7		/token就是一个secret
Events:              <none>
  • serviceaccout 创建时 Kubernetes 会默认创建对应的 secret。对应的 secret 会自动挂载到Pod 的 /run/secrets/kubernetes.io/serviceaccount 目录中。
# 进入pod中查看secret的挂载信息。
[root@server2 manifest]# kubectl exec  my-nginx-7f45d597d5-n7jft -- ls /var/run/secrets/kubernetes.io/serviceaccount
ca.crt					
namespace
token				/里面有证书,命名空间和token等信息。
  • ServiceAccount里有一个名为Tokens的可以作为Volume一样被Mount到Pod里的Secret,当Pod启动时这个Secret会被自动Mount到Pod的指定目录下,用来协助完成Pod中的进程访问API Server时的身份鉴权过程。
[root@server2 manifest]# kubectl describe pod my-nginx-7f45d597d5-n7jft 

    Mounts:
      /etc/nginx/conf.d from config-volume (rw)
      /var/run/secrets/kubernetes.io/serviceaccount from default-token-j7pl7 (ro)		
		//secret挂载到了这里

  default-token-j7pl7:			//secret 就是 sa 里面的一个token
    Type:        Secret (a volume populated by a Secret)
    SecretName:  default-token-j7pl7
    Optional:    false
QoS Class:       BestEffort
Node-Selectors:  <none>

Opaque Secret

Opaque使用base64编码存储信息,其value为base64编码后的值。我们需要自行创建。

我们在做ingress的 basic-auth 其实就是一个opaque 类型的secret:

[root@server2 manifest]# kubectl get secrets 
NAME                  TYPE                                  DATA   AGE
basic-auth            Opaque                                1      7h52m		//这个
default-token-j7pl7   kubernetes.io/service-account-token   3      12d
tls-secret            kubernetes.io/tls                     2      26h

命令行创建secret:

[root@server2 ~]# kubectl create secret generic dev-db-secret --from-literal=username=devuser --from-literal=password=S\!B\\*d\$zDsb
secret/dev-db-secret created
[root@server2 ~]# kubectl get secrets 
NAME                  TYPE                                  DATA   AGE

dev-db-secret         Opaque                                2      2s

注意如果密码具有特殊字符,则需要使用 \ 字符对其进行转义
在文件中创建secret:

[root@server2 ~]# echo -n 'admin' > ./username.txt
[root@server2 ~]# echo -n 'westos' > ./password.txt
[root@server2 ~]# kubectl create secret generic db-user-pass --from-file=./username.txt --from-file=./password.txt 
kubesecret/db-user-pass created
[root@server2 ~]# kubectl get secrets 
NAME                  TYPE                                  DATA   AGE

db-user-pass          Opaque                                2      4s

默认情况下 kubectl get和kubectl describe 为了安全是不会显示密码的内容,可以通过以下方式查看:

[root@server2 ~]# kubectl get  secrets dev-db-secret -o yaml
apiVersion: v1
data:
  password: UyFCXCpkJHpEc2I=
  username: ZGV2dXNlcg==
kind: Secret
metadata:
  creationTimestamp: "2020-07-01T09:12:14Z"
  managedFields:
  - apiVersion: v1
    fieldsType: FieldsV1
    fieldsV1:
      f:data:
        .: {}
        f:password: {}
        f:username: {}
      f:type: {}
    manager: kubectl
    operation: Update
    time: "2020-07-01T09:12:14Z"
  name: dev-db-secret
  namespace: default
  resourceVersion: "478900"
  selfLink: /api/v1/namespaces/default/secrets/dev-db-secret
  uid: e08f8d85-c4ac-4e82-a177-ab70a0e55c1e
type: Opaque
[root@server2 ~]# echo  UyFCXCpkJHpEc2I= |base64 -d
S!B\*d$zDsb
[root@server2 ~]# echo ZGV2dXNlcg== |base64 -d
devuser			//进行转换就出来了

yaml清单secret

[root@server2 ~]# echo admin |base64
YWRtaW4K
[root@server2 ~]# echo caoaoyuan |base64
Y2FvYW95dWFuCg==
[root@server2 ~]# vim mysecret.yaml
apiVersion: v1
kind: Secret
metadata:
  name: mysecret
type: Opaque
data:
  username: YWRtaW4=
  password: Y2FvYW95dWFuCg==

[root@server2 cm]# kubectl apply -f mysecret.yaml 
kubec	gsecret/mysecret created
[root@server2 cm]# kubectl get secrets 
NAME                  TYPE                                  DATA   AGE
basic-auth            Opaque                                1      8h
db-user-pass          Opaque                                2      10m
default-token-j7pl7   kubernetes.io/service-account-token   3      12d
dev-db-secret         Opaque                                2      9m10s
mysecret              Opaque                                2      6s		//这个

将Secret挂载到Volume中:

[root@server2 cm]# vim mysecret.yaml  
apiVersion: v1
kind: Secret
metadata:
  name: mysecret
type: Opaque
data:
  username: YWRtaW4=
  password: Y2FvYW95dWFuCg==

---
apiVersion: v1
kind: Pod
metadata:
  name: mysecret
spec:
  containers:
  - name: nginx
    image: nginx
    volumeMounts:
    - name: secrets
      mountPath: "/secret"		/挂接到这个位置,pod会自动创建
      readOnly: true
  volumes:
  - name: secrets
    secret:
      secretName: mysecret

[root@server2 cm]# kubectl apply -f  mysecret.yaml 
secret/mysecret unchanged
pod/mysecret created
[root@server2 cm]# kubectl exec mysecret -- ls /secret
password
username
[root@server2 cm]# kubectl exec mysecret -- cat /secret/password
caoaoyuan
[root@server2 cm]# kubectl exec mysecret -- cat /secret/username
admin

就挂接进去了。
向指定路径映射 secret 密钥:

[root@server2 cm]# vim mysecret.yaml 
apiVersion: v1
kind: Secret
metadata:
  name: mysecret
type: Opaque
data:
  username: YWRtaW4=
  password: Y2FvYW95dWFuCg==

---
apiVersion: v1
kind: Pod
metadata:
  name: mysecret
spec:
  containers:
  - name: nginx
    image: nginx
    volumeMounts:
    - name: secrets
      mountPath: "/secret"
      readOnly: true
  volumes:
  - name: secrets
    secret:
      secretName: mysecret
      items:
      - key: username				/选择mysecret中的username这个key
        path: my-group/my-username			/将它挂载道这个位置
[root@server2 cm]# kubectl apply -f mysecret.yaml 
secret/mysecret created
pod/mysecret created
[root@server2 cm]# kubectl exec mysecret -- ls /secret/
my-group
[root@server2 cm]# kubectl exec mysecret -- ls /secret/my-group
my-username
[root@server2 cm]# kubectl exec mysecret -- cat /secret/my-group/my-username
admin

可以看出值有指定的数据挂接到了这里。

将Secret设置为环境变量:

[root@server2 cm]# vim mysecret.yaml 
apiVersion: v1
kind: Secret
metadata:
  name: mysecret
type: Opaque
data:
  username: YWRtaW4=
  password: Y2FvYW95dWFuCg==

---
apiVersion: v1
kind: Pod
metadata:
  name: secret-env
spec:
  containers:
  - name: nginx
    image: nginx
    env:
    - name: SECRET_USERNAME		/自己定义名称
      valueFrom:
        secretKeyRef:
          name: mysecret		/调用secret的值
          key: username
    - name: SECRET_PASSWORD
      valueFrom:
        secretKeyRef:
          name: mysecret
          key: password
[root@server2 cm]# kubectl apply -f mysecret.yaml 
secret/mysecret unchanged
pod/secret-env created

[root@server2 cm]# kubectl exec secret-env  -- env
PATH=/usr/local/sbin:/usr/local/bin:/usr/sbin:/usr/bin:/sbin:/bin
HOSTNAME=secret-env
SECRET_PASSWORD=caoaoyuan

SECRET_USERNAME=admin
KUBERNETES_SERVICE_PORT_HTTPS=443

HOME=/root

环境变量读取Secret很方便,但是无法支撑Secret动态更新。

kubernetes.io/dockerconfigjson

kubernetes.io/dockerconfigjson 类型的secret 用于存储 docker registry 的认证信息.
我们目前用的私有仓库是harbor仓库,我们现在有一个未公开的仓库,里面又一个镜像:
在这里插入图片描述

在这里插入图片描述
现在我们去拉取:

[root@server3 ~]# docker pull reg.caoaoyuan.org/caoaoyuan/game2048
Using default tag: latest
Error response from daemon: pull access denied for reg.caoaoyuan.org/caoaoyuan/game2048, r

是被拒绝的我们值有登陆进去才能拉取:

[root@server3 ~]# docker login reg.caoaoyuan.org
Username: admin
Password: 
WARNING! Your password will be stored unencrypted in /root/.docker/config.json.
Configure a credential helper to remove this warning. See
https://docs.docker.com/engine/reference/commandline/login/#credentials-store

Login Succeeded
[root@server3 ~]# docker pull reg.caoaoyuan.org/caoaoyuan/game2048
Using default tag: latest
latest: Pulling from caoaoyuan/game2048
534e72e7cedc: Pull complete 
f62e2f6dfeef: Pull complete 
fe7db6293242: Pull complete 
3f120f6a2bf8: Pull complete 
4ba4e6930ea5: Pull complete 
Digest: sha256:8a34fb9cb168c420604b6e5d32ca6d412cb0d533a826b313b190535c03fe9390
Status: Downloaded newer image for reg.caoaoyuan.org/caoaoyuan/game2048:latest
reg.caoaoyuan.org/caoaoyuan/game2048:latest

而我们登陆的信息保存在用户主目录下的 .docker 下:

[root@server3 ~]# cd .docker/
[root@server3 .docker]# cat config.json 
{
	"auths": {
		"reg.caoaoyuan.org": {
			"auth": "YWRtaW46Y2FvYW95dWFu"
		}
	},
	"HttpHeaders": {
		"User-Agent": "Docker-Client/19.03.11 (linux)"
	}
[root@server3 .docker]# docker rmi reg.caoaoyuan.org/caoaoyuan/game2048:latest 
// 先删除镜像
[root@server3 .docker]# docker logout			//退出
[root@server3 .docker]# cat config.json 
{
	"auths": {},
	"HttpHeaders": {
		"User-Agent": "Docker-Client/19.03.11 (linux)"
	}

这种方式是一种不安全且不够灵活的方式,我们可以通过kubernetes.io/dockerconfigjson 类型的secret 来实现简化

手动创建:

[root@server2 cm]# kubectl create secret docker-registry myregistrykey \		/secret 名称
--docker-server=reg.caoaoyuan.org \				/仓库地址
--docker-username=admin --docker-password=caoaoyuan \		/仓库的用户密码
[email protected]				/用户邮箱

secret/myregistrykey created

[root@server2 cm]# kubectl get secrets 
NAME                  TYPE                                  DATA   AGE
basic-auth            Opaque                                1      9h
db-user-pass          Opaque                                2      98m
default-token-j7pl7   kubernetes.io/service-account-token   3      13d
dev-db-secret         Opaque                                2      97m
myregistrykey         kubernetes.io/dockerconfigjson        1      94s

使用:

[root@server2 cm]# cat pod.yml 
apiVersion: v1
kind: Pod
metadata:
  name: mypod
spec:
  containers:
    - name: game2048
      image: reg.caoaoyuan.org/caoaoyuan/game2048
  imagePullSecrets:
    - name: myregistrykey


secret/myregistrykey created
[root@server2 cm]# kubectl apply -f pod.yml 
pod/mypod created
[root@server2 cm]# kubectl get pod
NAME                        READY   STATUS    RESTARTS   AGE
my-nginx-7f45d597d5-n7jft   1/1     Running   0          4h19m
mypod                       1/1     Running   0          9s
/注意这时我们并没有docker login。
發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章