在 Tekton 中使用自定义镜像时,由于配置错误而无法创建 pod

问题描述

在 Tekton pipeline 中,使用产品提供的镜像可以正常工作,但在使用用户自定义镜像时,您可能会遇到 TaskRun 执行失败。

错误表现

  1. TaskRun 执行失败,状态为 False,原因是 CreateContainerConfigError

    $ kubectl get taskruns -n ${namespace} ${taskrun_name}
    NAME                     SUCCEEDED   REASON                       STARTTIME   COMPLETIONTIME
    hello-c7pnj-run-script   False       CreateContainerConfigError   9m43s
  2. TaskRun 事件显示错误消息:

    Failed: Failed to create pod due to config error
  3. 相关 pod 事件显示错误消息:

    Failed: Error: container's runAsUser breaks non-root policy

根因分析

此类问题通常由以下两个原因导致:

  1. 镜像本身存在问题。
  2. 镜像与 Task 配置不兼容。

故障排查

如果此问题仅在使用自定义镜像时出现,建议按照以下步骤进行排查:

  1. 验证镜像本身是否存在问题:

    $ podman run -it --rm ${registry} ${cmd}
  2. 检查 Task 配置与镜像的兼容性:

    • 检查 Task 是否配置了 runAsNonRoot: true
    • 检查镜像的默认用户是 root 还是非数字用户 ID。

示例 Task 配置:

apiVersion: tekton.dev/v1
kind: Task
metadata:
  name: foo
spec:
  steps:
    - name: bar
      securityContext:
        runAsNonRoot: true

示例 Containerfile 配置:

USER root

解决方案

方案 1:调整镜像构建配置,将默认用户设置为非 root 用户

前提条件

  • 具备重新构建镜像的环境和权限。

步骤

参考 Adjust Containerfile for Task-Compatible Custom Images 修改 Containerfile 配置。

方案 2:修改 TaskRun 或 PipelineRun 执行配置

前提条件

  • 具备修改 TaskRun 或 PipelineRun 的权限。

步骤

  1. 单独执行 TaskRun 时添加配置:

    apiVersion: tekton.dev/v1
    kind: TaskRun
    metadata:
      name: foo
    spec:
      taskRef:
        name: foo
      podTemplate:
        securityContext:
          runAsUser: 65532
  2. 执行 PipelineRun 时添加配置:

    # 方法 1:为所有 Tasks 添加配置
    apiVersion: tekton.dev/v1
    kind: PipelineRun
    spec:
      taskRunTemplate:
        podTemplate:
          securityContext:
            runAsUser: 65532
    
    # 方法 2:为特定 Tasks 添加配置
    apiVersion: tekton.dev/v1
    kind: PipelineRun
    spec:
      taskRunSpecs:
        - pipelineTaskName: example-git-clone
          podTemplate:
            securityContext:
              runAsUser: 65532
              fsGroup: 65532

方案 3:修改全局 Tekton 配置

前提条件

  • 具备集群操作权限。
  • 具备修改 TektonConfig 资源的权限。
  • 注意:此配置会影响所有 Tasks。

步骤

  1. 修改 TektonConfig 资源: 增加以下 spec.pipeline.default-pod-template 配置:

    apiVersion: config.tekton.dev/v1beta1
    kind: TektonConfig
    metadata:
      name: config
    spec:
      pipeline:
        default-pod-template: |
          securityContext:
            runAsUser: 65532
  2. 验证配置是否生效:

    $ kubectl get configmap -n tekton-pipelines config-defaults -o yaml | grep 'default-pod-template: |' -A2
    
    # Expected output
    default-pod-template: |
      securityContext:
        runAsUser: 65532

方案 4:修改 Task 定义

前提条件

  • 具备修改 Task 的权限。
  • 注意:此配置会影响所有使用该 Task 的 TaskRuns 或 PipelineRuns。

步骤

  1. 方法 1:移除 runAsNonRoot 配置:

    apiVersion: tekton.dev/v1
    kind: Task
    metadata:
      name: foo
    spec:
      steps:
        - name: bar
          securityContext:
            # runAsNonRoot: true
  2. 方法 2:添加 runAsUser 配置:

    apiVersion: tekton.dev/v1
    kind: Task
    metadata:
      name: foo
    spec:
      steps:
        - name: bar
          securityContext:
            runAsNonRoot: true
            runAsUser: 65532

预防错误

  1. 镜像构建

    • 优先使用非 root 用户构建镜像。
    • 统一使用 UID 65532 作为非 root 用户。
    • 确保应用在非 root 用户下可以正常运行。
  2. Task 配置

    • 根据安全要求决定是否启用 runAsNonRoot
    • 如有需要,相应配置 runAsUser
  3. 权限管理

    • 遵循最小权限原则。
    • 提前规划目录权限。
    • 定期检查权限配置。

相关内容