Kubernetes集群实践(二)如何编写k8s资源清单yaml文件

本文主要介绍如何编写k8s资源清单yaml文件。

在K8s集群上进行资源配置通常都是通过yaml文件进行的,因此如何快速编写yaml文件就变得十分重要。

关键词:k8s

yaml文件格式

这个可以参考我的上一篇文章。

yaml资源清单基本格式

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
apiVersion: apps/v1 # API版本
kind: Deployment # 资源类型
metadata: # 资源元数据
name: web
namespace: default
spec: # 资源的期望值
replicas: 3 # 副本实例数目
selector: # 资源选择器,与下面的metadata.labels保持一致
matchLabels:
app: web
template: # Pod模板
metadata: # Pod元数据
labels:
app: web
spec: # Pod资源的期望值
containers: # 容器配置
- name: web
- image: busybox

KubernetesAPI

当我们去提交一个Pod,或者get一个Pod的时候,它的content内容都是用JSON或者是YAML表达的。上图中有个yaml的例子,在这个yamlfile中,对Pod资源的描述也分为几个部分。

第一个部分,一般来讲会是API的version。比如在这个例子中是V1,它也会描述我在操作哪个资源;比如说我的kind如果是pod,在Metadata中,就写上这个Pod的名字;比如说nginx,我们也会给它打一些label,我们等下会讲到label的概念。在Metadata中,有时候也会去写annotation,也就是对资源的额外的一些用户层次的描述。比较重要的一个部分叫做SpecSpec也就是我们希望Pod达到的一个预期的状态。比如说它内部需要有哪些container被运行;比如说这里面有一个nginx的container,它的image是什么?它暴露的port是什么?当我们从KubernetesAPI中去获取这个资源的时候,一般来讲在Spec下面会有一个项目叫status,它表达了这个资源当前的状态;比如说一个Pod的状态可能是正在被调度、或者是已经running、或者是已经被terminates,就是被执行完毕了。刚刚在API之中,我们讲了一个比较有意思的metadata叫做“label”,这个label可以是一组键值对。比如下图的第一个pod中,label就可能是一个color等于red,即它的颜色是红颜色。当然你也可以加其他label,比如说size:big就是大小,定义为大的,它可以是一组label。这些label是可以被selector,也就是选择器所查询的。这个能力实际上跟我们的sql类型的select语句是非常相似的,比如下图中的三个Pod资源中,我们就可以进行select。namecolor等于red,就是它的颜色是红色的,我们也可以看到,只有两个被选中了,因为只有他们的label是红色的,另外一个label中写的color等于yellow,也就是它的颜色是黄色,是不会被选中的。

通过label,kubernetes的API层就可以对这些资源进行一个筛选,那这些筛选也是kubernetes对资源的集合所表达默认的一种方式。

使用yaml创建资源对象Deployment

资源清单可以通过以下命令导出,会有很多冗余信息

1
kubectl get 资源类型 -n 命名空间 -o yaml

省略-n参数将导出默认命名空间default的资源信息

以上名字在查看配置文件其他字段含义时十分有用!

使用以下命令可查看所有pod的命名空间

1
kubectl get pods -o wide --all-namespaces

apiVersion字段可以通过以下命令查询

1
kubectl api-resources |grep 资源类型

资源对象文件

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
apiVersion: apps/v1		# API版本【必需字段】
Kind: Deployment # 资源对象【必需字段】
metedata: # 资源元数据【必须字段】
name: web # 资源名称
namespace: default # 资源所在的命名空间
spec: # deployment的期望状态
replicas: 1 # 副本实例数量
selector: # 标签选择器,与下文中的metadata.labels保持一致
matchLabels:
app: web
template: # Pod模板
metedata: # Pod元数据
labels: # 定义标签
# 标签一般根据项目属性去写
# 例如 project: ms
app: web # 标签
spec: # Pod规格
containers: # 容器配置
- name: web # 容器名
image: busybox # 镜像名
#command: ["sh"] # 容器执行命令
#args: ["-c", "while true ; do continue ; done"] # 命令执行的参数

以上资源清单等同于

1
kubectl create deployment web --image=busybox --replicas=3 -n default

使用yaml创建资源对象Service

1
2
3
4
5
6
7
8
9
10
11
12
apiVersion: v1              # api版本【必需字段】
kind: Service # 资源类型【必需字段】
metedata: # 资源元数据【必需字段】
name: web
namespace: default # 资源所在namespace
spec: # 期望的资源配置
ports: 80 # Service端口,通过Cluster IP访问时使用的端口
- protocol: TCP # 通信协议
targetPort: 8080 # 容器内部的通信端口
selector:
app: web # 标签
type: NodePort # Service暴露类型,NodePort允许集群外部访问

以上资源清单等同于:

1
kubectl expose sevice web --port=80 --target-port=8080 --type=NodePort -n default

可以将以上两个资源清单合并成一个yaml文件,两个文件中间需要有---分割线,否则kubectl只识别最后一个yaml的内容

快速编写K8s资源清单

用create命令生成deployment的yaml

导出的yaml文件有很多冗余字段,不需要可以删除

如:creationTimestamp和status可以删除

使用--dry-run可以检查是否有错误

1
kubectl create deployment nginx --image=nginx -o yaml --dry-run=client > deployment.yaml

用expose命令生成service的yaml

导出的yaml文件有很多冗余字段,不需要可以删除

如:creationTimestamp和status可以删除

1
kubectl expose servcie nginx --port=80 --target-port=8080 --type=NodePort -o yaml --dry-run=client > service.yaml

用get命令导出yaml

这种方式导出的yaml存在很多冗余

1
kubectl get deployment nginx -o yaml > deployment.yml

怎么查询资源清单文件的指定字段

以下命令能查到pod.spec.containers下的所有字段

1
kubectl explain pods.spec.containers

如何查询资源所有字段

1
kubectl explain deployment

模糊查询资源类型

1
kubectl api-resources | grep 资源类型的模糊字母

检查yaml语法是否有误

可以使用kube-linter来检查yaml语法是否有误

https://github.com/stackrox/kube-linter

执行检测

1
kube-linter lint pod.yaml

参考

  • https://blog.csdn.net/omaidb/article/details/121855353