1、在yaml文件中配置环境变量
(1)、配置固定值环境变量
env:
- name: INTERVAL
value: "30"
2、通过configmap配置环境变量
Kubemetes 允许将配置选项分离到单独的资源对象 ConfigMap 中, 本质上就是一个键 / 值对映射,值可以是短字面量,也可以是完整的配置文件 。
(1)、可以通过文件来创建comfigMap
kubectl create configmap fortune-config --from-file=configmap-files
(2)、引用cm
volumeMounts:
- name: config
mountPath: /etc/nginx/conf.d --挂载configMap卷到这个目录
readOnly: true
...
volumes:
- name: config
configMap:
name: fortune-config --卷定义引用configMap fortune-config
(3)、 挂载某一文件夹会隐藏该文件夹中已存在的文件
将卷挂载至某个文件夹,意味着容器镜像中/etc/nginx/conf.d文件夹下原本存在的任何文件都会被隐藏。
Linux 系统挂载文件系统至非空文件夹时通常表现如此。文件夹中只会包含被挂载文件系统中的文件,即便文件夹中原本的文件是不可访问的也是同样如此。
(4)、 ConfigMap独立文件被挂载且不隐藏文件夹中的其他文件
volumeMounts:
- name: myvolume
mountPath: /etc/someconfig.conf --挂载到某一文件,而不是文件夹
subPath: myconfig.conf --仅挂载指定的条目 myconfig.conf,而不是完整的configMap 卷
(5)、更新应用配置且不重启应用程序 (挂载完整卷才会自动加载,如果只是挂载卷中的某个文件则不会)
使用环境变量或者命令行参数作为配置源的弊端在于无法在进程运行时更新配置。 将ConfigMap暴露为卷可以达到配置热更新的效果, 无须重新创建pod或者重启容器。
ConfgMap被更新之后, 卷中引用它的所有文件也会相应更新, 进程发现文件被改变之后进行重载。 Kubemetes同样支待文件更新之后手动通知容器。
3、两种创建configmap的方式
(1)、通过yaml文件创建
apiVersion: v1
kind: ConfigMap
metadata:
name: test-cfg
namespace: default
data:
cache_host: memcached-gcxt
cache_port: "11211"
cache_prefix: gcxt
my.cnf: |
[mysqld]
log-bin = mysql-bin
app.properties: |
property.1 = value-1
property.2 = value-2
property.3 = value-3
kubectl create -f test-cfg.yml
(2)、通过命令行创建
kubectl create configmap test-config --from-file=./configs --configs是实际配置文件
kubectl create configmap test-config3 --from-literal=db.host=10.5.10.116 --from-listeral=db.port='3306' --在命令行中传递参数
4、configmap挂载使用的三种方式
(1)、直接传递给pod(cm中定义的是key-value形式时使用)
apiVersion: v1
kind: ConfigMap
metadata:
name: special-config
namespace: default
data:
special.how: very
special.type: charm
---
apiVersion: v1
kind: Pod
metadata:
name: dapi-test-pod
spec:
containers:
- name: test-container
image: gcr.io/google_containers/busybox
command: [ "/bin/sh", "-c", "env" ]
env:
- name: SPECIAL_LEVEL_KEY
valueFrom:
configMapKeyRef:
name: special-config
key: special.how
- name: SPECIAL_TYPE_KEY
valueFrom:
configMapKeyRef:
name: special-config
key: special.type
restartPolicy: Never
(2)、通过在pod命令行下引用
apiVersion: v1
kind: ConfigMap
metadata:
name: special-config
namespace: default
data:
special.how: very
special.type: charm
---
apiVersion: v1
kind: Pod
metadata:
name: dapi-test-pod
spec:
containers:
- name: test-container
image: gcr.io/google_containers/busybox
command: [ "/bin/sh", "-c", "echo $(SPECIAL_LEVEL_KEY) $(SPECIAL_TYPE_KEY)" ]
env:
- name: SPECIAL_LEVEL_KEY
valueFrom:
configMapKeyRef:
name: special-config
key: special.how
- name: SPECIAL_TYPE_KEY
valueFrom:
configMapKeyRef:
name: special-config
key: special.type
restartPolicy: Never
(3)、使用volume将ConfigMap作为文件或目录直接挂载,其中每一个key-value键值对都会生成一个文件,key为文件名,value为内容,下面是一个示例。
此种引用方式一般在comfigMap是通过配置文件创建的时候使用,可以直接将某个配置文件或者某些配置文件挂载到容器的指定目录下
apiVersion: v1
kind: ConfigMap
metadata:
name: special-config
namespace: default
data:
special.how: very
special.type: charm
--
apiVersion: v1
kind: Pod
metadata:
name: dapi-test-pod
spec:
containers:
- name: test-container
image: gcr.io/google_containers/busybox
command: [ "/bin/sh", "-c", "cat /etc/config/special.how" ]
volumeMounts:
- name: config-volume
mountPath: /etc/config
volumes:
- name: config-volume
configMap:
name: special-config
restartPolicy: Never
5、问题:configMap热更新讨论测试?
测试一:更新使用ConfigMap挂载的Env
#vim nginx-cm.yaml
apiVersion: v1
kind: ConfigMap
metadata:
name: env-config
namespace: default
data:
log_level: INFO
#vim nginx-deployment.yaml
apiVersion: extensions/v1beta1
kind: Deployment
metadata:
name: my-nginx
spec:
replicas: 1
template:
metadata:
labels:
app: my-nginx
spec:
containers:
- name: my-nginx
image: nginx:1.10
ports:
- containerPort: 80
envFrom:
- configMapRef:
name: env-config
等待应用启动之后,进入应用pod容器查看环境变量:
env|grep log_level
#输出:
log_level=INFO
修改configmap:env-config,修改日志登记为DEBUG,再次进入应用pod容器查看环境变量,发现日志等级没有发生任何变化。
重启应用,再次进入应用pod容器,查看环境变量,发现环境变量log_level=DEBUG。
测试结果:未实现热更新,需要重启应用才能生效。
测试二:更新使用ConfigMap挂载的Volume
#vim nginx-cm2.yaml
apiVersion: v1
kind: ConfigMap
metadata:
name: special-config
namespace: default
data:
log_level: INFO
#vim nginx-deployment-v.yaml
apiVersion: extensions/v1beta1
kind: Deployment
metadata:
name: my-nginx-2
spec:
replicas: 1
template:
metadata:
labels:
app: my-nginx-2
spec:
containers:
- name: my-nginx-2
image: nginx:1.10
ports:
- containerPort: 80
volumeMounts:
- name: config-volume
mountPath: /etc/config
volumes:
- name: config-volume
configMap:
name: special-config
等待应用启动后,进入应用pod容器查看环境变量:
cat /etc/config/log_level
#输出:
INFO
修改configmap:special-config,修改日志登记为DEBUG,再次进入应用pod容器查看环境变量,一分钟左右发现日志级别发生改变。从INFO变化为DEBUG。
测试结果:实现热更新。
结论:
更新 ConfigMap 后:
(1)、使用该 ConfigMap 挂载的 Env 不会同步更新
(2)、使用该 ConfigMap 挂载的 Volume 中的数据需要一段时间(实测大概1分钟)才能同步更新
ENV 是在容器启动的时候注入的,启动之后 kubernetes 就不会再改变环境变量的值。
更多文章请关注我的知乎账号:https://www.zhihu.com/people/dengjiabo/activities