

本文為英文版的機器翻譯版本，如內容有任何歧義或不一致之處，概以英文版為準。

# 自備容器的配方
<a name="bring-own-container-recipe"></a>

在本節中，我們提供step-by-step指南，說明您需要bring your own container (BYOC)執行的 Braket 混合任務：指令碼、檔案，以及結合這些指令碼、檔案和步驟，以啟動和執行您的自訂Docker映像。兩個常見案例的配方：

1. 在Docker映像中安裝其他軟體，並在任務中僅使用 Python 演算法指令碼。

1. 使用非 Python 語言撰寫的演算法指令碼搭配混合任務，或 x86 以外的 CPU 架構。

對於案例 2，定義*容器項目指令碼*更為複雜。

當 Braket 執行您的混合任務時，它會啟動請求的 Amazon EC2 執行個體數量和類型，然後執行Docker映像 URI 輸入指定的映像，以在其上建立任務。使用 BYOC 功能時，您可以指定私有 [Amazon ECR 儲存庫](https://docs.aws.amazon.com/AmazonECR/latest/userguide/Repositories.html)中託管的映像 URI，而此儲存庫具有讀取存取權。Braket Hybrid Jobs 使用該自訂映像來執行任務。

建置可與混合任務搭配使用之Docker映像所需的特定元件。如果您不熟悉撰寫和建置 `Dockerfiles`，請參閱 [Dockerfile 文件](https://docs.docker.com/reference/dockerfile/)和 [Amazon ECR CLI 文件](https://docs.aws.amazon.com/AmazonECR/latest/userguide/getting-started-cli.html)。

**Topics**
+ [Dockerfile 的基礎映像](#base-image-dockerfile)
+ [（選用） 修改過的容器進入點指令碼](#modified-container-entry-point)
+ [使用 安裝所需的軟體和容器指令碼 `Dockerfile`](#install-docketfile)

## Dockerfile 的基礎映像
<a name="base-image-dockerfile"></a>

如果您使用的是 Python，並且想要在 Braket 提供的容器中提供的軟體上安裝軟體，則基礎映像的選項是託管於 [GitHub 儲存庫](https://github.com/amazon-braket/amazon-braket-containers)和 Amazon ECR 上的其中一個 Braket 容器映像。您需要[向 Amazon ECR 進行身分驗證](https://docs.aws.amazon.com/AmazonECR/latest/userguide/getting-started-cli.html#cli-authenticate-registry)，才能提取映像並在其上建置。例如，BYOC Docker 檔案的第一行可以是： `FROM [IMAGE_URI_HERE]`

接著，填寫其餘的 Dockerfile來安裝和設定您要新增至容器的軟體。預先建置的 Braket 映像將已包含適當的容器進入點指令碼，因此您不需要擔心是否包含該指令碼。

如果您想要使用非 Python 語言，例如 C\$1\$1、Rust 或 Julia，或者想要為非 x86 CPU 架構建置映像，例如 ARM，您可能需要在裸機公有映像之上建置 。您可以在 [Amazon Elastic Container Registry Public Gallery](https://gallery.ecr.aws/) 找到許多這類影像。請務必選擇適用於 CPU 架構的 GPU，並視需要選擇您要使用的 GPU。

## （選用） 修改過的容器進入點指令碼
<a name="modified-container-entry-point"></a>

**注意**  
如果您只將其他軟體新增至預先建置的 Braket 映像，則可以略過本節。

若要在混合任務中執行非 Python 程式碼，請修改定義容器進入點的 Python 指令碼。例如，[`braket_container.py`Amazon Braket Github 上的 python 指令碼](https://github.com/amazon-braket/amazon-braket-containers/blob/main/src/braket_container.py)。這是 Braket 預先建置的映像用來啟動演算法指令碼並設定適當環境變數的指令碼。容器進入點指令碼本身**必須使用** Python，但可以啟動非 Python 指令碼。在預先建置的範例中，您可以看到 Python 演算法指令碼是以 [Python 子程序](https://github.com/amazon-braket/amazon-braket-containers/blob/main/src/braket_container.py#L274)或[全新的程序](https://github.com/amazon-braket/amazon-braket-containers/blob/main/src/braket_container.py#L257)啟動。透過修改此邏輯，您可以啟用進入點指令碼來啟動非 Python 演算法指令碼。例如，您可以修改 [https://github.com/amazon-braket/amazon-braket-containers/blob/main/src/braket_container.py#L139](https://github.com/amazon-braket/amazon-braket-containers/blob/main/src/braket_container.py#L139) 函數，根據副檔名結尾啟動 Rust 程序。

您也可以選擇撰寫全新的 `braket_container.py`。它應該將輸入資料、來源封存和其他必要的檔案從 Amazon S3 複製到容器中，並定義適當的環境變數。

## 使用 安裝所需的軟體和容器指令碼 `Dockerfile`
<a name="install-docketfile"></a>

**注意**  
如果您使用預先建置的 Braket 映像作為Docker基礎映像，則容器指令碼已存在。

如果您在上一個步驟中建立了修改過的容器指令碼，則需要將其複製到容器中，**並將**環境變數定義為 `SAGEMAKER_PROGRAM` `braket_container.py`，或您已命名為新容器進入點指令碼的內容。

以下是`Dockerfile`可讓您在 GPU 加速任務執行個體上使用 Julia 的 範例：

```
FROM nvidia/cuda:12.2.0-devel-ubuntu22.04

    
 ARG DEBIAN_FRONTEND=noninteractive
 ARG JULIA_RELEASE=1.8
 ARG JULIA_VERSION=1.8.3


 ARG PYTHON=python3.11 
 ARG PYTHON_PIP=python3-pip
 ARG PIP=pip


 ARG JULIA_URL = https://julialang-s3.julialang.org/bin/linux/x64/${JULIA_RELEASE}/
 ARG TAR_NAME = julia-${JULIA_VERSION}-linux-x86_64.tar.gz


 ARG PYTHON_PKGS = # list your Python packages and versions here


 RUN curl -s -L ${JULIA_URL}/${TAR_NAME} | tar -C /usr/local -x -z --strip-components=1 -f -


 RUN apt-get update \

    && apt-get install -y --no-install-recommends \

    build-essential \

    tzdata \

    openssh-client \

    openssh-server \

    ca-certificates \

    curl \

    git \

    libtemplate-perl \

    libssl1.1 \

    openssl \

    unzip \ 

    wget \

    zlib1g-dev \

    ${PYTHON_PIP} \

    ${PYTHON}-dev \




 RUN ${PIP} install --no-cache --upgrade ${PYTHON_PKGS}


 RUN ${PIP} install --no-cache --upgrade sagemaker-training==4.1.3


 # Add EFA and SMDDP to LD library path
 ENV LD_LIBRARY_PATH="/opt/conda/lib/python${PYTHON_SHORT_VERSION}/site-packages/smdistributed/dataparallel/lib:$LD_LIBRARY_PATH"
 ENV LD_LIBRARY_PATH=/opt/amazon/efa/lib/:$LD_LIBRARY_PATH


 # Julia specific installation instructions
 COPY Project.toml /usr/local/share/julia/environments/v${JULIA_RELEASE}/
 RUN JULIA_DEPOT_PATH=/usr/local/share/julia \

    julia -e 'using Pkg; Pkg.instantiate(); Pkg.API.precompile()'
 # generate the device runtime library for all known and supported devices
 RUN JULIA_DEPOT_PATH=/usr/local/share/julia \

    julia -e 'using CUDA; CUDA.precompile_runtime()'


 # Open source compliance scripts
 RUN HOME_DIR=/root \

 && curl -o ${HOME_DIR}/oss_compliance.zip https://aws-dlinfra-utilities.s3.amazonaws.com/oss_compliance.zip \

 && unzip ${HOME_DIR}/oss_compliance.zip -d ${HOME_DIR}/ \

 && cp ${HOME_DIR}/oss_compliance/test/testOSSCompliance /usr/local/bin/testOSSCompliance \

 && chmod +x /usr/local/bin/testOSSCompliance \

 && chmod +x ${HOME_DIR}/oss_compliance/generate_oss_compliance.sh \

 && ${HOME_DIR}/oss_compliance/generate_oss_compliance.sh ${HOME_DIR} ${PYTHON} \

 && rm -rf ${HOME_DIR}/oss_compliance*


 # Copying the container entry point script
 COPY braket_container.py /opt/ml/code/braket_container.py
 ENV SAGEMAKER_PROGRAM braket_container.py
```

此範例會下載並執行 提供的指令碼 AWS ，以確保符合所有相關開放原始碼授權。例如，透過正確歸因由 管理的任何已安裝程式碼MIT license。

如果您需要包含非公有程式碼，例如託管在私有 GitHub 或 GitLab 儲存庫中的程式碼，**請勿**在Docker映像中嵌入 SSH 金鑰來存取它。相反地，請在建置Docker Compose時使用 ，以允許 Docker 存取其建置所在的主機電腦上的 SSH。如需詳細資訊，請參閱 [Docker 中的安全使用 SSH 金鑰存取私有 Github 儲存庫](https://www.fastruby.io/blog/docker/docker-ssh-keys.html)指南。

**建置和上傳Docker映像**

使用正確定義的 `Dockerfile`，您現在可以依照步驟[建立私有 Amazon ECR 儲存庫](https://docs.aws.amazon.com/AmazonECR/latest/userguide/repository-create.html)，如果其中尚未存在的話。您也可以建置、標記容器映像並將其上傳至儲存庫。

您已準備好建置、標記和推送映像。如需 選項的完整說明`docker build`和一些範例，請參閱 [Docker 建置文件](https://docs.docker.com/reference/cli/docker/buildx/build/)。

對於上述定義的範例檔案，您可以執行：

```
aws ecr get-login-password --region ${your_region} | docker login --username AWS --password-stdin ${aws_account_id}.dkr.ecr.${your_region}.amazonaws.com
 docker build -t braket-julia .
 docker tag braket-julia:latest ${aws_account_id}.dkr.ecr.${your_region}.amazonaws.com/braket-julia:latest
 docker push ${aws_account_id}.dkr.ecr.${your_region}.amazonaws.com/braket-julia:latest
```

**指派適當的 Amazon ECR 許可**

Braket Hybrid Jobs Docker 映像必須託管在私有 Amazon ECR 儲存庫中。根據預設，私有 Amazon ECR 儲存庫**不會**提供對 Braket Hybrid Jobs IAM role或任何其他要使用您映像的使用者的讀取存取權，例如協作者或學生。您必須[設定儲存庫政策](https://docs.aws.amazon.com/AmazonECR/latest/userguide/set-repository-policy.html)來授予適當的許可。一般而言，只將許可授予您想要存取映像的特定使用者和IAM角色，而不是允許具有 的任何人image URI提取它們。