Tekton Pipelinesの制御フロー

TektonのPipelineは、Taskの集合体です。
spec.tasksにTaskの配列を定義するのですが、とくに指定しない限り並列に実行されます。

runAfter

runAfterは先行タスクを指定するキーです。
これにより、タスクをシリアルに実行できます。

apiVersion: tekton.dev/v1
kind: Pipeline
metadata:
  name: some-pipeline
spec:
  tasks:
  - name: task1
    taskRef:
      name: some-task
  - name: task2
    runAfter:
    - task1
    taskRef:
      name: another-task

runAfterで直列化した場合、先行タスクが失敗すると後続タスクは実行されません。
多くのCIでは、パイプラインのどこかで異常があった場合に終了するフローが必要ですが、runAfterを用いると簡潔に実装できます。

タスクの完了は一般的なシェルスクリプトと同様、exitコード0/非0で制御できます。

なお、runAfterの子要素は配列であり、複数のタスクを条件に指定した場合には、AND条件で判定します。
いずれかのタスクがSkippedになった場合には実行されません。whenの判定で先行タスクの一部が非該当になった場合などに起こり得ます。
コードの外見が自明ではないので、注意が必要です。

when

whenを指定するとTask実行前に条件判定し、マッチした場合のみTask実行します。
whenの子要素は配列で、複数指定した場合にはAND条件で判定されます。

apiVersion: tekton.dev/v1
kind: Pipeline
metadata:
  name: some-pipeline
spec:
  params:
  - name: exec
  tasks:
  - name: task1
    taskRef:
      name: some-task
    when:
    - input: $(params.exec)
      operator: in
      values: ["true"]

この例では、PipelineRunから供給されるparamsを判定に利用しています。
状況によって一部のタスクを実行したりしなかったりする制御はwhenで実装できます。

なお、whenはフローの前後関係を直接制御するものではありません。
直列化するには既述のrunAfterを併用し、実行ステータス以外の条件をwhenで判定します。

finally

Piplelineで一部のタスクが異常終了すると後続タスクは実行されません。
アボート時にも実行したいタスクは、spec.finallyに定義すると動作します。

apiVersion: tekton.dev/v1
kind: Pipeline
metadata:
  name: some-pipeline
spec:
  tasks:
  - name: task1
    taskRef:
      name: some-task
  finally:
  - name: task2
    taskRef:
      name: another-task

spec.finallyspec.tasksとほぼ同様で、必要に応じて複数のタスクを定義可能です。

finallyはwhenガードを定義しない限り、つねに実行されます。
finallyではspec.tasksの実行結果を、 tasks.statusで参照でき、whenの判定に利用できます。

ステータスはドキュメント記載のとおりやや複雑な挙動をとりますが、簡易的にはSucceededまたはFailedを利用できるでしょう。

ステータス以外の変数は、 Variable Substitutions Supported by Tasks and Pipelinesに掲載されています。
pipelineTaskの失敗時にはResultに値が入らないため、失敗した処理のログなどはfinally中の処理で取り出せません。

Workspaces

タスク間のディレクトリ共有については、 TektonのWorkspace機能で解説しています。

中馬崇尋
Chuma Takahiro