CICD

[AWS/CodeBuild] 서울 리전 CodeBuild에서 빌드된 Docker 이미지를 arm64 인스턴스에서 사용가능하도록 하는 방법

삼콩 2022. 2. 18. 16:05

CodeBuild는 AWS에서 제공하는 소스코드 빌드 서비스이다. CodeBuild는 수행되면 컨테이너를 임시로 생성하여 해당 환경에서 소스코드 빌드, docker image 생성, docker push 등을 수행하게된다.

AWS에서 arm 기반 인스턴스(A1, M6g 등)는 동 성능대비 비용 절감의 효과가 있어 선택하는 경우가 있을 것이라고 생각된다. 서울리전에서 이 인스턴스에 CodeBuild에서 빌드된 docker image를 실행시키고자 하면 정상동작되지 않는다.

 

이유는 docker build를 수행한 CodeBuild (x86_64)와 컨테이너가 실행될 인스턴스(arm)의 명령체계가 달라서이다.

 

공식 문서에따르면 CodeBuild는 현재 x86_64와 arm 이미지를 지원하나, 서울리전 (ap-northeast-2) 에서는 AWS 관리형 arm 이미지를 지원하지 않는다. (https://docs.aws.amazon.com/ko_kr/codebuild/latest/userguide/build-env-ref-compute-types.html)

서울리전 CodeBuild 콘솔 상에 아래와 같이 뜨지만, (허상일뿐...) arm 이미지를 선택하여 생성을 시도하면 오류가 발생한다.

  • amazonlinux2-aarch64-standard: arm 기반
  • amazonlinux2-x86_64-standard: x86_64 기반

정말 기대되는 순간이었다..

The environment type ARM_CONTAINER and compute type BUILD_GENERAL_LARGE combination is not supported in ap-northeast-2

서울 리전 (ap-northeast-2)에서 지원하지 않음😂

 

해결할 수 있는 가장 빠른 방법은 대상 인스턴스의 타입을 x86_64 체계의 인스턴스로 변경하는 방법이 있으나 금액, 혹은 해당 인스턴스에 이미 구동되고 있는 시스템들이 있는 관계로 codebuild를 반드시 arm 환경에서 해야 할 경우 다음의 방법을 사용할 수 있다. 

CodeBuild의 빌드 정의 파일 (buildSpec.yml)에 buildx 설치 스크립트 작성 및 사용

buildx는 Docker의 experimental feature로 제공되고있는 기능으로 다른 플랫폼으로 빌드할 수 있도록 해준다 (docker 19.03 버전부터 사용가능하다). 

CodeBuild의 commands에 아래와 같이 입력하여 buildx를 다운로드 및 구성 한다.

curl -JLO https://github.com/docker/buildx/releases/download/v0.7.1/buildx-v0.7.1.linux-amd64
mkdir -p ~/.docker/cli-plugins
mv buildx-v0.7.1.linux-amd64 ~/.docker/cli-plugins/docker-buildx
chmod a+rx ~/.docker/cli-plugins/docker-buildx
docker run --privileged --rm tonistiigi/binfmt --install all

[명렁어 출처] https://gist.github.com/leepa/260a7f8765a48db094f5cbf2fb45ea48

 

만약 그 과정에서 다음과 같은 오류가 발생한다면, 권한 문제일 수 있으므로 codebuild 아래 권한(Privileged)을 허용해준다.

docker: Cannot connect to the Docker daemon at unix:///var/run/docker.sock. Is the docker daemon running?

 

 

# 환경 구동을 위한 인스턴스 생성
docker buildx create --use --name arm64_env
# docker 이미지 build 및 push
docker buildx build --push --platform=linux/amd64,linux/arm64 -t $AWS_ACCOUNT_ID.dkr.ecr.$AWS_DEFAULT_REGION.amazonaws.com/$IMAGE_REPO_NAME:$IMAGE_TAG .

 

이렇게 생성된 이미지를 arm 인스턴스 (t4g, m6g 등)에서 컨테이너 생성하였을 경우 성공적으로 올라왔다. (나는 ECS 클러스터 테스트 중이였어서 ECS 서비스를 실행하여 확인하였다.)

 

 

 

(AWS는 제발 CodeBuild의 arm 이미지를 서울 리전에서 제공해줬으면...)

 


[참고]
https://gist.github.com/leepa/260a7f8765a48db094f5cbf2fb45ea48

https://aws.amazon.com/ko/blogs/korea/new-m6g-ec2-instances-powered-by-arm-based-aws-graviton2/