前往小程序,Get更优阅读体验!
立即前往
首页
学习
活动
专区
工具
TVP
发布
社区首页 >专栏 >使用 Workspaces 加速 Tekton 流水线

使用 Workspaces 加速 Tekton 流水线

作者头像
我是阳明
发布2021-06-25 17:07:59
2.1K0
发布2021-06-25 17:07:59
举报
文章被收录于专栏:k8s技术圈

在实际工作中,我们经常需要的一个功能是能够在任务之间共享制品,以便缓存构建工具(比如 Maven 和 NPM)的依赖项,在 Tekton 0.10 版本就发布增加了对 Workspaces 的支持,这使得流水线中的任务可以更加轻松地使用 PV 来共享数据了,Workspaces 允许指定一个或多个 pipeline 中 task 运行时需要的 volume。

Tekton Pipelines 中的 Workspaces 是指流水线运行时需要的共享卷的声明,在流水线定义中,Workspaces 可以作为共享卷传递给相关任务,这样当为多个任务提供相同的 Workspaces 的时候,它们就可以从相同的 Volumes 中读取和写入数据。当然 Workspaces 的 Volumes 卷除了可以是 PVC,也可以是 ConfigMap,或者是在任务之间挂载和共享的 Secret 资源。

接下来让我们看看在实践中如何使用 Workspaces 来缓存 Maven 依赖,加速流水线的构建,这里我们使用的项目为:https://github.com/cnych/spring-petclinic。

要在流水线中构建 Maven 项目,当然需要定义一个 Maven 的 Task 任务,其实在 Tekton Catalog 里面就已经包含了这样的通用的 Task 了,但是这里我们需要对其进行一些修改来为 Maven 的依赖项添加 Workspaces 支持。

代码语言:javascript
复制
# workspace-mvn-task.yaml
apiVersion: tekton.dev/v1beta1
kind: Task
metadata:
  name: mvn-task
spec:
  workspaces:
  - name: maven-repo
  resources:
    inputs:
    - name: source
      type: git
  params:
  - name: GOALS
    description: The Maven goals to run
    type: array
    default: ["package"]
  steps:
    - name: mvn
      image: cnych/cloud-builders-mvn:tekton
      workingDir: /workspace/source
      command: ["/usr/bin/mvn"]
      args:
        - -Dmaven.repo.local=$(workspaces.maven-repo.path)
        - "$(inputs.params.GOALS)"

上面的任务中我们新增了一个名为 maven-repo 的 Workspace,该工作区规定无论何时运行该任务,都应该提供并配置一个卷来充当本地的 Maven 存储库,然后将工作区的路径传递给 Maven 命令,以便通过 -Dmaven.repo.local=$(workspaces.maven-repo.path) 命令将工作区的路径作为本地的 Maven 库,当然也可以配置 Workspace 挂载的路径,这里我们使用的是默认的路径。

接着我们来定义一个使用 Maven 任务构建 Java 应用程序的流水线 Pipeline,为了演示 Maven 依赖的缓存效果,这里的流水线我们运行3个 Maven 任务来执行构建、集成测试,并生成测试结果和代码覆盖率等报告。

流水线定义如下所示:

代码语言:javascript
复制
# workspace-mvn-pipeline.yaml
apiVersion: tekton.dev/v1beta1
kind: Pipeline
metadata:
  name: mvn-pipeline
spec:
  workspaces:  # 声明 workspaces
  - name: local-maven-repo
  resources: # 声明使用的资源
  - name: app-git
    type: git
  tasks:
  - name: build  # 构建任务
    taskRef:
      name: mvn-task  # 引用上面的 mvn 任务
    resources:  # 传递 resources 资源
      inputs:
      - name: source
        resource: app-git
    params:  # 传递 params 参数
    - name: GOALS
      value: ["package"]
    workspaces:  # 传递 workspaces
    - name: maven-repo
      workspace: local-maven-repo
  - name: int-test  # 测试任务
    taskRef:
      name: mvn-task
    runAfter: ["build"]  # 需要 build 任务执行完成后
    resources:
      inputs:
      - name: source
        resource: app-git
    params:
    - name: GOALS
      value: ["verify"]
    workspaces:
    - name: maven-repo
      workspace: local-maven-repo
  - name: gen-report  # 测试报告
    taskRef:
      name: mvn-task
    runAfter: ["build"]  # 需要 build 任务执行完成后
    resources:
      inputs:
      - name: source
        resource: app-git
    params:
    - name: GOALS
      value: ["site"]
    workspaces:
    - name: maven-repo
      workspace: local-maven-repo

需要注意流水线中的 local-maven-repo 工作区的声明,它指出,当此流水线运行时,应提供一个卷并将其用作此工作区,然后将此工作区提供给此流水线中的每个任务,以便它们都共享相同的工作区。然后我们根据传入的 GOALS 参数来决定应该执行的任务。

流水线 Pipeline 声明完成后,现在我们就可以运行这个流水线来构建 Spring PetClinic 这个示例应用了,在启动流水线之前,需要先创建一个 PVC 来提供一个 Workspace 对 Maven 依赖项进行缓存。

代码语言:javascript
复制
# workspace-mvn-pvc.yaml
apiVersion: v1
kind: PersistentVolumeClaim
metadata:
  name: mvn-repo-pvc
spec:
  resources:
    requests:
      storage: 5Gi
  volumeMode: Filesystem
  storageClassName: nfs-storage  # 使用 StorageClass 自动生成 PV
  accessModes:
    - ReadWriteOnce

这里我们使用了一个名为 nfs-storage 的 StorageClass,这样就可以自动生成一个对应的 PV 进行绑定,如果你没有需要自行创建一个对应的静态 PV。

现在我们就可以创建一个使用上述 PVC 作为流水线工作区的 PipelineRun 来执行流水线了:

代码语言:javascript
复制
# workspace-mvn-pipelinerun.yaml
apiVersion: tekton.dev/v1beta1
kind: PipelineRun
metadata:
  name: mvn-pipelinerun
spec:
  pipelineRef:
    name: mvn-pipeline
  resources:
  - name: app-git
    resourceSpec:
      type: git
      params:
        - name: url
          value: https://github.com.cnpmjs.org/cnych/spring-petclinic
  workspaces:
  - name: local-maven-repo
    persistentVolumeClaim:
      claimName: mvn-repo-pvc

请注意 PVC 和为缓存 maven 依赖项而声明的工作区之间的映射,mvn-repo-pvc 被传递到流水线和相应的任务作为缓存文件和制品的共享卷。

第一次流水线运行将需要一些时间来下载依赖项执行任务,直接创建上面声明的几个资源对象,观察 PipelineRun 的执行过程:

代码语言:javascript
复制
kubectl apply -f workspace-mvn-task.yaml
kubectl apply -f workspace-mvn-pipeline.yaml
kubectl apply -f workspace-mvn-pvc.yaml
kubectl apply -f workspace-mvn-pipelinerun.yaml

当第一次执行流水线的时候会在执行 mvn 命令的时候消耗大量的时间,因为需要下载依赖包,我这里的环境差不多等了20分钟左右:

然后在执行后面的两个任务的时候就非常快了,因为前面任务执行完成后会把依赖项存入到 Workspace 声明的 PVC 中去,后面的任务直接使用了这个 Workspace,我们可以重新执行一次 PipelineRun,对比下前后两次的时间,在我的环境中,执行时间由37分钟减少到大约两分钟。

代码语言:javascript
复制
$ tkn pr list
NAME                      STARTED         DURATION     STATUS
mvn-pipelinerun-r-fgwf2   3 minutes ago   2 minutes    Succeeded
mvn-pipelinerun           2 hours ago     37 minutes   Succeeded
# 查看第一次pipelinerun的执行情况
$ tkn pr describe mvn-pipelinerun
Name:              mvn-pipelinerun
Namespace:         default
Pipeline Ref:      mvn-pipeline
Service Account:   default
Timeout:           1h0m0s
Labels:
 tekton.dev/pipeline=mvn-pipeline

?️  Status

STARTED       DURATION     STATUS
2 hours ago   37 minutes   Succeeded
......
?  Taskruns

 NAME                                 TASK NAME    STARTED       DURATION     STATUS
 ∙ mvn-pipelinerun-int-test-mbppx     int-test     2 hours ago   33 seconds   Succeeded
 ∙ mvn-pipelinerun-gen-report-xlns9   gen-report   2 hours ago   36 minutes   Succeeded
 ∙ mvn-pipelinerun-build-x9zkf        build        2 hours ago   20 minutes   Succeeded

# 查看第二次执行的详细信息
$ tkn pr describe mvn-pipelinerun-r-fgwf2
Name:              mvn-pipelinerun-r-fgwf2
Namespace:         default
Pipeline Ref:      mvn-pipeline
Service Account:   default
Timeout:           1h0m0s
Labels:
 reruns=mvn-pipelinerun
 tekton.dev/pipeline=mvn-pipeline

?️  Status

STARTED         DURATION    STATUS
4 minutes ago   2 minutes   Succeeded
......

?  Taskruns

 NAME                                         TASK NAME    STARTED         DURATION     STATUS
 ∙ mvn-pipelinerun-r-fgwf2-gen-report-n69g8   gen-report   4 minutes ago   1 minute     Succeeded
 ∙ mvn-pipelinerun-r-fgwf2-int-test-4g58z     int-test     4 minutes ago   32 seconds   Succeeded
 ∙ mvn-pipelinerun-r-fgwf2-build-ftqgr        build        4 minutes ago   38 seconds   Succeeded

测试任务运行没有受到太大影响,因为它使用了大部分在构建任务运行中下载的依赖项,即使在第一次流水线运行中也是如此。

我们可以看到利用 Workspaces 功能可以对我们的流水线构建进行大幅度的优化,特别是对于依赖包特别大的应用,比如 Maven、NPM、Go Modules 等。

本文参与 腾讯云自媒体同步曝光计划,分享自微信公众号。
原始发表:2021-06-19,如有侵权请联系 cloudcommunity@tencent.com 删除

本文分享自 k8s技术圈 微信公众号,前往查看

如有侵权,请联系 cloudcommunity@tencent.com 删除。

本文参与 腾讯云自媒体同步曝光计划  ,欢迎热爱写作的你一起参与!

评论
登录后参与评论
0 条评论
热度
最新
推荐阅读
领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档