在 K8S Job 中使用 OCI Connector 构建镜像

阅读前请参考 在 K8S 工作负载中使用 OCI Connector 代理的一般逻辑

目录

功能概述

本文将指导您如何在 Kubernetes Job 中使用 OCI Connector 构建镜像并推送到 Registry。借助 OCI Connector 的能力,普通用户无需接触或配置认证凭据,从而最大限度地保障这些凭据的安全性。

在 Kubernetes Job 中使用 OCI Connector 时,需要注意以下要点:

  • 将构建目标镜像的地址更改为 connector 的代理地址。什么是 Connector 代理地址
    • 例如:harbor.example.cn/test/abc:v1 -> harbor.default.cluster.local/test/abc:v1
  • 挂载 Connector 提供的配置。
  • 为客户端工具配置 insecure registry

本文以 buildkitd 为例,详细介绍如何创建 Kubernetes Job,利用 OCI Connector 完成镜像构建和推送,且客户端无需配置认证信息。

前提条件

  • 创建一个 Connector。
  • 用于构建镜像的 Dockerfile。

Connector

kubectl apply -f - <<EOF
apiVersion: connectors.alauda.io/v1alpha1
kind: Connector
metadata:
  name: harbor
spec:
  address: https://harbor.example.com # 替换为可访问的 OCI registry 地址
  auth:
    name: tokenAuth
    params:
    - name: repository
      value: testing/busybox
    secretRef:
      name: harbor-secret
  connectorClassName: oci
---
apiVersion: v1
stringData: # 替换为实际的认证信息
  password: admin
  username: admin
kind: Secret
metadata:
  name: harbor-secret
type: cpaas.io/distribution-registry-token
EOF

Dockerfile

为了演示构建和推送流程,我们需要准备一个 Dockerfile。为简化操作,我们将 Dockerfile 的内容存储在 ConfigMap 中,并通过 Kubernetes Pod 卷挂载到 Pod。

kubectl apply -f - <<EOF
apiVersion: v1
kind: ConfigMap
metadata:
  name: dockerfile
data:
  Dockerfile: |
    FROM scratch
    LABEL maintainer="example@example.com"
    WORKDIR /app
    ENV APP_VERSION="1.0.0"
EOF

操作步骤

创建 K8S Job

  • 为了使用 connector 的代理能力,需要将代理所需的认证信息注入到 docker/config.json,因此必须提供一个卷用于挂载 docker/config.json
  • 为了让客户端访问 HTTP 代理,需要为客户端配置 insecure-registries,因此必须提供一个卷用于挂载 buildkitd.toml
  • 修改推送镜像的地址为 connector 的代理地址。

关于如何获取 Connector 的代理地址,请参见:OCI Connector Class 代理信息说明

Job 内容如下:

cat << EOF | kubectl create -f -
kind: Pod
apiVersion: v1
metadata:
  generateName: buildkit-build-
spec:
  restartPolicy: Never
  containers:
  - name: buildkit
    image: docker-mirrors.alauda.cn/moby/buildkit:v0.18.2
    securityContext:
      privileged: true
    env:
    - name: BUILDKITD_FLAGS
      value: "--config /etc/buildkit/buildkitd.toml"
    command:
    - /bin/sh
    - -c
    args:
    - |
      set -ex
      buildctl-daemonless.sh --debug \
      build \
      --progress=plain \
      --frontend=dockerfile.v0 \
      --opt filename=Dockerfile \
      --local context=/workspace \
      --local dockerfile=/workspace \
      --output type=image,name=c-harbor.default.svc.cluster.local/test/test-cjt:v1,push=true \
      --export-cache type=inline
    volumeMounts:
    - name: dockerfile
      mountPath: /workspace
    - name: docker-config
      mountPath: /root/.docker
    - name: buildkitd-config
      mountPath: /etc/buildkit

  volumes:

  # 将 dockerfile 挂载到 Pod
  - name: dockerfile
    configMap:
      name: dockerfile

  # 将 docker 的 config.json 挂载到 Pod
  - name: docker-config
    csi:
      readOnly: true
      driver: connectors-csi
      volumeAttributes:
        connector.name: "harbor"
        configuration.names: "docker-config"

  # 将 buildkitd.toml 挂载到 Pod
  - name: buildkitd-config
    csi:
      readOnly: true
      driver: connectors-csi
      volumeAttributes:
        connector.name: "harbor"
        configuration.names: "buildkitd"
EOF

操作结果

您可以通过以下命令检查 Job 是否执行成功:

$ kubectl get job

总结

我们完成了“在 K8S Job 中使用 OCI Connector 构建镜像”的全过程。可以看到,在 Job 执行过程中,用户需要指定镜像仓库的认证信息,而在运行 Job 的 Pod 内,用户无法访问 Connector 配置的认证数据。这极大地确保了凭据在实际使用中的不泄露,保障了工具认证信息的安全性。