Pod的配置管理

一笑奈何 提交于 2020-04-05 14:57:56

在Kubernetes中,资源对象和信息都存储在Etcd中,但是对于某一个服务的配置该如何管理了?
当然你可以在镜像打包的时候,将配置文件直接配置打包到镜像里面,这样确实可以达到目的。
但是大部分的容器是在运行之后需要改配置,每次都重新打包确实会是一个不小的工作。
当然可以通过文件映射或者环境变量来改变容器的配置,这是稍微比较不错的做法。
但是如果在大规模集群中,容器的配置管理将是一个非常麻烦的事项。
Kubernetes从1.2开始提供一种统一的应用配置管理方案——ConfigMap。
ConfigMap将应用所需的配置信息与程序进行分离,这样配置信息可以更好的被多次复用。
在Kubernetes中,配置信息会被封装成一个个资源资源对象,这样便于集中管理和使用。

如果你需要修改配置,那么只需要修改ConfigMap的引用对象或者直接修改ConfigMao资源对象的配置就可以了。

1.ConfigMap

ConfigMap供容器使用的典型用法如下:
(1)生成为容器内的环境变量
(2)以Volume的形式挂载为容器内部的文件或者目录
ConfigMap以一个或多个key:value的形式保存在Kubernetes系统中供应用使用,
既可以用于表示一个变量的值(例如apploglevel=info),也可以用于表示一个一个完整配置文件的内容(server.xml=<?xml>)。

 

2.创建ConfigMap资源对象

(1)通过yaml配置文件方式创建

apiVersion: v1
kind: ConfigMap
metadata:
  name: cm-appvars
data:
  apploglevel: info  #将值指定为字符串
  appdatadir: /var/data  #指定为文件名或者目录

ConfigMap是以键值(key=value)对的形式保存配置信息,key可以是任何不重复字符串,value可以是字符串也可以是文件名目录名。

#创建configmap资源对象
root@console:/k8s-script/chapter02# kubectl create -f cm-appvars.yaml 
configmap "cm-appvars" created

#查看configMap资源对象
root@console:/k8s-script/chapter02# kubectl get configmap
NAME         DATA      AGE
cm-appvars   2         15s

#查看资源对象的详细信息
root@console:/k8s-script/chapter02# kubectl describe configmap/cm-appvars
Name:         cm-appvars
Namespace:    default
Labels:       <none>
Annotations:  <none>

Data
====
appdatadir:
----
/var/data
apploglevel:
----
info
Events:  <none>

#以yaml的格式输出资源对象的详细
root@console:/k8s-script/chapter02# kubectl get configmap/cm-appvars -o yaml
apiVersion: v1
data:
  appdatadir: /var/data
  apploglevel: info
kind: ConfigMap
metadata:
  creationTimestamp: 2019-07-08T03:27:17Z
  name: cm-appvars
  namespace: default
  resourceVersion: "117304"
  selfLink: /api/v1/namespaces/default/configmaps/cm-appvars
  uid: 49baf4d4-a130-11e9-9c97-52540095a842

Kubernetes还支持将配置文件的内容定义为ConfigMap的用法。

apiVersion: v1
kind: ConfigMap
metadata:
  name: cm-appconfigfiles
data:
  key-config.json: '{
    "server":"192.168.1.1",
    "server_port":8038,
    "password":"666666",
    "timeout":300,
    "method":"aes-256-cfb",
    "fast_open": false
}'

相关操作:

#创建ConfigMap资源对象
root@console:/k8s-script/chapter02# kubectl create -f cm-appconfigfiles.yaml 
configmap "cm-appconfigfiles" created
#查看ConfigMap资源对象
root@console:/k8s-script/chapter02# kubectl get configmap
NAME                DATA      AGE
cm-appconfigfiles   1         16s
cm-appvars          2         28m
#查看资源对象的详细信息
root@console:/k8s-script/chapter02# kubectl describe configmap/cm-appconfigfiles
Name:         cm-appconfigfiles
Namespace:    default
Labels:       <none>
Annotations:  <none>

Data
====
key-config.json:
----
{ "server":"192.168.1.1", "server_port":8038, "password":"666666", "timeout":300, "method":"aes-256-cfb", "fast_open": false }
Events:  <none>

(2)通过kubectl命令行方式创建

不使用yaml文件,直接通过kubectl create configmap也可以创建ConfigMap,
可以使用参数--from-file或--from-literal指定内容,并且可以在一行命令中指定多个参数。

A.通过--from-file参数从文件中进行创建,可以指定key的名称,也可以在一个命令行中创建多个key的ConfigMap。

root@console:~# kubectl create configmap cm-ssh-config.xml --from-file=ssh_config
configmap "cm-ssh-config.xml" created
root@console:~# kubectl get configmap
NAME                DATA      AGE
cm-appconfigfiles   1         2h
cm-appvars          2         2h
cm-ssh-config.xml   1         17s

  B.通过--from-file参数从目录中进行创建,该目录的每个配置文件名都被设置为key,文件的内容被设置为value。

root@console:~# kubectl create configmap cm-appconf --from-file=configfiles
configmap "cm-appconf" created
root@console:~# kubectl describe configmap cm-appconf
Name:         cm-appconf
Namespace:    default
Labels:       <none>
Annotations:  <none>

Data
====
server.xml:
----

logging.properties:
----

Events:  <none>

  C.--from-literal从文本中进行创建,直接将指定的key#=value#创建为ConfigMap。

root@console:~# kubectl create configmap cm-appenv --from-literal=loglevel=info --from-literal=appdatadir=/var/data
configmap "cm-appenv" created
root@console:~# kubectl describe configmap/cm-appenv
Name:         cm-appenv
Namespace:    default
Labels:       <none>
Annotations:  <none>

Data
====
appdatadir:
----
/var/data
loglevel:
----
info
Events:  <none>

 

3.在Pod中使用ConfigMap

(1)通过环境变量使用ConfigMap

apiVersion: v1
kind: Pod
metadata:
  name: cm-test-pod
spec:
  containers:
  - name: cm-test
    image: busybox:latest
    command: ["/bin/sh","-c","env|grep APP"]
    env:
    - name: APPLOGLEVEL
      valueFrom:
        configMapKeyRef:
          name: cm-appvars
          key: apploglevel
    - name: APPDATADIR
      valueFrom:
        configMapKeyRef:
          name: cm-appvars
          key: appdatadir

在创建cm-test-pod这个Pod的时候,将cm-appvars这个configmap中内容以环境变量的方式进行引入。
并且在容器进行启动的时候显示这个两个环境变量的值。

root@console:/k8s-script/chapter02# kubectl create -f cm-test-pod.yaml 
pod "cm-test-pod" created
#查看日志,确定已经引入到了环境变量中
root@console:/k8s-script/chapter02# kubectl logs cm-test-pod
APPDATADIR=/var/data
APPLOGLEVEL=info

从kubernetes1.6版本开始,引入了一个新的字段envFrom,
实现在Pod环境内直接将ConfigMap中所定义的key=value自动生成环境变量。

apiVersion: v1
kind: Pod
metadata:
  name: cm-test-pod2
spec:
  containers:
  - name: cm-test
    image: busybox:latest
    imagePullPolicy: Never
    command: ["/bin/sh","-c","env"]
    envFrom:
    - configMapRef:
        name: cm-appvars

相关操作:

#创建Pod
root@console:/k8s-script/chapter02# kubectl create -f cm-test-pod2.yaml
pod "cm-test-pod2" created
#查看环境变量
root@console:/k8s-script/chapter02# kubectl log cm-test-pod2|grep app
apploglevel=info
appdatadir=/var/data

(2)通过volumeMount使用ConfigMap

apiVersion: v1
kind: Pod
metadata:
  name: cm-test-app
spec:
  volumes:
  - name: serverxml
    configMap:
      name: cm-appconf
      items:
      - key: key-serverxml
        path: server.xml
      - key: key-logging.properties
        path: logging.properties
  containers:
  - name: cm-test-app
    image: kubeguide/tomcat-app:v1
    ports:
    - containerPort: 8080
    volumeMounts:
    - name: serverxml
      mountPath: /configfiles

 

4.使用ConfigMap的限制条件

(1)ConfigMap必须在Pod之前创建
(2)COnfigMap受Namespace限制,只能处于相同Namespaces中的Pod可以引用它
(3)ConfigMap中的配额管理还未能实现
(4)kubelet只支持可以被API Server管理的Pod使用ConfigMap。
kubelet在本Node上通过--manifest-url或--config自动创建的静态Pod将无法引用ConfigMap
(5)在Pod对ConfigMap进行挂载(volumeMount)操作时,容器内部只能挂载为“目录”,无法挂载为“文件”。
在挂载到容器内部后,目录中将包含ConfigMap定义的每个item,如果该目录下原来还有其它文件,
则容器内的该目录将会被挂载的ConfigMap覆盖。如果应用程序需要保留原来的其它文件,则需要进行额外的处理。
可以将ConfigMap挂载到容器内部的临时目录,再通过启动脚本将配置文件复制或链接到应用所用的实际配置目录下。

易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!