kubernetes存儲 -- Configmap應用配置管理

簡介

生產環境中很多應用程序的配置可能需要通過配置文件,命令行參數和環境變量的組合配置來完成。這些配置應該從image中解耦,以此來保持容器化應用程序的可移植性。在K8S1.2後引入ConfigMap來處理這種類型的配置數據。

  • Configmap用於保存服務的配置數據,以鍵值對形式存儲。
  • configMap 資源提供了向 Pod 注入配置數據的方法。
  • 旨在讓鏡像和配置文件解耦,以便實現鏡像的可移植性可複用性
  • 典型的使用場景:
    • 填充環境變量的值
    • 設置容器內的命令行參數
    • 填充卷的配置文件

創建ConfigMap

創建ConfigMap的方式有4種:
• 使用字面值創建
• 使用文件創建
• 使用目錄創建
• 編寫configmap的yaml文件創建

使用字面值創建

[root@server2 manifest]# kubectl create configmap mycm --from-literal=wo=caoaoyuan --from-literal=ni=liuyan
configmap/mycm created							/cm名,任意							/輸入健值對
[root@server2 manifest]# kubectl get cm
NAME   DATA   AGE
mycm   2      115s
[root@server2 manifest]# kubectl describe cm mycm 
Name:         mycm
Namespace:    default
Labels:       <none>
Annotations:  <none>

Data
====
ni:
----
liuyan
wo:
----
caoaoyuan
Events:  <none>

文件的形式

[root@server2 manifest]# kubectl create configmap my-config-2 --from-file=/etc/resolv.conf
configmap/my-config-2 created
[root@server2 manifest]# kubectl get cm
NAME          DATA   AGE
my-config-2   1      7s
mycm          2      4m4s

[root@server2 manifest]# kubectl describe cm my-config-2 
Name:         my-config-2
Namespace:    default
Labels:       <none>
Annotations:  <none>

Data
====
resolv.conf:			//key的名稱是文件名稱
----
3
nameserver 114.114.114.114			//value的值是這個文件的內容

Events:  <none>

[root@server2 manifest]# cat /etc/resolv.conf

nameserver 114.114.114.114

通過目錄創建

[root@server2 ~]# mkdir test
[root@server2 ~]# cp /etc/resolv.conf test/
[root@server2 ~]# cp /etc/fstab test/
[root@server2 ~]# ls test/
fstab  resolv.conf

[root@server2 ~]# kubectl create configmap my-config-3 --from-file=test
configmap/my-config-3 created
[root@server2 ~]# kubectl describe cm my-config-3
Name:         my-config-3
Namespace:    default
Labels:       <none>
Annotations:  <none>

Data
====
fstab:
----

#
# /etc/fstab
# Created by anaconda on Tue Apr 28 02:35:30 2020
#
# Accessible filesystems, by reference, are maintained under '/dev/disk'
# See man pages fstab(5), findfs(8), mount(8) and/or blkid(8) for more info
#
/dev/mapper/rhel-root   /                       xfs     defaults        0 0
UUID=004d1dd6-221a-4763-a5eb-c75e18655041 /boot                   xfs     defaults        0 0
#/dev/mapper/rhel-swap   swap                    swap    defaults        0 0

resolv.conf:
----

nameserver 114.114.114.114

Events:  <none>

可以發現通過目錄進行創建的時候,是把目錄內的文件作爲,key, 其內容作爲 value。

編寫configmap的yaml文件

[root@server2 ~]# mkdir cm
[root@server2 ~]# cd cm/
[root@server2 cm]# vim cm1.yml
apiVersion: v1
kind: ConfigMap
metadata:
  name: cm1-config
data:
  db_host: "172.25.0.250"		//還是健值對的形式
  db_port: "3306"
  
[root@server2 cm]# kubectl create -f cm1.yaml
[root@server2 cm]# kubectl describe cm cm1
Name:         cm1-config
Namespace:    default
Labels:       <none>
Annotations:  
Data
====
db_host:
----
172.25.0.250
db_port:
----
3306
Events:  <none>

如何使用configmap

  1. 通過環境變量的方式直接傳遞給pod
  2. 通過在pod的命令行下運行的方式
  3. 作爲volume的方式掛載到pod內

通過環境變量

方式一:重新定義

[root@server2 cm]# vim  cm1.yml
apiVersion: v1
kind: ConfigMap
metadata:
  name: cm1-config
data:
  db_host: "172.25.0.250"
  db_port: "3306"

---
apiVersion: v1
kind: Pod
metadata:
  name: pod1
spec:
  containers:
  - name: pod1
    image: busybox
    command: ["/bin/sh", "-c", "env"]			//啓用這個pod執行這個命令
    env:
    - name: key1			//環境變量名稱
      valueFrom:		//數據來源
        configMapKeyRef:
          name: cm1-config		//把configmap的數據應用到pod中
          key: db_host		//健是上面定義的key1,值是db_host的值
    - name: key2
      valueFrom:
        configMapKeyRef:
          name: cm1-config
          key: db_port
  restartPolicy: Never
[root@server2 cm]# kubectl apply -f cm1.yml 
configmap/cm1-config unchanged
pod/pod1 created
[root@server2 cm]# kubectl get pod
NAME   READY   STATUS      RESTARTS   AGE
pod1   0/1     Completed   0          6s			//執行命令後就完成了
[root@server2 cm]# kubectl logs pod1
KUBERNETES_SERVICE_PORT=443
KUBERNETES_PORT=tcp://10.96.0.1:443
HOSTNAME=pod1
SHLVL=1
HOME=/root
KUBERNETES_PORT_443_TCP_ADDR=10.96.0.1
PATH=/usr/local/sbin:/usr/local/bin:/usr/sbin:/usr/bin:/sbin:/bin
KUBERNETES_PORT_443_TCP_PORT=443
key1=172.25.0.250					//key1對應db_host值
KUBERNETES_PORT_443_TCP_PROTO=tcp
key2=3306							//key2對應db_port的值
KUBERNETES_SERVICE_PORT_HTTPS=443
KUBERNETES_PORT_443_TCP=tcp://10.96.0.1:443
KUBERNETES_SERVICE_HOST=10.96.0.1
PWD=/
[root@se

方式二:直接導入cm

[root@server2 cm]# vim cm1.yml
apiVersion: v1
kind: ConfigMap
metadata:
  name: cm1-config
data:
  db_host: "172.25.0.250"
  db_port: "3306"

---
apiVersion: v1
kind: Pod
metadata:
  name: pod1
spec:
  containers:
  - name: pod1
    image: busybox
    command: ["/bin/sh", "-c", "env"]
      envFrom:
      - configMapRef:
        name: cm1-config		///直接從cm中導入數據
  restartPolicy: Never
[root@server2 cm]# kubectl apply -f cm1.yml 
configmap/cm1-config unchanged
pod/pod1 created
[root@server2 cm]# kubectl get pod
NAME   READY   STATUS      RESTARTS   AGE
pod1   0/1     Completed   0          6s
[root@server2 cm]# kubectl logs pod1 
KUBERNETES_SERVICE_PORT=443
KUBERNETES_PORT=tcp://10.96.0.1:443
HOSTNAME=pod1
SHLVL=1
db_port=3306
...
db_host=172.25.0.250			//導入了cm中的值

使用conigmap設置命令行參數

[root@server2 cm]# vim cm1.yml
apiVersion: v1
kind: ConfigMap
metadata:
  name: cm1-config
data:
  db_host: "172.25.0.250"
  db_port: "3306"

---
apiVersion: v1
kind: Pod
metadata:
  name: pod1
spec:
  containers:
  - name: pod1
    image: busybox
    command: ["/bin/sh", "-c", "echo $(db_host) $(db_port)"]		//命令行中直接調用變量
    envFrom:
    - configMapRef:
      name: cm1-config
  restartPolicy: Never


[root@server2 cm]# kubectl apply -f cm1.yml 
configmap/cm1-config unchanged
pod/pod1 created
[root@server2 cm]# kubectl logs pod1 
172.25.0.250 3306			//調用出來了

通過數據卷使用configmap

[root@server2 cm]# vim cm1.yml
apiVersion: v1
kind: ConfigMap
metadata:
  name: cm1-config
data:
  db_host: "172.25.0.250"
  db_port: "3306"

---
apiVersion: v1
kind: Pod
metadata:
  name: pod1
spec:
  containers:
  - name: pod1
    image: busybox 
    command: ["/bin/sh", "-c", "cat /config/db_host"]		/查看改目錄下內容,沒有會自動創建
    volumeMounts:				/卷掛載
    - name: config-volume			/使用的卷的名稱
      mountPath: /config			/掛載點
  volumes:		/指定卷
  - name: config-volume			//指定卷名稱
    configMap:
      name: cm1-config				//映射到cm上,

[root@server2 cm]# kubectl apply -f cm1.yml 
configmap/cm1-config unchanged
pod/pod1 created
[root@server2 cm]# kubectl logs pod1 
172.25.0.250			db_host的值

更改一下:

    command: ["/bin/sh", "-c", "cat /config/db_port"]		/改爲查看端口

[root@server2 cm]# kubectl apply -f cm1.yml 
configmap/cm1-config unchanged
pod/pod1 created
[root@server2 cm]# kubectl logs pod1 
3306

這樣就明白了吧。
我們還可以登陸進去看一下。

[root@server2 cm]# cat cm1.yml 
...(省略)
spec:
  containers:
  - name: pod1
    image: nginx 	/換爲nginx鏡像
    volumeMounts:
    - name: config-volume
      mountPath: /config
  volumes:
  - name: config-volume
    configMap:
      name: cm1-config
[root@server2 cm]# kubectl apply -f cm1.yml 
configmap/cm1-config unchanged
pod/pod1 created
[root@server2 cm]# kubectl exec -it pod1 -- bash
root@pod1:/# cd /config/
root@pod1:/config# ls
db_host  db_port

root@pod1:/config# cat db_host 
172.25.0.250
root@pod1:/config# cat db_port 
3306root@pod1:/config# 

configmap熱更新

configmap管理的是配置數據,是和服務掛鉤的,當服務配置發生改變時,cm 也應該進行熱更新。

就比如我們上面的 cm 中有兩個數據, db_host 、db_port,當他們的數據發生改變時,會不會進行熱更新哪。

[root@server2 cm]# kubectl edit cm cm1-config 		//直接編輯這個 cm
# Please edit the object below. Lines beginning with a '#' will be ignored,
# and an empty file will abort the edit. If an error occurs while saving this file will be
# reopened with the relevant failures.
#
apiVersion: v1
data:
  db_host: 172.25.0.100
  db_port: "3300"				//改變地址和端口
kind: ConfigMap

[root@server2 cm]# kubectl describe cm cm1-config 
Name:         cm1-config
Namespace:    default
Labels:       <none>
Annotations:  
Data
====
db_host:
----
172.25.0.100
db_port:
----
3300			//可見cm已經改變
Events:  <none>

那末pod中會不會自動進行更新哪?

[root@server2 cm]# kubectl exec -it pod1 -- cat /config/db_host
172.25.0.100
[root@server2 cm]# kubectl exec -it pod1 -- cat /config/db_port
3300

我們再外部更新完卷之後,pod內也發生了變化。但是pod的服務並沒有發生變化。
我們現在把 pod 內 nginx 的配置文件放到數據卷中,將 cm 和pod內的容器結合起來,當我們更改時,讓他自動熱更新到 pod 中 的 nginx 服務 中去。

這是我們就需要用到deployment的控制器來進行滾動更新。

[root@server2 cm]# vim server.conf				//編寫一個nginx的配置文件
server {
  listen	8000;				/ 修改一下端口
  server_name _;

  location / {
	root /usr/share/nginx/html;
	index index.html index.htm;
    }
}

[root@server2 cm]# kubectl create configmap nginx-config --from-file=server.conf 	//創建cm
configmap/nginx-config created
[root@server2 cm]# kubectl describe cm nginx-config 
Name:         nginx-config
Namespace:    default
Labels:       <none>
Annotations:  <none>

Data
====
server.conf:
----
server {
  listen  8000;
  server_name _;

  location / {
  root /usr/share/nginx/html;
  index index.html index.htm;
    }
}

Events:  <none>

創建控制器:

apiVersion: apps/v1
kind: Deployment
metadata:
  name: my-nginx
spec:
  replicas: 1
  selector:
    matchLabels:
      app: nginx
  template:
    metadata:
      labels:
        app: nginx
    spec:
      containers:
      - name: nginx
        image: nginx
        volumeMounts:
        - name: config-volume
          mountPath: /etc/nginx/conf.d		//掛載到include目錄下
      volumes:
      - name: config-volume
        configMap:
          name: nginx-config		//映射nginx-config 這個cm的數據
[root@server2 cm]# kubectl apply -f cm1.yml 
deployment.apps/my-nginx created
[root@server2 cm]# kubectl get pod -o wide
NAME                        READY   STATUS    RESTARTS   AGE   IP               NODE      NOMINATED NODE   READINESS GATES
my-nginx-575fd5b9c4-nmm4b   1/1     Running   0          34s   10.244.141.216   server3   <none>           <none>
[root@server2 cm]# curl 10.244.141.216
curl: (7) Failed connect to 10.244.141.216:80; Connection refused
[root@server2 cm]# curl 10.244.141.216:8000
<!DOCTYPE html>
<html>
<head>
<title>Welcome to nginx!</title>			//80端口訪問不到,8000端口生效了

登陸進pod中查看:

[root@server2 cm]# kubectl exec -it my-nginx-7db4c4f989-scdc4 --  cat /etc/nginx/conf.d/server.conf 
server {
  listen	8000;			/是8000端口
  server_name _;

  location / {
	root /usr/share/nginx/html;
	index index.html index.htm;
    }
}

熱更新:

[root@server2 cm]# kubectl edit cm nginx-config 			//編輯cm
data:
  server.conf: "server {\n  listen\t8080			端口換爲8080端口
  
[root@server2 cm]# kubectl exec my-nginx-7db4c4f989-scdc4 -- cat /etc/nginx/conf.d/server.conf
server {
  listen	8080;				/變成了8080端口
  server_name _;

  location / {
	root /usr/share/nginx/html;
	index index.html index.htm;
    }
}

但是pod仍然沒有改變,只是配置文件變了,還沒有觸發。

[root@server2 cm]# curl 10.244.22.11:8080
curl: (7) Failed connect to 10.244.22.11:8080; Connection refused
[root@server2 cm]# curl 10.244.22.11:8000
<!DOCTYPE html>
<html>
<head>
<title>Welcome to nginx!</title>		8000端口依然訪問,更新後的8080端口訪問不到

需要手動觸發Pod滾動更新, 這樣才能再次加載nginx.conf配置文件:

[root@server2 cm]# kubectl patch deployments.apps my-nginx --patch \ 
'{"spec": {"template":{"metadata": {"annotations": {"version/config": "2020062701"}}}}}'

my-nginx 指定控制器,因爲控制器下可能有多個pod
version/config": "20200219指定版本

這是之前的pod:
[root@server2 cm]# kubectl get pod -o wide
NAME                        READY   STATUS    RESTARTS   AGE   IP             NODE      NOMINATED NODE   READINESS GATES
my-nginx-7db4c4f989-scdc4   1/1     Running   0          16m   10.244.22.11   server4   <none>           <none>
[root@server2 cm]# kubectl patch deployments.apps my-nginx --patch '{"spec": {"template":{"metadata": {"annotations": {"version/config": "2020062701"}}}}}'
deployment.apps/my-nginx patched
[root@server2 cm]# kubectl get pod -o wide
NAME                        READY   STATUS              RESTARTS   AGE   IP             NODE      NOMINATED NODE   READINESS GATES
my-nginx-7db4c4f989-scdc4   1/1     Running             0          20m   10.244.22.11   server4   <none>           <none>
my-nginx-7f45d597d5-n7jft   0/1     ContainerCreating   0          4s    <none>         server3   <none>           <none>
[root@server2 cm]# kubectl get pod -o wide
NAME                        READY   STATUS        RESTARTS   AGE   IP               NODE      NOMINATED NODE   READINESS GATES
my-nginx-7db4c4f989-scdc4   0/1     Terminating   0          20m   <none>           server4   <none>           <none>
my-nginx-7f45d597d5-n7jft   1/1     Running       0          7s    10.244.141.217   server3   <none>           <none>

可以看出新建了一個pod,之前的pod已經刪除了

[root@server2 cm]# curl 10.244.141.217:8080				
<!DOCTYPE html>
<html>
<head>
<title>Welcome to nginx!</title>			/已經切換到8080端口了
發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章