共用方式為


YAML 管線中的容器作業

Azure DevOps Services | Azure DevOps Server 2022 - Azure DevOps Server 2019

本文說明 Azure Pipelines 中的容器作業。

根據預設,Azure Pipelines 作業 會直接在安裝代理程式的主計算機上執行。 裝載的代理程式作業很方便,需要很少的初始設定和基礎結構才能維護,而且非常適合基本專案。

如果您想要進一步控制工作內容,您可以在容器中定義和執行作業。 容器是主機操作系統的輕量抽象概念,可提供與主機的隔離。 當您在容器中執行作業時,您可以選取組建所需的確切作業系統、工具和相依性版本。

Linux 和 Windows 代理程式 可以直接在主機或容器上執行管線作業。 macOS 上無法使用容器任務。

針對容器作業,代理程式會先擷取並啟動容器。 然後作業的每個步驟都會在容器內執行。

如果您需要個別建置步驟層級的精細控制, 步驟目標 可讓您為每個步驟選擇容器或主機。

必要條件

  • 使用 YAML 管線。 傳統管線不支援容器作業。
  • 使用裝載的 Windows 或 Ubuntu 代理程式。 只有 windows-*ubuntu-* 代理程式支援執行中的容器。 代理 macos-* 程式不支援執行容器。
  • 您的代理程式已針對容器任務進行設定。
    • Windows 和 Linux 代理程式必須已安裝 Docker,而且需要存取 Docker 精靈的許可權。
    • 當代理程式已在容器內執行時,不支援容器。 您無法使用巢狀容器。

其他容器需求

以 Linux 為基礎的容器具有下列需求。 如需因應措施,請參閱 Nonglibc 型容器

  • 已安裝Bash
  • GNU C 連結庫 (glibc) 型
  • ENTRYPOINT
  • 提供 USER 存取 groupadd 及其他高級命令,而不使用 sudo
  • 可以執行代理程式所提供的Node.js

    注意

    Node.js必須針對 Windows 主機上的 Linux 容器預安裝。

Docker Hub 上提供的一些已移除容器,特別是以 Alpine Linux 為基礎的容器,不符合這些需求。 具備 ENTRYPOINT 的容器可能無法運作,因為 Azure Pipelines docker createdocker exec 預期容器始終處於啟動和運行狀態。

單一作業範例

下列範例會定義單一作業的 Windows 或 Linux 容器。

下列簡單範例會定義 Linux 容器:

pool:
  vmImage: 'ubuntu-latest'

container: ubuntu:18.04

steps:
- script: printenv

上述範例會指示系統擷取從 ubuntu 標記的18.04映像,然後啟動容器。 命令 printenv 會在 ubuntu:18.04 容器內執行。

多個作業

您可以使用容器在多個作業中執行相同的步驟。 下列範例會在多個版本的UbuntuLinux中執行相同的步驟。 您不需要提及jobs關鍵詞,因為只定義了一個作業。

pool:
  vmImage: 'ubuntu-latest'

strategy:
  matrix:
    ubuntu16:
      containerImage: ubuntu:16.04
    ubuntu18:
      containerImage: ubuntu:18.04
    ubuntu20:
      containerImage: ubuntu:20.04

container: $[ variables['containerImage'] ]

steps:
- script: printenv

在單一代理主機上具有代理池的多個作業

容器作業會使用基礎主機代理程式的 Docker 組態檔進行映射登錄授權。 此檔案會在 Docker 登錄容器初始化結束時登出。 後續容器作業的登錄映像提取可能會遭到 unauthorized authentication 拒絕,因為另一個以平行方式執行的作業已經註銷 Docker 組態檔。

解決方案是設定 Docker 環境變數 DOCKER_CONFIG ,這是裝載代理程式上所執行之每個代理程式集區特有的。 將DOCKER_CONFIG匯出到每個代理程式集區的 runsvc.sh 腳本,如下所示:

export DOCKER_CONFIG=./.docker

啟動選項

您可以指定 options 來控制容器啟動,如下列範例所示:

container:
  image: ubuntu:18.04
  options: --hostname container-test --ip 192.168.0.1

steps:
- script: echo hello

執行 docker create --help 提供您可以傳遞至 Docker 呼叫的選項清單。 並非所有選項都保證可與 Azure DevOps 搭配使用。 請先檢查,以查看您是否可以使用 container 屬性來完成相同的目標。

如需詳細資訊,請參閱 Azure DevOps YAML 架構參考中的 docker create 命令參考和 resources.containers.container 定義

可重複使用的容器定義

下列範例會定義 區段中的 resources 容器,然後依指派的別名加以參考。 為了清楚起見,關鍵詞 jobs 被明確地列出。

resources:
  containers:
  - container: u16
    image: ubuntu:16.04

  - container: u18
    image: ubuntu:18.04

  - container: u20
    image: ubuntu:20.04

jobs:
- job: RunInContainer
  pool:
    vmImage: 'ubuntu-latest'

  strategy:
    matrix:
      ubuntu16:
        containerResource: u16
      ubuntu18:
        containerResource: u18
      ubuntu20:
        containerResource: u20

  container: $[ variables['containerResource'] ]

  steps:
  - script: printenv

服務端點

您可以在公用 Docker Hub 以外的其他登錄上裝載容器。 若要在 Azure Container Registry 或其他私人容器登錄上裝載映像,包括私人 Docker Hub 登錄,請新增服務連線以存取登錄。 然後,您可以在容器定義中參考端點。

私人 Docker Hub 連線:

container:
  image: registry:ubuntu1804
  endpoint: private_dockerhub_connection

Azure Container Registry 連線:

container:
  image: myprivate.azurecr.io/windowsservercore:1803
  endpoint: my_acr_connection

注意

Azure Pipelines 無法設定 Amazon Elastic Container Registry (ECR) 的服務連線,因為 Amazon ECR 需要其他用戶端工具,才能將 AWS 認證轉換成 Docker 可用來驗證的專案。

非基於glibc的容器

Azure Pipelines 代理程式會提供一份Node.js複本,這是執行工作和腳本所需的複本。 若要瞭解託管代理程式的Node.js版本,請參閱 Microsoft裝載的代理程式。

Node.js 版本針對託管雲中使用的 C 執行時期進行編譯,通常是 glibc。 某些 Linux 變體會使用其他 C 運行時間。 例如,Alpine Linux 使用 musl。

如果您想要使用非glibc 型容器,您需要:

  • 提供您自己的Node.js複本。
  • 將標籤新增至您的影像,告知代理程式在何處尋找Node.js二進位檔。
  • 提供 Azure Pipelines 依賴的其他相依項目:bashsudowhichgroupadd

提供您自己的Node.js

如果您使用非glibc 型容器,您必須負責將節點二進位檔新增至容器。 Node.js 18 是一個安全的選擇。 從 node:18-alpine 映像開始。

告訴代理人關於Node.js

代理程式會讀取容器標籤 "com.azure.dev.pipelines.handler.node.path"。 如果此標籤存在,它必須是Node.js二進位檔的路徑。

例如,在以node:18-alpine為基礎的映像中,將下列這一行新增至您的 Dockerfile:

LABEL "com.azure.dev.pipelines.agent.handler.node.path"="/usr/local/bin/node"

新增必要套件

Azure Pipelines 假設已安裝一般系統管理套件的Bash型系統。 Alpine Linux 尤其沒有隨附數個必要的套件。 安裝 bashsudoshadow 以涵蓋基本需求。

RUN apk add bash sudo shadow

如果您依賴任何內含或 Marketplace 任務,請務必提供它們所需的二進位檔案。

完整的 Dockerfile 範例

FROM node:18-alpine

RUN apk add --no-cache --virtual .pipeline-deps readline linux-pam \
  && apk add bash sudo shadow \
  && apk del .pipeline-deps

LABEL "com.azure.dev.pipelines.agent.handler.node.path"="/usr/local/bin/node"

CMD [ "node" ]