Kubernetes(k8s)配置檔案管理:ConfigMap

人生的哲理發表於2023-02-02

一.系統環境

伺服器版本 docker軟體版本 Kubernetes(k8s)叢集版本 CPU架構
CentOS Linux release 7.4.1708 (Core) Docker version 20.10.12 v1.21.9 x86_64

Kubernetes叢集架構:k8scloude1作為master節點,k8scloude2,k8scloude3作為worker節點

伺服器 作業系統版本 CPU架構 程式 功能描述
k8scloude1/192.168.110.130 CentOS Linux release 7.4.1708 (Core) x86_64 docker,kube-apiserver,etcd,kube-scheduler,kube-controller-manager,kubelet,kube-proxy,coredns,calico k8s master節點
k8scloude2/192.168.110.129 CentOS Linux release 7.4.1708 (Core) x86_64 docker,kubelet,kube-proxy,calico k8s worker節點
k8scloude3/192.168.110.128 CentOS Linux release 7.4.1708 (Core) x86_64 docker,kubelet,kube-proxy,calico k8s worker節點

二.前言

使用ConfigMap的前提是已經有一套可以正常執行的Kubernetes叢集,關於Kubernetes(k8s)叢集的安裝部署,可以檢視部落格《Centos7 安裝部署Kubernetes(k8s)叢集》https://www.cnblogs.com/renshengdezheli/p/16686769.html。

三.ConfigMap概覽

ConfigMap 是一種 API 物件,用來將非機密性的資料儲存到鍵值對中。使用時, Pods 可以將其用作環境變數、命令列引數或者儲存卷中的配置檔案。

ConfigMap 是一個 API 物件, 讓你可以儲存其他物件所需要使用的配置。 和其他 Kubernetes 物件都有一個 spec 不同的是,ConfigMap 使用 data 和 binaryData 欄位。這些欄位能夠接收鍵-值對作為其取值。data 和 binaryData 欄位都是可選的。data 欄位設計用來儲存 UTF-8 字串,而 binaryData 則被設計用來儲存二進位制資料作為 base64 編碼的字串。

ConfigMap 的名字必須是一個合法的 DNS 子域名。

data 或 binaryData 欄位下面的每個鍵的名稱都必須由字母數字字元或者 -、_ 或 . 組成。在 data 下儲存的鍵名不可以與在 binaryData 下出現的鍵名有重疊。

從 v1.19 開始,你可以新增一個 immutable 欄位到 ConfigMap 定義中, 建立不可變更的 ConfigMap。

ConfigMap 將你的環境配置資訊和 容器映象 解耦,便於應用配置的修改

注意ConfigMap 並不提供保密或者加密功能。 如果你想儲存的資料是機密的,請使用 Secret,關於secret的使用請檢視部落格《Kubernetes(k8s)密碼管理:Secret》, 或者使用其他第三方工具來保證你的資料的私密性,而不是用 ConfigMap。

ConfigMap的用途如下:使用 ConfigMap 來將你的配置資料和應用程式程式碼分開。

  • 比如,假設你正在開發一個應用,它可以在你自己的電腦上(用於開發)和在雲上 (用於實際流量)執行。 你的程式碼裡有一段是用於檢視環境變數 DATABASE_HOST,在本地執行時, 你將這個變數設定為 localhost,在雲上,你將其設定為引用 Kubernetes 叢集中的 公開資料庫元件的 服務。

這讓你可以獲取在雲中執行的容器映象,並且如果有需要的話,在本地除錯完全相同的程式碼。

ConfigMap 在設計上不是用來儲存大量資料的。在 ConfigMap 中儲存的資料不可超過 1 MiB。如果你需要儲存超出此尺寸限制的資料,你可能希望考慮掛載儲存卷 或者使用獨立的資料庫或者檔案服務。

四.建立ConfigMap

查詢configmap

[root@k8scloude1 secret-manage]# kubectl get cm
NAME               DATA   AGE
kube-root-ca.crt   1      5h29m

configmap的建立方式和secret類似,可以使用鍵值對,也可以使用檔案

使用鍵值對建立configmap

[root@k8scloude1 secret-manage]# kubectl create cm cm1 --from-literal=xioaming=zxc --from-literal=bob=plm
configmap/cm1 created

[root@k8scloude1 secret-manage]# kubectl get cm
NAME               DATA   AGE
cm1                2      4s
kube-root-ca.crt   1      5h31m

檢視configmap的詳細內容

[root@k8scloude1 secret-manage]# kubectl describe cm cm1 
Name:         cm1
Namespace:    secret-manage
Labels:       <none>
Annotations:  <none>

Data
====
bob:
----
plm
xioaming:
----
zxc
Events:  <none>

以yaml格式檢視configmap

[root@k8scloude1 secret-manage]# kubectl get cm cm1 -o yaml
apiVersion: v1
data:
  bob: plm
  xioaming: zxc
kind: ConfigMap
metadata:
  creationTimestamp: "2022-01-21T09:25:32Z"
  name: cm1
  namespace: secret-manage
  resourceVersion: "890529"
  selfLink: /api/v1/namespaces/secret-manage/configmaps/cm1
  uid: bdbb0647-dfe9-45ec-827d-9af2ea12a0a1

使用檔案建立configmap

[root@k8scloude1 secret-manage]# kubectl create cm cm2 --from-file=/etc/shadow --from-file=/etc/hosts
configmap/cm2 created

[root@k8scloude1 secret-manage]# kubectl create cm cm3 --from-file=nginx.conf 
configmap/cm3 created

[root@k8scloude1 secret-manage]# kubectl get cm
NAME               DATA   AGE
cm1                2      4m18s
cm2                2      22s
cm3                1      4s
kube-root-ca.crt   1      5h35m

五.ConfigMap的使用

5.1 以環境變數的方式使用ConfigMap

使用MySQL映象建立pod,以環境變數的方式引用ConfigMap

[root@k8scloude1 secret-manage]# vim mysqlconfgmap.yaml 

#configMapKeyRef:指定confgmap的名字和key
[root@k8scloude1 secret-manage]# cat mysqlconfgmap.yaml 
apiVersion: v1
kind: Pod
metadata:
  creationTimestamp: null
  labels:
    run: mysql
  name: mysql
spec:
  terminationGracePeriodSeconds: 0
  containers:
  - image: hub.c.163.com/library/mysql:latest
    imagePullPolicy: IfNotPresent
    name: mysql
    resources: {}
    env:
    - name: MYSQL_ROOT_PASSWORD
      valueFrom:
        configMapKeyRef:
          name: cm1
          key: xioaming
  dnsPolicy: ClusterFirst
  restartPolicy: Always
status: {}

建立pod

[root@k8scloude1 secret-manage]# kubectl apply -f mysqlconfgmap.yaml 
pod/mysql created

[root@k8scloude1 secret-manage]# kubectl get pod -o wide
NAME    READY   STATUS    RESTARTS   AGE   IP               NODE         NOMINATED NODE   READINESS GATES
mysql   1/1     Running   0          24s   10.244.112.139   k8scloude2   <none>           <none>

連線mysql資料庫

[root@k8scloude1 secret-manage]# mysql -uroot -pzxc -h 10.244.112.139
Welcome to the MariaDB monitor.  Commands end with ; or \g.
Your MySQL connection id is 3
Server version: 5.7.18 MySQL Community Server (GPL)

Copyright (c) 2000, 2018, Oracle, MariaDB Corporation Ab and others.

Type 'help;' or '\h' for help. Type '\c' to clear the current input statement.

MySQL [(none)]> exit
Bye

檢視mysql pod的mysql密碼MYSQL_ROOT_PASSWORD,mysql密碼沒有顯示

[root@k8scloude1 secret-manage]# kubectl describe pod mysql | grep -A10 Environment
    Environment:
      MYSQL_ROOT_PASSWORD:  <set to the key 'xioaming' of config map 'cm1'>  Optional: false
    Mounts:
      /var/run/secrets/kubernetes.io/serviceaccount from kube-api-access-dllmm (ro)
Conditions:
  Type              Status
  Initialized       True 
  Ready             True 
  ContainersReady   True 
  PodScheduled      True 
Volumes:

刪除pod

[root@k8scloude1 secret-manage]# kubectl delete pod mysql --force
warning: Immediate deletion does not wait for confirmation that the running resource has been terminated. The resource may continue to run on the cluster indefinitely.
pod "mysql" force deleted

5.2 以卷的方式使用ConfigMap

配置pod,以卷的方式引用configmap,掛載cm3的nginx.conf到/etc/nginx/nginx.conf

[root@k8scloude1 secret-manage]# vim volumenginxconfconfigmap.yaml 

[root@k8scloude1 secret-manage]# cat volumenginxconfconfigmap.yaml 
apiVersion: v1
kind: Pod
metadata:
  creationTimestamp: null
  labels:
    run: nginx
  name: nginx
spec:
  terminationGracePeriodSeconds: 0
  #定義configmap型別的卷
  volumes:
  - name: configmap1
    configMap:
      name: cm3
  containers:
  - image: nginx
    imagePullPolicy: IfNotPresent
    name: nginx
    resources: {}
    #把nginx.conf檔案掛載到/etc/nginx/nginx.conf
    volumeMounts:
    - name: configmap1
      mountPath: /etc/nginx/nginx.conf
      subPath: nginx.conf
  dnsPolicy: ClusterFirst
  restartPolicy: Always
status: {}

建立pod

[root@k8scloude1 secret-manage]# kubectl apply -f volumenginxconfconfigmap.yaml 
pod/nginx created

[root@k8scloude1 secret-manage]# kubectl get pod -o wide
NAME    READY   STATUS    RESTARTS   AGE   IP               NODE         NOMINATED NODE   READINESS GATES
nginx   1/1     Running   0          9s    10.244.112.141   k8scloude2   <none>           <none>

進入Nginx容器

[root@k8scloude1 secret-manage]# kubectl exec -it nginx -- bash
root@nginx:/# cat /etc/nginx/nginx.conf | head -3
##modify file
user  nginx;
worker_processes  auto;
root@nginx:/# exit
exit

可以使用edit編輯nginx.conf檔案

[root@k8scloude1 secret-manage]# kubectl edit cm cm3
configmap/cm3 edited

檢視修改過後的configmap內容

[root@k8scloude1 secret-manage]# kubectl get cm cm3 -o yaml | head -7
apiVersion: v1
data:
  nginx.conf: |+
    ##modify file
    ##new add
    user  nginx;
    worker_processes  auto;

進入容器檢視Nginx的配置檔案,可以發現:cm3裡檔案內容已經改變了,但是容器裡檔案內容沒變。

pod裡的配置檔案nginx.conf沒有變化,需要重新建立pod

[root@k8scloude1 secret-manage]# kubectl exec -it nginx -- bash
root@nginx:/# cat /etc/nginx/nginx.conf | head -3
##modify file
user  nginx;
worker_processes  auto;
root@nginx:/# exit
exit

刪除pod並重新建立pod

[root@k8scloude1 secret-manage]# kubectl delete pod nginx --force
warning: Immediate deletion does not wait for confirmation that the running resource has been terminated. The resource may continue to run on the cluster indefinitely.
pod "nginx" force deleted

[root@k8scloude1 secret-manage]# kubectl apply -f volumenginxconfconfigmap.yaml 
pod/nginx created

此時nginx.conf檔案內容已經改變了,就達到了修改configmap檔案,從而改變容器裡配置檔案的目的。

[root@k8scloude1 secret-manage]# kubectl exec -it nginx -- bash
root@nginx:/# cat /etc/nginx/nginx.conf | head -3
##modify file
##new add
user  nginx;
root@nginx:/# exit
exit

檢視所有的configmap

[root@k8scloude1 secret-manage]# kubectl get cm -A
NAMESPACE         NAME                                 DATA   AGE
default           kube-root-ca.crt                     1      12d
kube-node-lease   kube-root-ca.crt                     1      12d
kube-public       cluster-info                         1      12d
kube-public       kube-root-ca.crt                     1      12d
kube-system       calico-config                        4      12d
kube-system       coredns                              1      12d
kube-system       extension-apiserver-authentication   6      12d
kube-system       kube-proxy                           2      12d
kube-system       kube-root-ca.crt                     1      12d
kube-system       kubeadm-config                       2      12d
kube-system       kubelet-config-1.21                  1      12d
ns1               kube-root-ca.crt                     1      11d
ns2               kube-root-ca.crt                     1      11d
pod               kube-root-ca.crt                     1      9d
secret-manage     cm1                                  2      33m
secret-manage     cm2                                  2      29m
secret-manage     cm3                                  1      12m
secret-manage     kube-root-ca.crt                     1      6h5m
volume            kube-root-ca.crt                     1      3d5h

可以編輯其他的configmap內容

[root@k8scloude1 secret-manage]# kubectl edit cm calico-config -n kube-system
Edit cancelled, no changes made.

[root@k8scloude1 secret-manage]# kubectl edit cm kube-proxy -n kube-system
Edit cancelled, no changes made.