生产环境中很多应用程序的配置可能需要通过配置文件,命令行参数和环境变量的组合配置来完成。这些配置应该从image中解耦,以此来保持容器化应用程序的可移植性。在K8S1.2后引入ConfigMap来处理这种类型的配置数据。
Configmap用于保存服务的配置数据,以键值对形式存储。configMap 资源提供了向 Pod 注入配置数据的方法。旨在让镜像和配置文件解耦,以便实现镜像的可移植性和可复用性。典型的使用场景: 填充环境变量的值设置容器内的命令行参数填充卷的配置文件创建ConfigMap的方式有4种: • 使用字面值创建 • 使用文件创建 • 使用目录创建 • 编写configmap的yaml文件创建
可以发现通过目录进行创建的时候,是把目录内的文件作为,key, 其内容作为 value。
更改一下:
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管理的是配置数据,是和服务挂钩的,当服务配置发生改变时,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端口了