什么是 KCL
KCL (Kusion Configuration Language) 是一个开源的基于约束的记录及函数言语,主要用于装备编写和战略校验场景。KCL 希望经过老练的编程言语技术和实践来改进对很多冗杂装备的编写,致力于构建环绕装备的更好的模块化、扩展性和稳定性,更简略的逻辑编写,以及更快的自动化集成和杰出的生态延展性。
所谓装备就是当咱们部署软件体系时,咱们并不认为它们是固定不变的。不断发展的事务需求、根底架构要求和其他因素意味着体系不断改变。当咱们需求快速更改体系行为,而且更改进程需求昂贵、冗长的重建和重新部署进程时,事务代码更改往往是不行的。而装备能够为咱们提供了一种低开支的方法来改变体系功用,比方咱们会经常为体系编写一些如下所示的 JSON 或 YAML 文件作为咱们体系的装备。
- JSON 装备
{
"server": {
"addr": "127.0.0.1",
"listen": 4545
},
"database": {
"enabled": true,
"ports": [
8000,
8001,
8002
],
}
}
- YAML 装备
server:
addr: 127.0.0.1
listen: 4545
database:
enabled: true
ports:
- 8000
- 8001
- 8002
咱们能够依据需求选择在 JSON 和 YAML 文件中存储静态装备。此外,装备还能够存储在答应更灵敏装备的高级言语中,经过代码编写、烘托并得到静态装备。KCL 就是这样一种装备言语,咱们能够编写 KCL 代码来生成 JSON/YAML 等装备。这篇文章咱们要点叙述运用 KCL 生成并办理 Kubernetes 资源,并经过一些简略的比方给咱们一个简略的快速开端,更多的内容咱们会在后续文章展开。
为什么运用 KCL
当咱们办理 Kubernetes 资源清单时,咱们常常会手写保护,或许运用 Helm 和 Kustomize 等东西来保护咱们 YAML 装备或许装备模版,然后经过 kubectl 和 helm 指令行等东西将资源下发到集群。但是作为一个 “YAML 工程师” 每天保护 YAML 装备无疑是琐碎且无聊的,而且简单出错。
apiVersion: apps/v1
kind: Deployment
metadata: ... # Omit
spec:
selector:
matchlabels:
cell: RZ00A
replicas: 2
template:
metadata: ... # Omit
spec:
tolerations:
- effect: NoSchedules
key: is-over-quota
operator: Equal
value: 'true'
containers:
- name: test-app
image: images.example/app:v1 # Wrong ident
resources:
limits:
cpu: 2 # Wrong type. The type of cpu should be str
memory: 4Gi
# Field missing: ephemeral-storage
affinity:
nodeAffinity:
requiredDuringSchedulingIgnoredDuringExecution:
nodeSelectorTerms:
- matchExpressions:
- key: is-over-quota
operator: In
values:
- 'true'
-
- YAML 中的结构化数据是无类型的,缺少验证方法,无法当即查看所有数据的有效性
-
- YAML 编程才能欠佳,简单写出不正确的缩进,也没有逻辑判断、等常见代码安排方法,简单写出很多重复装备,难以保护
-
- 用户很难了解 YAML 装备所有细节,比方上 Kubernetes 装备中的
toleration
和affinity
字段,如果用户不了解调度逻辑,它可能被过错地省略掉或许剩余的添加
- 用户很难了解 YAML 装备所有细节,比方上 Kubernetes 装备中的
因而,KCL 希望在 Kubernetes YAML 资源办理层面处理如下问题:
-
- 用生产级高性能编程言语以编写代码的方法提高装备的灵敏度,比方条件句子、循环、函数、包办理等特性提高装备重用的才能
-
- 在代码层面提高装备语义验证的才能,比方字段可选 / 必选、类型、规模等装备查看才能
-
- 提供装备分块编写、组合和抽象的才能,比方结构界说、结构继承、约束界说等才能
本篇文章是 KCL 能够做什么系列文章第一篇,要点叙述 KCL 快速入门,后续会持续更新和分享 KCL 的一系列特点和运用场景,咱们敬请期待!
怎么运用 KCL 生成并办理 Kubernetes 资源
前提条件
首要能够在KCL 项目首页依据指导下载并装置 KCL,然后准备一个Kubernetes环境
生成 Kubernetes 资源
咱们能够编写如下 KCL 代码并命名为 main.k ,KCL 受 Python 启示,根底语法十分接近 Python, 比较简单学习和上手
apiVersion = "apps/v1"
kind = "Deployment"
metadata = {
name = "nginx"
labels.app = "nginx"
}
spec = {
replicas = 3
selector.matchLabels = metadata.labels
template.metadata.labels = metadata.labels
template.spec.containers = [
{
name = metadata.name
image = "${metadata.name}:1.14.2"
ports = [{ containerPort = 80 }]
}
]
}
上述 KCL 代码中咱们别离声明晰一个 Kubernets Deployment 资源的apiVersion
、kind
、metadata
和spec
等变量,并别离赋值了相应的内容,特别地,咱们将metadata.labels
字段别离重用在spec.selector.matchLabels
和spec.template.metadata.labels
字段。能够看出,比较于 YAML,KCL 界说的数据结构更加紧凑,而且能够经过界说局部变量实现装备重用。
咱们能够履行如下指令行得到一个 Kubernetes YAML 文件
kcl main.k
输出为:
apiVersion: apps/v1
kind: Deployment
metadata:
name: nginx
labels:
app: nginx
spec:
replicas: 3
selector:
matchLabels:
app: nginx
template:
metadata:
labels:
app: nginx
spec:
containers:
- name: nginx
image: nginx:1.14.2
ports:
- containerPort: 80
当然咱们能够将 KCL 东西与 kubectl 等东西结合运用,让咱们履行如下指令并看看效果
$ kcl main.k | kubectl apply -f -
deployment.apps/nginx configured
能够从指令行的成果看出看出与咱们运用直接运用 YAML 装备和 kubectl apply 的一个 Deployment 体会完全一致
经过 kubectl 查看部署状态
$ kubectl get deploy
NAME READY UP-TO-DATE AVAILABLE AGE
nginx 3/3 3 3 15s
编写代码办理 Kubernetes 资源
关于 Kubernetes 资源发布时,咱们常常会遇到装备参数需求动态指定的场景,比方不同的环境需求设置不同的image
字段值生成不同环境的资源。关于这种场景,咱们能够经过 KCL 的条件句子和option
函数动态地接纳外部参数。咱们能够在上述比方的根底上依据不同的环境调整装备参数,比方关于如下代码,咱们编写了一个条件句子并输入一个名为env
的动态参数
apiVersion = "apps/v1"
kind = "Deployment"
metadata = {
name = "nginx"
labels.app = "nginx"
}
spec = {
replicas = 3
selector.matchLabels = metadata.labels
template.metadata.labels = metadata.labels
template.spec.containers = [
{
name = metadata.name
image = "${metadata.name}:1.14.2" if option("env") == "prod" else "${metadata.name}:latest"
ports = [{ containerPort = 80 }]
}
]
}
运用 KCL 指令行-D
符号接纳一个从外部设置的动态参数:
kcl main.k -D env=prod
输出为:
apiVersion: apps/v1
kind: Deployment
metadata:
name: nginx-deployment
labels:
app: nginx
spec:
replicas: 3
selector:
matchLabels:
app: nginx
template:
metadata:
labels:
app: nginx
spec:
containers:
- name: nginx
image: nginx:1.14.2
ports:
- containerPort: 80
上述代码片段中的image = "${metadata.name}:1.14.2" if option("env") == "prod" else "${metadata.name}:latest"
意思为:当动态参数env
的值被设置为prod
时,image 字段值为nginx:1.14.2
, 否则为nginx:latest
,因而咱们能够依据需求为 env 设置为不同的值取得不同内容的 Kubernetes 资源。
而且 KCL 支撑将 option 函数动态参数保护在装备文件中,比方编写下面展示的kcl.yaml
文件
kcl_options:
- key: env
value: prod
运用如下指令行也能够得到同样的效果,简化 KCL 动态参数的输入进程
kcl main.k -Y kcl.yaml
输出为:
apiVersion: apps/v1
kind: Deployment
metadata:
name: nginx-deployment
labels:
app: nginx
spec:
replicas: 3
selector:
matchLabels:
app: nginx
template:
metadata:
labels:
app: nginx
spec:
containers:
- name: nginx
image: nginx:1.14.2
ports:
- containerPort: 80
下一期
本期内容大概简略介绍了用 KCL 编写装备的快速入门和运用KCL 界说并办理 Kubernetes 资源。
目前阶段 Kustomize 和 Helm 现已慢慢演进成在 Kubernetes 装备界说和办理领域的事实意义上的规范,了解 Kubernetes 的小伙伴可能更喜爱显式装备编写方法编写。那么相较于 Kustomize 和 Helm,用 KCL 来写装备文件烘托,又有什么异同呢?考虑到有很多小伙伴现已在运用 Helm,Kustomize 这样的东西,下一期我将介绍用 KCL 的方法来写对应的装备代码,敬请期待!!
如果您喜爱这篇文章,必定记住收藏 + 重视!!更多精彩内容请拜访(如果您喜爱 KCL 这个项目,无妨 star 一下鼓励一下作者哦):
KCL 库房地址:github.com/KusionStack…
Kusion 库房地址:github.com/KusionStack…
Konfig 库房地址:github.com/KusionStack…
一起欢迎参加咱们的社区进行交流:
github.com/KusionStack…