九,configMap及secret的基本使用

Posted peng-zone

tags:

篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了九,configMap及secret的基本使用相关的知识,希望对你有一定的参考价值。

制定容器配置的方式

  1. 自定义命令行参数来实现;

    1. command
    2. args []
  2. 把配置文件直接写入镜像;(耦合多过于紧密,局限性太大)

  3. 环境变量实现, 容器从物理机中的环境变量来导入配置

    1. 所配置的应用支持从环境变量中来读取
    2. 用预处理脚本entrypoint处理,通过环境变量传递过来的配置
  4. 存储卷;通过挂在对应的已经存放了配置文件的存储卷上,如configMap,secret等

  5. docker config(可以通过docker命令行改变配置,但k8s集群基本不使用)

configMap存储数据为明文,敏感数据慎用

将配置文件从镜像中解耦, 从而增强了应用的可以执行以及应用的复制性.(简单说就是把容器内的配置文件本地化,方便容器多用途使用)

创建configMap的几种方式

创建ConfigMap的方式有4种:

  • 通过直接在命令行中指定configmap参数创建,即--from-literal=key=value

    kubectl create configmap nginx-config --from-literal=nginx_port=80 --from-literal=server_name=myapp.beijingfc.com
    
    #查看configmap
    [root@master ~]# kubectl get cm
    NAME           DATA   AGE
    nginx-config   2      4s
    
    #查看configmap的具体信息
    [root@master ~]# kubectl describe configmaps nginx-config
    Name:         nginx-config
    Namespace:    default
    Labels:       <none>
    Annotations:  <none>
    
    Data
    ====
    nginx_port:
    ----
    80
    server_name:
    ----
    myapp.beijingfc.com
    Events:  <none>
  • 通过指定文件创建,即将一个配置文件创建为一个ConfigMap,--from-file=File_Path

    #文件内容
    cat manifests/configmap/www.conf
    server {
            server_name myapp.beijingfc.com;
        listen 80;
        root /data/web/html
    }
    
    #通过文件创建configmap
    kubectl create configmap nginx-www --from-file=./manifests/configmap/www.conf
    
    #查看configmap
    [root@master configmap]# kubectl describe configmaps nginx-www
    Name:         nginx-www
    Namespace:    default
    Labels:       <none>
    Annotations:  <none>
    
    Data
    ====
    www.conf:
    ----
    server {
      server_name myapp.beijingfc.com;
        listen 80;
        root /data/web/html
    }
    
    Events:  <none>
  • 通过一个文件内多个键值对,--from-env-file=

    cat << EOF > env.txt
    db.host=10.0.0.50
    db.port=3306
    EOF
    kubectl create cm env-cm --from-env-file=env.txt

    如果有多个env文件, 只有最后一个env文件会生效

    [root@master configmap_test]# cat game.properties
    enemies=aliens
    lives=3
    enemies.cheat=true
    enemies.cheat.level=noGoodRotten
    secret.code.passphrase=UUDDLRLRBABAS
    secret.code.allowed=true
    secret.code.lives=30
    
    [root@master configmap_test]# cat ui.properties
    color.good=purple
    color.bad=yellow
    allow.textmode=true
    how.nice.to.look=fairlyNice
    #执行命令创建configmap
    kubectl create configmap configmap-env --from-env-file=./game.properties --from-env-file=./ui.properties
    #可以看到, 只有ui.properties生效了
    [root@master configmap_test]# kubectl get configmaps configmap-env -o yaml
    apiVersion: v1
    data:
      allow.textmode: "true"
      color.bad: yellow
      color.good: purple
      how.nice.to.look: fairlyNice
    kind: ConfigMap
    metadata:
      creationTimestamp: "2019-09-11T01:58:17Z"
      name: configmap-env
      namespace: default
      resourceVersion: "186936"
      selfLink: /api/v1/namespaces/default/configmaps/configmap-env
      uid: 4e36009f-267c-4713-8a7a-99d8f6dd3039
  • 事先写好标准的configmap的yaml文件,然后kubectl apply -f 创建

    [root@master configmap]# cat test.yaml
    apiVersion: v1
    kind: ConfigMap
    metadata:
      name: cm-4
    data:
      db.host: 10.0.0.50
      db.port: "3306"
    [root@master configmap]# kubectl apply -f test.yaml
    [root@master configmap]# kubectl describe cm cm-4
    Name:         cm-4
    Namespace:    default
    Labels:       <none>
    Annotations:  kubectl.kubernetes.io/last-applied-configuration:
                    {"apiVersion":"v1","data":{"db.host":"10.0.0.50","db.port":"3306"},"kind":"ConfigMap","metadata":{"annotations":{},"name":"cm-4","...
    
    Data
    ====
    db.host:
    ----
    10.0.0.50
    db.port:
    ----
    3306
    Events:  <none>

命令行创建和测试configMap实例

命令行键值对创建

kubectl describe configmap nginx-www -o yaml
[root@master volume]# kubectl create configmap nginx-config --from-literal=nginx_port=80 --from-literal=server_name=myapp.beijingfc.com
configmap/nginx-config created
[root@master volume]# kubectl get configmap
NAME           DATA   AGE
nginx-config   2      7s
[root@master volume]# kubectl describe configmap nginx-config
Name:         nginx-config
Namespace:    default
Labels:       <none>
Annotations:  <none>

Data
====
nginx_port:
----
80
server_name:
----
myapp.beijingfc.com
Events:  <none>

创建一个Pod 挂载测试

配置清单如下:

[root@master configmap]# cat pod-configmap.yaml 
apiVersion: v1
kind: Pod
metadata:
  name: pod-cm
  namespace: default
  labels:
    app: myapp
    tier: frontend
  annotations:
    jubaozhu.com/created-by: "cluster admin"
spec:
  containers:
  - name: myapp
    image: ikubernetes/myapp:v1
    ports:
    - name: http
      containerPort: 80
    env:                            # 这里使用env, 表示容器中会用环境变量导入
    - name: NGINX_SERVER_PORT       # 这里的name表示容器中的key值
      valueFrom:
        configMapKeyRef:
          name: nginx-config        # 这里name是指向configMap对应的名称
          key: nginx_port           # 表示容器中key 所对应的 value的值, 此处取值的地方是定义的configMap中的对应的value值
    - name: NGINX_SERVER_NAME       # 因为要导入两个值,所以要写两份, 写法和上面的导入环境变量的方式相同
      valueFrom:
        configMapKeyRef:
          name: nginx-config
          key: server_name

创建后测试

[root@master configmap]# kubectl apply -f pod-configmap.yaml 
pod/pod-cm created
[root@master configmap]# kubectl get pod -o wide
NAME          READY   STATUS    RESTARTS   AGE   IP            NODE                NOMINATED NODE   READINESS GATES
pod-cm        1/1     Running   0          8s    10.244.1.30   node03.kubernetes   <none>           <none>

创建Pod后,进入到对应的容器中查看环境变量

[root@master configmap]# kubectl exec -it pod-cm -- /bin/sh
/ # env
MYAPP_SVC_PORT_80_TCP_ADDR=10.98.57.156
KUBERNETES_PORT=tcp://10.96.0.1:443
KUBERNETES_SERVICE_PORT=443
MYAPP_SVC_PORT_80_TCP_PORT=80
HOSTNAME=pod-cm
SHLVL=1
MYAPP_SVC_PORT_80_TCP_PROTO=tcp
HOME=/root
NGINX_SERVER_PORT=80
NGINX_SERVER_NAME=myapp.beijingfc.com
... ...
... ...

可以通过命令行edit编辑configMap
测试通过edit把端口变更为8080

[root@master configmap]# kubectl edit configmap nginx-config

    apiVersion: v1
    data:
      nginx_port: "8080"   #修改为8080
      server_name: myapp.beijingfc.com
    kind: ConfigMap
    metadata:
      creationTimestamp: "2019-10-11T06:47:27Z"
      name: nginx-config
      namespace: default
      resourceVersion: "4556708"
      ... ...
      ... ...
      :wq
configmap/nginx-config edited
[root@master configmap]# kubectl describe configmap nginx-config
Name:         nginx-config
Namespace:    default
Labels:       <none>
Annotations:  <none>

Data
====
nginx_port:
----
8080     #端口已修改为8080
server_name:
----
myapp.beijingfc.com
Events:  <none>

修改之后, 需要些许时间等待后,容器中的环境变量就会变更,需要再次进入容器后查看环境变量中的端口的值已经变成了8080

通过指定文件创建configMap实例

首先需要手动编辑一个相应的配置文件

[root@master configmap]# cat www.conf 
server {
    server_name myapp.beijingfc.com;
    listen 80;
    root /data/web/html/;
}

然后使用命令创建如下:

[root@master configmap]# kubectl create configmap nginx-www --from-file=www.conf        # 这里只有一个等号, 表示 key 就是文件名称, 而value 是文件内容
configmap/nginx-www created
[root@master configmap]# kubectl get configmap
NAME           DATA   AGE
nginx-config   2      2m41s
nginx-www      1      4s
[root@master configmap]# kubectl describe configmap nginx-www
Name:         nginx-www
Namespace:    default
Labels:       <none>
Annotations:  <none>

Data
====
www.conf:
----
server {
    server_name myapp.beijingfc.com;
    listen 80;
    root /data/web/html/;
}

Events:  <none>
[root@master configmap]# kubectl get configmap nginx-www -o yaml
apiVersion: v1
data:
  www.conf: |
    server {
        server_name myapp.beijingfc.com;
        listen 80;
        root /data/web/html/;
    }
kind: ConfigMap
metadata:
  creationTimestamp: "2019-08-06T08:44:37Z"
  name: nginx-www
  namespace: default
  resourceVersion: "3850257"
  selfLink: /api/v1/namespaces/default/configmaps/nginx-www
  uid: 81050135-532c-4f0e-8fcf-99727cc2c498

创建Pod测试

创建相应清单文件

[root@master configmap]# cat pod-configmap-2.yaml 
apiVersion: v1
kind: Pod
metadata:
  name: pod-cm-2
  namespace: default
  labels:
    app: myapp
    tier: frontend
  annotations:
    jubaozhu.com/created-by: "cluster admin"
spec:
  containers:
  - name: myapp
    image: ikubernetes/myapp:v1
    ports:
    - name: http
      containerPort: 80
    volumeMounts:                       # 可直接挂在configMap到Pod中
    - name: nginxconf                   # 这里指定卷名称
      mountPath: /etc/nginx/config.d/   # 这里指定挂在的路径
      readOnly: true                    # 这里表示当挂载失败的时候,容器能否启动成功,True表示可以正常启动,否则一点挂载失败,Pod的状态是Error
  volumes:                      # 定义一个卷, 实质上是一个configMap
  - name: nginxconf             # 卷名称
    configMap:                  # 在此指定卷类型为configMap
      name: nginx-config        # 这里指定 configMap对应的名称

创建后测试

[root@master configmap]# kubectl apply -f pod-configmap-2.yaml 
pod/pod-cm-2 created
[root@master configmap]# kubectl get pods -o wide
NAME          READY   STATUS    RESTARTS   AGE   IP            NODE                NOMINATED NODE   READINESS GATES
pod-cm-2      1/1     Running   0          5s    10.244.2.29   node02.kubernetes   <none>           <none>

然后进入Pod中查看挂在是否正常

[root@master configmap]# kubectl exec -it pod-cm-2 -- /bin/sh
/ # cd /etc/nginx/config.d/
/etc/nginx/config.d # ls -l
total 0
lrwxrwxrwx    1 root     root            17 Aug  6 09:12 nginx_port -> ..data/nginx_port
lrwxrwxrwx    1 root     root            18 Aug  6 09:12 server_name -> ..data/server_name
/etc/nginx/config.d # cat server_name 
myapp.beijingfc.com              # servername显示正常
/etc/nginx/config.d # cat nginx_port         
80                            # 端口显示正常
/etc/nginx/config.d # exit                

同样也支持在线修改, 需要些许时间后就容器中的对应的值就会产生变化

贴近实际进行测试

上面创建了一个nginx-www 的一个正常的nginx主机的一个配置文件, 下面挂在到Pod中尝试访问是否正常

[root@master configmap]# vim pod-configmap-3.yaml
apiVersion: v1
kind: Pod
metadata:
  name: pod-cm-3
  namespace: default
  labels:
    app: myapp
    tier: frontend
  annotations:
    jubaozhu.com/created-by: "cluster admin"
spec:
  containers:
  - name: myapp
    image: ikubernetes/myapp:v1
    ports:
    - name: http
      containerPort: 80
    volumeMounts:
    - name: nginxconf
      mountPath: /etc/nginx/conf.d/     # 挂载点为实际的nginx配置文件目录
      readOnly: true
  volumes:
  - name: nginxconf
    configMap:
      name: nginx-www

创建后测试

[root@master configmap]# kubectl apply -f pod-configmap-3.yaml 
pod/pod-cm-3 created
[root@master configmap]# kubectl get pods -o wide
NAME          READY   STATUS    RESTARTS   AGE   IP            NODE                NOMINATED NODE   READINESS GATES
pod-cm-3      1/1     Running   0          6s    10.244.3.33   node01.kubernetes   <none>           <none>

进入Pod中查看

[root@master configmap]# kubectl exec -it pod-cm-3 -- /bin/sh
/ # cd /etc/nginx/conf.d/
/etc/nginx/conf.d # ls
www.conf
/etc/nginx/conf.d # cat www.conf 
server {
    server_name myapp.beijingfc.com;
    listen 8088;
    root /data/web/html/;
}

因为配置的nginx虚拟主机对应的目录不存在,下面来手动创建目录和写入测试内容

[root@master configmap]# kubectl exec -it pod-cm-3 -- /bin/sh
/ # mkdir /data/web/html -p
/ # echo '<h1>Nginx Server configured by ConfigMap</h1>' > /data/web/html/index.html

集群外部测试访问:

<h1>Nginx Server configured by ConfigMap</h1>
[root@master configmap]# curl 10.244.3.33:80

需要注意的是, 如果在线修改了configMap后, 这里需要手动进入到Pod中, 重载一下nginx才可以, 否则不生效

secret(使用 base64 编码,并非明文存储)

secret 使用 base64 编码,并非明文存储

三种类型:

  1. generic 通用的secret, 一般保存密码使用
  2. tls 保存证书和对应的秘钥
  3. docker-registry docker的认证信息

举例测试 generic

通过命令的形式创建一个 secret

[root@master configmap]# kubectl create secret generic mysql-root-password --from-literal=password=MyP@ss123
secret/mysql-root-password created
[root@master configmap]# kubectl get secret
NAME                    TYPE                                  DATA   AGE
default-token-bc86p     kubernetes.io/service-account-token   3      28d
mysql-root-password     Opaque                                1      4s         # 这里看到创建成功
tomcat-ingress-secret   kubernetes.io/tls                     2      5d21h
[root@master configmap]# kubectl describe secret mysql-root-password
Name:         mysql-root-password
Namespace:    default
Labels:       <none>
Annotations:  <none>

Type:  Opaque

Data
====
passwork:  9 bytes          # value的值被加密 没有被直接显示出来

解密

[root@master configmap]# kubectl get secret mysql-root-password -o yaml
apiVersion: v1
data:
  passwork: TXlQQHNzMTIz                # base64 编码格式的密码加密方式
kind: Secret
metadata:
  creationTimestamp: "2019-08-07T01:07:11Z"
  name: mysql-root-password
  namespace: default
  resourceVersion: "3942726"
  selfLink: /api/v1/namespaces/default/secrets/mysql-root-password
  uid: f73164b5-8619-42c4-8186-c13ae8ebd89d
type: Opaque
[root@master configmap]# echo TXlQQHNzMTIz | base64 -d     # 使用base64解码........
MyP@ss123[root@master configmap]#

创建Pod 应用此 secret

[root@master configmap]# cat pod-secret-1.yaml 
apiVersion: v1
kind: Pod
metadata:
  name: pod-secret-1
  namespace: default
  labels:
    app: myapp
    tier: frontend
  annotations:
    jubaozhu.com/created-by: "cluster admin"
spec:
  containers:
  - name: myapp
    image: ikubernetes/myapp:v1
    ports:
    - name: http
      containerPort: 80
    env:
    - name: MYSQL_ROOT_PASSWORD
      valueFrom:
        secretKeyRef:
          name: mysql-root-password
          key: password

创建查看

[root@master configmap]# kubectl apply -f pod-secret-1.yaml 
pod/pod-secret-1 created
[root@master configmap]# kubectl get pods
NAME           READY   STATUS    RESTARTS   AGE
pod-secret-1   1/1     Running   0          2s
[root@master configmap]# kubectl exec -it pod-secret-1 -- /bin/sh
/ # env
MYAPP_SVC_PORT_80_TCP_ADDR=10.98.57.156
KUBERNETES_SERVICE_PORT=443
KUBERNETES_PORT=tcp://10.96.0.1:443
MYAPP_SVC_PORT_80_TCP_PORT=80
HOSTNAME=pod-secret-1
SHLVL=1
MYAPP_SVC_PORT_80_TCP_PROTO=tcp
HOME=/root
MYSQL_ROOT_PASSWORD=MyP@ss123   #查看已经把密码注入到了环境变量
... ...
... ...

以上是关于九,configMap及secret的基本使用的主要内容,如果未能解决你的问题,请参考以下文章

k8s之安全信息(Secret)及配置信息(ConfigMap)

k8s之安全信息(secret)及配置信息(configmap)管理

KUBERNETES05_NFS坏境搭建PVPVC挂载目录ConfigMap挂载文件Secret挂载敏感信息

KUBERNETES05_NFS坏境搭建PVPVC挂载目录ConfigMap挂载文件Secret挂载敏感信息

k8s的configMap基本概念及案例

k8s 配置存储之 Configmap & secret