容器中获取Pod信息
众所周知,Pod的逻辑概念是在容器之上的,Kubernetes创建Pod治好后,就会为Pod和相关的容器设定一些额外的信息,如pod的名称、IP、Node IP、Lable、Annotaion以及容器的相关的资源限制等,在很多的使用场景中,这些信息对容器内的应用有很大的用处,Kubernetes提供了Downward API机制来将Pod和容器的某些元数据信息注入到容器环境中以方便提供给容器中的应用使用。
Downward API可以通过以下两种方式将Pod和容器的元数据信息注入容器内部。
- 环境变量:将Pod或者容器信息设置为容器的环境变量。
- Volume挂载:将Pod或者容器信息以文件的形式挂载到容器内部。
环境变量方式
将Pod信息设置为容器内的环境变量
apiVersion: v1
kind: Pod
metadata:
name: dapi-envars-fieldref
spec:
containers:
- name: test-container
image: busybox
command: [ "sh", "-c"]
args:
- while true; do
echo -en '\n';
printenv MY_NODE_NAME MY_POD_NAME MY_POD_NAMESPACE;
printenv MY_POD_IP MY_POD_SERVICE_ACCOUNT;
sleep 10;
done;
env:
- name: MY_NODE_NAME
valueFrom:
fieldRef:
fieldPath: spec.nodeName # Pod所在的Node的名称
- name: MY_POD_NAME
valueFrom:
fieldRef:
fieldPath: metadata.name # Pod的名称
- name: MY_POD_NAMESPACE
valueFrom:
fieldRef:
fieldPath: metadata.namespace # Pod所在的命名空间的名称
- name: MY_POD_IP
valueFrom:
fieldRef:
fieldPath: status.podIP # Pod的IP地址
- name: MY_POD_SERVICE_ACCOUNT
valueFrom:
fieldRef:
fieldPath: spec.serviceAccountName # Pod使用的ServiceAccount名称
restartPolicy: Never
注意:环境变量不直接设置value,而是设置valueFrom对Pod的元数据进行引用
使用上述的YAML文件创建Pod,通过日志打印可将环境变量的值打印出来,可以通过日志看到Pod的Node IP、Pod的名称、命名空间的名称、Pod IP、ServiceAccount名称等相关的容器的环境变量。
将Container的信息设定为容器的环境变量
apiVersion: v1
kind: Pod
metadata:
name: dapi-envars-resourcefieldref
spec:
containers:
- name: test-container
image: busybox
imagePullPolicy: Never
command: [ "sh", "-c"]
args:
- while true; do
echo -en '\n';
printenv MY_CPU_REQUEST MY_CPU_LIMIT;
printenv MY_MEM_REQUEST MY_MEM_LIMIT;
sleep 10;
done;
resources:
requests:
memory: "32Mi"
cpu: "125m"
limits:
memory: "64Mi"
cpu: "250m"
env:
- name: MY_CPU_REQUEST
valueFrom:
resourceFieldRef:
containerName: test-container
resource: requests.cpu # 容器的CPU请求值
- name: MY_CPU_LIMIT
valueFrom:
resourceFieldRef:
containerName: test-container
resource: limits.cpu # 容器的CPU限制值
- name: MY_MEM_REQUEST
valueFrom:
resourceFieldRef:
containerName: test-container
resource: requests.memory # 容器的内存请求值
- name: MY_MEM_LIMIT
valueFrom:
resourceFieldRef:
containerName: test-container
resource: limits.memory # 容器的内存限制值
restartPolicy: Never
在上述的YAML文件中,通过Downward API将Container的资源限制信息设定为环境变量、
Volume挂载方式
将Pod信息挂载为容器内部文件
apiVersion: v1
kind: Pod
metadata:
name: kubernetes-downwardapi-volume-example
labels:
zone: us-est-coast
cluster: test-cluster1
rack: rack-22
annotations:
build: two
builder: john-doe
spec:
containers:
- name: client-container
image: busybox
command: ["sh", "-c"]
args:
- while true; do
if [[ -e /etc/podinfo/labels ]]; then
echo -en '\n\n'; cat /etc/podinfo/labels; fi;
if [[ -e /etc/podinfo/annotations ]]; then
echo -en '\n\n'; cat /etc/podinfo/annotations; fi;
sleep 5;
done;
volumeMounts:
- name: podinfo
mountPath: /etc/podinfo
volumes:
- name: podinfo
downwardAPI:
items:
- path: "labels"
fieldRef:
fieldPath: metadata.labels # Pod的Lable列表
- path: "annotations"
fieldRef:
fieldPath: metadata.annotations # Pod的Annotation列表
在Pod的volumes字段中使用Downward API的方法:通过fieldRef字段设定需要引用Pod的元数据信息,将其设定到volume的items中。
通过容器级别volumeMounts的设置,系统会基于volume中各item的path名称生成文件。
按照上述的YAML文件,系统将在容器中的/etc/podinfo目录下生成lables和annotations两个文件,在lables文件中包含了Pod的所有的Label列表,在annotation文件中包含了Pod的所有的Annotation列表。
使用上述的文件创建Pod,并且使用查看日志命令,可以查看到相关的信息,也可以进入容器中查看相关的路径下的挂载文件,并且查看挂载文件中的内容。
将Container信息挂载为容器内部文件
apiVersion: v1
kind: Pod
metadata:
name: kubernetes-downwardapi-volume-example-2
spec:
containers:
- name: client-container
image: k8s.gcr.io/busybox:1.24
command: ["sh", "-c"]
args:
- while true; do
echo -en '\n';
if [[ -e /etc/podinfo/cpu_limit ]]; then
echo -en '\n'; cat /etc/podinfo/cpu_limit; fi;
if [[ -e /etc/podinfo/cpu_request ]]; then
echo -en '\n'; cat /etc/podinfo/cpu_request; fi;
if [[ -e /etc/podinfo/mem_limit ]]; then
echo -en '\n'; cat /etc/podinfo/mem_limit; fi;
if [[ -e /etc/podinfo/mem_request ]]; then
echo -en '\n'; cat /etc/podinfo/mem_request; fi;
sleep 5;
done;
resources:
requests:
memory: "32Mi"
cpu: "125m"
limits:
memory: "64Mi"
cpu: "250m"
volumeMounts:
- name: podinfo
mountPath: /etc/podinfo
volumes:
- name: podinfo
downwardAPI:
items:
- path: "cpu_limit"
resourceFieldRef:
containerName: client-container
resource: limits.cpu # 容器的CPU限制
divisor: 1m
- path: "cpu_request"
resourceFieldRef:
containerName: client-container
resource: requests.cpu # 容器的CPU请求
divisor: 1m
- path: "mem_limit"
resourceFieldRef:
containerName: client-container
resource: limits.memory # 容器的内存限制
divisor: 1Mi
- path: "mem_request"
resourceFieldRef:
containerName: client-container
resource: requests.memory # 容器的内存请求
divisor: 1Mi
使用上述的YAML文件创建Pod,查看Pod的日志,可以看到挂载文件的相关内容,也可以进入容器查看挂载文件内容。
Downward API支持设定的Pod和Container信息
-
通过fieldRef设定的元数据如下
- metadata.name:Pod名称
- metadata.namespace: Pod所在的命名空间名称
- metadata.uid:Pod的UID (Kubernetes 1.8.0 +)
- metadata.labels[‘<KEY>’]:Pod某个Label的值,通过KEY进行引用
- metadata.annotations[‘<KEY>’]:Pod某个Annotation的值,通过KEY进行引用
-
通过resourceFieldRef设定的元数据如下
- Container级别的CPU Limit
- Container级别的CPU Request
- Container级别的Memory Limit
- Container级别的Memory Request
- Container级别的临时存储空间(ephemeral-storage)Limit (Kubernetes 1.8.0 +)
- Container级别的临时存储空间(ephemeral-storage)Request (Kubernetes 1.8.0 +)
-
通过fieldRef字段设定的元数据如下
- metadata.label:Pod的Label列表,每个Label都以KEY为文件名,value为文件内容,每个Label占文件一行
- metadata.annotations: Pod的Annotation列表,每个Annotation都以KEY为文件名,value为文件内容,每个Annotation占文件一行
-
Pod元数据信息可以设置为容器内的环境变量
- status.podIP:Pod的IP地址
- spec.serviceAccountName:Pod使用的ServiceAccount名称
- spec.nodeName:Pod所在Node的名称 (Kubernetes 1.4.0 +)
- status.hostIP:Pod所在Node的IP地址 (Kubernetes 1.7.0 +)