Jenkins 不使用共享库的话 Pipeline 维护太困难,有学共享库的时间不如研究点新技术,早就想试试 tekton 了

1 介绍

其中TaskTaskRunPipelinePipelineRunPipelineResourceCondition作为其核心 CRD,这里主要介绍它们。

  • Task:定义构建任务,它由一系列有序 steps 构成。每个 step 可以定义输入和输出,且可以将上一个 step 的输出作为下一个 step 的输入。每个 step 都会由一个 container 来执行。
  • TaskRun:Task 用于定义具体要做的事情,并不会真正的运行,而 TaskRun 就是真正的执行者,并且会提供执行所需需要的参数,一个 TaskRun 就是一个 Pod。
  • Pipeline:顾名思义就是流水线,它由一系列 Tasks 组成。就像 Task 中的 step 一样,上一个 Task 的输出可以作为下一个 Task 的输入。
  • PipelineRun:Pipeline 的实际执行,创建后会创建 Pod 来执行 Task,一个 PipelineRun 中有多个 Task。
  • PipelineResource:主要用于定义 Pipeline 的资源,常见的如 Git 地址、Docker 镜像等。
  • Condition:它主要是在 Pipeline 中用于判断的,Task 的执行与否通过 Condition 的判断结果来决定。

Tasks and Pipelines

如图所示,一个 Pipeline 是由许多 Task 组成,每个 Task 又由许多 step 组成。在实际工作中,我们可以灵活定义各种 Task,Task 可以复用,然后根据需要任意组合 Task 形成各类 Pipeline 来完成不同的需求。

2 准备工作

2.1 拉取镜像

1
2
3
4
5
6
7
8
9
10
11
12
13
14
docker pull ccr.ccs.tencentyun.com/ccops/tektoncd-pipeline-cmd-controller:v0.33.3
docker pull ccr.ccs.tencentyun.com/ccops/tektoncd-pipeline-cmd-kubeconfigwriter:v0.33.3
docker pull ccr.ccs.tencentyun.com/ccops/tektoncd-pipeline-cmd-git-init:v0.33.3
docker pull ccr.ccs.tencentyun.com/ccops/tektoncd-pipeline-cmd-entrypoint:v0.33.3
docker pull ccr.ccs.tencentyun.com/ccops/tektoncd-pipeline-cmd-nop:v0.33.3
docker pull ccr.ccs.tencentyun.com/ccops/tektoncd-pipeline-cmd-imagedigestexporter:v0.33.3
docker pull ccr.ccs.tencentyun.com/ccops/tektoncd-pipeline-cmd-pullrequest-init:v0.33.3
docker pull ccr.ccs.tencentyun.com/ccops/tektoncd-pipeline-cmd-workingdirinit:v0.33.3
docker pull ccr.ccs.tencentyun.com/ccops/cloudsdktool-cloud-sdk:v1
docker pull ccr.ccs.tencentyun.com/ccops/distroless-base:v1
docker pull ccr.ccs.tencentyun.com/ccops/tektoncd-pipeline-cmd-webhook:v0.33.3
docker pull ccr.ccs.tencentyun.com/ccops/tektoncd-dashboard-cmd-dashboard:v0.24.1
docker pull ccr.ccs.tencentyun.com/ccops/kaniko-executor:v1.6.0
docker pull ccr.ccs.tencentyun.com/ccops/kubectl:1.22.8

2.2 获取代码

git clone https://git.ccops.cc/Kubernetes/tekton.git

2.3 安装 jq

1
yum install jq -y

2.4 配置秘钥

1
kubectl create secret docker-registry dockerhub --docker-server=仓库地址 --docker-username="用户名" --docker-password="密码" --dry-run=client -o json | jq -r '.data.".dockerconfigjson"' | base64 -d > /tmp/config.json && kubectl create secret generic docker-config --from-file=/tmp/config.json

2.5 配置 kubeconfig

1
kubectl create secret generic kubernetes-config --from-file=/root/.kube/config

2.6 安装 tekon 客户端,可选,我这里没装

点这里下载

3 tekton 安装

3.1 添加 dashboard 访问方式 externalIPs

1
2
3
vim tekton/csi/tekton-dashboard-release.yaml
externalIPs:
- 10.1.1.1

3.2 安装

会自动安装到 tekton-pipelines 命名空间,不建议更换

1
kubectl apply -f tekton/csi

3.3 查看 pod

1
2
3
4
5
kubectl get pod -n tekton-pipelines
NAME READY STATUS RESTARTS AGE
tekton-dashboard-796d7f9d69-qzsfc 1/1 Running 0 44h
tekton-pipelines-controller-844c695595-8mpmf 1/1 Running 0 23h
tekton-pipelines-webhook-5d7b464584-2bqch 1/1 Running 0 44h

3.4 查看访问方式

1
2
3
4
5
kubectl get svc -n tekton-pipelines
NAME TYPE CLUSTER-IP EXTERNAL-IP PORT(S) AGE
tekton-dashboard ClusterIP 172.19.93.135 10.1.1.1 9097/TCP 44h
tekton-pipelines-controller ClusterIP 172.19.4.207 <none> 9090/TCP,8008/TCP,8080/TCP 45h
tekton-pipelines-webhook ClusterIP 172.19.221.253 <none> 9090/TCP,8008/TCP,443/TCP,8080/TCP 45h

3.5 测试

1
kubectl apply -f tekton/hello/task.yaml

3.5.1 查看

image-20220401143402368

4 配置流水线

4.1 跳过私有仓库证书验证,可选

1
2
tail -n 1 build-push-image-task.yaml
- --skip-tls-verify

4.2 Task

Task 就是一个任务模板,Task 的定义中可以包含变量,在真正执行的时候需要给变量赋值。

Task 通过 input.params 定义入参,每一个入参还可以指定默认值,在每一个 step 中可以$(params.A)引用变量。steps 字段表示当前 Task 有哪些步骤组成,每一个 step 都会通过定义一个 container 来执行具体的操作。

Task 主要包括以下元素:

  • Workspaces:定义工作区,Task 可以共享工作区
  • Parameters:用于定义 params 参数
  • Steps:定义具体的操作步骤
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
 cat deploy-to-k8s-task.yaml
apiVersion: tekton.dev/v1alpha1
kind: Task
metadata:
name: deploy-to-k8s
spec:
workspaces:
- name: source
- name: kubernetesconfig
mountPath: /root/.kube
params:
- name: pathToYamlFile
description: The path to the yaml file to deploy within the git source
default: deployment.yaml
- name: IMAGE
- name: TAG
steps:
- name: run-kubectl
image: registry.cn-hangzhou.aliyuncs.com/coolops/kubectl:1.19.16
workingDir: $(workspaces.source.path)
script: |
sed -i s#IMAGE#$(params.IMAGE)#g $(params.pathToYamlFile)
sed -i s#TAG#$(params.TAG)#g $(params.pathToYamlFile)
kubectl apply -f $(params.pathToYamlFile)

4.3 Pipeline

Pipeline 是一个编排 Task 的模板,通过 spec.params 来声明执行时需要的入参,通过 spec.tasks 来编排具体的 task,除此之外还可以通过 runAfter 来控制 Task 的先后顺序。

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
apiVersion: tekton.dev/v1beta1
kind: Pipeline
metadata:
name: devops-hello-world-pipeline
spec:
workspaces: # 声明 workspaces
- name: go-repo-pvc
- name: docker-config
- name: kubernetes-config
params:
# 定义代码仓库
- name: git_url
description: https://git.ccops.cc/golang_test/go_demo.git
- name: revision
type: string
default: "master"
- name: gitInitImage
type: string
default: "gexuchuan123/tektoncd-pipeline-cmd-git-init:v0.33.3"
# 定义镜像参数
- name: pathToDockerfile
description: The path to the build context, used by Kaniko - within the workspace
default: .
- name: imageUrl
description: Url of image repository
- name: imageTag
description: Tag to apply to the built image
default: latest
tasks: # 添加task到流水线中
- name: clone
taskRef:
name: git-clone
workspaces:
- name: output
workspace: go-repo-pvc
params:
- name: url
value: $(params.git_url)
- name: revision
value: $(params.revision)
- name: gitInitImage
value: $(params.gitInitImage)
- name: unit-test
workspaces: # 传递 workspaces
- name: source
workspace: go-repo-pvc
taskRef:
name: unit-test
runAfter: # 控制Task顺序
- clone
- name: build-push-image
params:
- name: pathToDockerfile
value: $(params.pathToDockerfile)
- name: imageUrl
value: $(params.imageUrl)
- name: imageTag
value: $(tasks.clone.results.commit)
taskRef:
name: build-push-image
runAfter:
- unit-test
workspaces: # 传递 workspaces
- name: source
workspace: go-repo-pvc
- name: dockerconfig
workspace: docker-config
- name: deploy-to-k8s
taskRef:
name: deploy-to-k8s
params:
- name: pathToYamlFile
value: deployment.yaml
- name: IMAGE
value: $(params.imageUrl)
- name: TAG
value: $(tasks.clone.results.commit)
workspaces:
- name: source
workspace: go-repo-pvc
- name: kubernetesconfig
workspace: kubernetes-config
runAfter:
- build-push-image

4.4 应用与查看

kubectl apply -f tekton/cicd/
image-20220401143402368

4.5 配置 git 账户

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
vim tekton/deploy/serviceaccount.yaml
apiVersion: v1
kind: Secret
metadata:
name: gitlab-auth
annotations:
tekton.dev/git-0: https://git.ccops.cc/ # git地址
type: kubernetes.io/basic-auth
stringData:
username: 用户名
password: 密码
---
apiVersion: v1
kind: ServiceAccount
metadata:
name: tekton-build-sa
secrets:
- name: gitlab-auth
---
apiVersion: rbac.authorization.k8s.io/v1
kind: ClusterRoleBinding
metadata:
name: tekton-clusterrole-binding
roleRef:
apiGroup: rbac.authorization.k8s.io
kind: ClusterRole
name: edit
subjects:
- kind: ServiceAccount
name: tekton-build-sa
namespace: default # 这里注意下命名空间,如果不在default要改
kubectl apply -f tekton/deploy/serviceaccount.yaml

4.6 配置 PipelineRun

Pipeline 和 Task 一样,单纯的定义完并不会运行,Pipeline 需要借助 PipelineRun 来完成真正的执行。

PipelineRun 会自动为 Pipeline 中定义的 Task 创建对应的 TaskRun。

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
cim tekton/deploy/pipeline-run.yaml
apiVersion: tekton.dev/v1beta1
kind: PipelineRun
metadata:
name: devops-hello-world-pipeline-run
spec:
pipelineRef:
name: devops-hello-world-pipeline
params:
- name: revision
value: master
- name: git_url
value: https://git.ccops.cc/golang_test/go_demo.git
- name: imageUrl
value: 自己的仓库地址
- name: imageTag
value: 这里配置也没用,会自动根据commit id修改
- name: pathToDockerfile
value: Dockerfile #dockerfile名称
workspaces:
- name: go-repo-pvc
volumeClaimTemplate:
spec:
storageClassName: nfs-client # 通过nfs csi自动创建pv,这里选择存储要注意,有的可能报错pvc被占用,因为tekton运行完tasks的pod不属于正常删除,文件句柄没有及时关闭导致挂载不了
accessModes:
- ReadWriteMany
resources:
requests:
storage: 1G
- name: docker-config
secret:
secretName: docker-config # 刚才添加的docker仓库信息
- name: kubernetes-config
secret:
secretName: kubernetes-config
serviceAccountName: tekton-build-sa

4.7 运行

kubectl apply -f tekton/deploy/pipeline-run.yaml

5 查看

6 Pipeline

image-20220401144155183

6.1 pod

1
2
3
kubectl get pod
NAME READY STATUS RESTARTS AGE
httpserver-6bd9bb97f6-xrcvb 1/1 Running 0 40m

7 总结

tekton 复用性非常强,如果需要部署 java 项目只需要新加个 maven taks,其他基本不用动