组成
针对 Pod 网络:Understanding kubernetes networking: pods
性质
Termination of Pods | https://kubernetes.io/docs/concepts/workloads/pods/pod-lifecycle/#pod-termination
启动命令 command 启动参数 args
Define a Command and Arguments for a Container | Kubernetes
How to set multiple commands in one yaml file with Kubernetes? – Stack Overflow
使用 command 定义启动命令,使用 args 定义启动参数。在容器启动后,该参数不能修改。
命令及参数的示例:
apiVersion: v1
kind: Pod
metadata:
name: example-command-demo
spec:
containers:
# 通过 command 及 args 来执行命令
- name: command-demo-container
command: ["printenv"]
args: ["HOSTNAME", "KUBERNETES_PORT"]
# 针对较长的参数
- name: long-args
command:
- java
- -jar
- -Dfoo=1
- -Dbar=2
- app.jar
节点选择 nodeSelector
Assign Pods to Nodes | https://kubernetes.io/docs/tasks/configure-pod-container/assign-pods-nodes/
...
spec:
containers:
- name: nginx
image: nginx
imagePullPolicy: IfNotPresent
nodeSelector:
disktype: ssd
...
镜像拉取策略 imagePullPolicy
IfNotPresent Always Never
拉取私有镜像 imagePullSecrets
第一步、创建访问私有镜像仓库的 Secret 信息:
kubectl create secret generic regcred \
--from-file=.dockerconfigjson=<path/to/.docker/config.json> \
--type=kubernetes.io/dockerconfigjson
# 或者,通过命令行指定
kubectl create secret docker-registry regcred \
--docker-server=<your-registry-server> \
--docker-username=<your-name> \
--docker-password=<your-pword> \
--docker-email=<your-email>
第二步、在 Pod 中,指定访问该仓库的凭证:
...
spec:
containers:
- name: private-reg-container
image: <your-private-image>
imagePullSecrets:
- name: regcred
...
初始化容器 | spec.initContainers
Init Containers | Kubernetes
Debug Init Containers | Kubernetes
影响 Pod 的启动行为,在某个 POD 启动后再启动另外换一个 POD 实例:
针对详细内容,参考官方手册 https://kubernetes.io/docs/concepts/workloads/pods/init-containers/
向往常一样,创建一个普通的 POD,然后以如下方式定义一个依赖的 POD:
kind: Deployment
apiVersion: apps/v1beta1
metadata:
name: nginx
spec:
relicas: 1
template:
metadata:
lable:
app: nginx
spec:
containers:
- name: webserver
image: nginx
ports:
- containerPort: 80
initContainers:
- name: checkabackend
image: busybox
# command: ["sh", "-c", "until nslookup..........."]
command:
- sh
- -c
- |
cd ...
ls ...
...
查看 initContainers 日志:
kubectl logs "<pod-name>" -c "<init-container-2>"
kubernetes – Init container to be ran only once per deployment – Stack Overflow
当 kubectl apply StatefulSet.yaml 时,只执行一次 initContainers,在后续 Pod 启动时不再执行 initContainers 的?或,是否能够仅运行 initContainers 一次?其为是 Pod 的组成部分,所以 Kubernetes 会为每个 Pod 执行 initContainers 定义。在 Pod 启动时,Kubernetes 会为每个 Pod 执行 initContainers 定义。同理,在 StatefulSet 中,难以实现 initContainers 只执行一次,同理也无法让 Deployment 中 initContainers 只执行一次。需要通过其他手段来实现,例如持久化的文件,如何文件存在,则 initContainers 脚本退出执行。
挂载外部存储 | spec.volumes[]
https://kubernetes.io/docs/concepts/storage/volumes/
nfs | https://kubernetes.io/docs/concepts/storage/volumes/#nfs
- You can also mount NFS volumes via PersistentVolumes which do allow you to set mount options.
- You can either set mount options server-side
- or use /etc/nfsmount.conf client-side
构建
查看 Pod 日志
该笔记将记录:在 Kubernetes 中,查看 Pod 日志及资源占用情况的方法,以及常见问题处理。
通过 kubectl logs 命令查看日志:
# kubectl logs --help
# kubectl logs "pod name" --namespace "your namespace"
# kubectl logs -n kube-system etcd-k8scp-01
# kubectl logs -n kube-system etcd-k8scp-01 -c "container-name" # 如果 Pod 包含多个容器,则通过 -c 选项指定容器名;
# kubectl logs -n kube-system etcd-k8scp-01 --previous # 查看以停止 Pod 的日志(前个 Pod 实例)
# 但,如果容器被清理,则 --previous 则无法成功;
应用
常用 Pod 文件模板
这是我们常用的 Pod 文件的模板,能够根据需要进行剪裁:
apiVersion: v1
kind: Pod
metadata:
name: dapi-envars-fieldref
spec:
containers:
- name: test-container
image: k8s.gcr.io/busybox
# 镜像拉取策略:Always、IfNotPresent;
imagePullPolicy: Always
# 字段 command 对应镜像的 entrypoint 指令;
command: [ "sh", "-c"]
# 字段 args 对应镜像的 CMD 指令;
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;
# 挂载存储
volumeMounts:
- name: config-vol
mountPath: /etc/config
# 限制资源
resources:
requests:
memory: "64Mi"
cpu: "250m"
limits:
memory: "128Mi"
cpu: "500m"
# 使用环境变量
env:
# 直接定义环境变量
- name: FOO
valueFrom:
fieldRef:
fieldPath: spec.nodeName
# 引用定义中的变量作为环境变量
- name: MY_POD_NAME
valueFrom:
fieldRef:
fieldPath: metadata.name
在命令中,使用环境变量
下面的 YAML 文件演示如何使用环境变量:
env: - name: MESSAGE value: "hello world" command: ["/bin/echo"] args: ["$(MESSAGE)"] # 环境变量出现在括号中,这对于在 command 或 args 字段中扩展变量是必需的。 # 以该方式引用环境变量 ≠ 在 Shell 中引用变量 # 该方式由 Kubernetes API 处理,后者由 Shell 解析
执行 Shell 脚本(针对多命令场景)
How to set multiple commands in one yaml file with Kubernetes? – Stack Overflow
下面的 YAML 文件演示如何执行 Shell 脚本:
# 常用简单格式
---
command: ["/bin/sh"]
args: ["-c", "while true; do echo hello; sleep 10;done"]
# 或者使用如下形式
---
command: ["/bin/sh", ""]
args:
- |
while true
do
echo hello
sleep 10
done
# 可以根据需要灵活组合
改进
默认 imagePullSecrets 定义
Automatically use secret when pulling from private registry
Kubernetes API Reference / ServiceAccount
在命名空间中,我们希望配置默认 ImagePullSecret 信息,而不需要为每个 Pod 单独添加配置。
# 首先创建 Secret
kubectl create secret docker-registry my-registry-secret \
--docker-server=<your-registry-server> \
--docker-username=<your-username> \
--docker-password=<your-password> \
--docker-email=<your-email> \
-n your-namespace
# 然后将 Secret 添加到 default ServiceAccount
kubectl patch serviceaccount default -n your-namespace \
-p '{"imagePullSecrets": [{"name": "my-registry-secret"}]}'
注意,在 Helm Chart 中,其创建的 Deployment 可能并不使用 default ServiceAccount 资源,所以可能仍旧需要修改 values.yaml 文件。
参考
Expose Pod Information to Containers Through Environment Variables | Kubernetes
Images | Kubernetes
Kubernetes/Concepts/Pods
Pull an Image from a Private Registry | Kubernetes
Managing Resources for Containers | Kubernetes
Labels and Selectors | Kubernetes
docker – Change entrypoint of a k8s Pod, but keep the CMD – Stack Overflow