목적: ECR에서 Requirements 같이 image가 관리 가능한지 확인, 가능할 경우 방법 및 적용.
단일 tag 안에서 나뉘어 관리되는 것이 docker repo 자체 기능인지, registry 별로 별도 지원해야하는 것인지 확인 필요
단일 tag일 경우, image pull 진행 시 platform 선택이 어떻게 이루어지는 것인지 확인 필요
명시적으로 platform을 지정해야하는지, 지정안했을 경우 어떻게 동작하는지 등
기존 ECR 문제점 확인
ECR 구조 설명
ECR은 내부적으로 repo아래에 Config 와 Layers로 분리되어 있습니다. 다들 docker push를 하시면서 layer가 하나씩 업로드 되는 상황들을 한번씩 보셨으리라 생각됩니다. ![]() |
Docker Manifest 확인
Docker inspect 명령어를 사용하면 Docker 개발 환경에서의 로컬 이미지의 Manifest 확인 가능
$ docker inspect 2fd81e4837329c8f8f90b1285854dffe4ee3e412af21f1077cfc8318e14ca186
ID기준으로 Config 하위에 어려가지 정보들이 있는 것을 확인 가능.
- Config
- Architecture
- OS
[
{
"Id": "sha256:112222",
"RepoTags": [
"2.dkr.ecr.ap-northeast-2.amazonaws.com/ecr-repo-an2-public-st:arm64",
"2.dkr.ecr.ap-northeast-2.amazonaws.com/ecr-repo-an2-public-st:latest",
"hello:arm64"
],
"RepoDigests": [
"22222.dkr.ecr.ap-northeast-2.amazonaws.com/ecr-repo-an2-public-e4121adb241fa518"
],
"Parent": "",
"Comment": "buildkit.dockerfile.v0",
"Created": "2023-01-17T01:23:11.125330987Z",
"Container": "",
"ContainerConfig": {
"Hostname": "",
"Domainname": "",
"User": "",
"AttachStdin": false,
"AttachStdout": false,
"AttachStderr": false,
"Tty": false,
"OpenStdin": false,
"StdinOnce": false,
"Env": null,
"Cmd": null,
"Image": "",
"Volumes": null,
"WorkingDir": "",
"Entrypoint": null,
"OnBuild": null,
"Labels": null
},
"DockerVersion": "",
"Author": "",
"Config": {
"Hostname": "",
"Domainname": "",
"User": "",
"AttachStdin": false,
"AttachStdout": false,
"AttachStderr": false,
"ExposedPorts": {
"8080/tcp": {}
},
"Tty": false,
"OpenStdin": false,
"StdinOnce": false,
"Env": [
"PATH=/usr/local/sbin:/usr/local/bin:/usr/sbin:/usr/bin:/sbin:/bin"
],
"Cmd": null,
"Image": "",
"Volumes": null,
"WorkingDir": "/app",
"Entrypoint": [
"./hello"
],
"OnBuild": null,
"Labels": null
},
"Architecture": "amd64",
"Os": "linux",
"Size": 7192365,
"VirtualSize": 7192365,
"GraphDriver": {
"Data": {
"LowerDir": "/var/lib/docker/overlay2/pzyhi6eizefv36oopt7tveopg/diff",
"MergedDir": "/var/lib/docker/overlay2/dwiu7tr71x21s7sf0sruant1b/merged",
"UpperDir": "/var/lib/docker/overlay2/dwiu7tr71x21s7sf0sruant1b/diff",
"WorkDir": "/var/lib/docker/overlay2/dwiu7tr71x21s7sf0sruant1b/work"
},
"Name": "overlay2"
},
"RootFS": {
"Type": "layers",
"Layers": [
"sha256:2",
"sha256:2"
]
},
"Metadata": {
"LastTagTime": "2023-01-17T01:24:13.826609381Z"
}
}
]
문제점 확인
- ECR내부적으로 Config / Layers 로 분리 되어 있음
- Config 하위에 Architecture 정보가 저장됨
- 기존 구조에서 여라가지 Architecture를 지원하기 위해서는 별도의 Tag를 생성하여 이미지를 사용(Pull)해야 함
- /my-image-linux-arm64:2.7 와 같은 태깅 형태가 필요.
- 1개의 tag에서 Archiectre별로 나눠 주지 못함
ECR Multi Architecture
- 기존 구조에서 Docker Manifest List가 추가 되어 각각의 Architecture 별로 분리되는 구조.
- Docker Manifest List가 여러개의 Archtecture Image를 싸고 있는 형태
목표
- Amd64/ Arm64 이미지를 생성하여 T20-st ECR에 Push하여
- 하나의 Latest(tag) 버전으로 2개의 Architecture 이미지가 정상 동작하는지 확인
설명
초반 구조에 대해 이야기를 조금 하는데, 그 이후에는 삽질 하는 것들이 나오니 빠른 결과를 보시려면 35분 이후로 이동하셔서 듣는 걸 추천
Takeaway
- 사전 arm64/ amd 64 build한 Output img 필요
- Architecture별 이미지 Docker (tag / push)하여 ECR에 업로드
# Tag
$ docker tag hello:arm64 1.dkr.ecr.ap-northeast-2.amazonaws.com/ecr-repo-an2-public-st:arm64
$ docker tag hello:amd64 1.dkr.ecr.ap-northeast-2.amazonaws.com/ecr-repo-an2-public-st:amd64
# Push
$ docker push 1.dkr.ecr.ap-northeast-2.amazonaws.com/ecr-repo-an2-public-st:arm64
$ docker push 1.dkr.ecr.ap-northeast-2.amazonaws.com/ecr-repo-an2-public-st:arm64
ECR이 제대로 Push 되어 있는지 확인
- ECR이 제대로 Push 되어 있는지 확인
# ECR Image list
$ aws ecr --region ap-northeast-2 describe-images --repository-name ecr-repo-an2-public-st
- Docker manifest 생성
# Create Manifest
docker manifest create ${AWS_ACCOUNT_ID}.dkr.ecr.${AWS_REGION}.amazonaws.com/${ECR_REPO_NAME} \
# ${AWS_ACCOUNT_ID}.dkr.ecr.${AWS_REGION}.amazonaws.com/${ECR_REPO_NAME}:${amd64} \
# ${AWS_ACCOUNT_ID}.dkr.ecr.${AWS_REGION}.amazonaws.com/${ECR_REPO_NAME}:${arm64}
# Add Annotation
docker manifest annoate --arch arm64 ${AWS_ACCOUNT_ID}.dkr.ecr.${AWS_REGION}.amazonaws.com/${ECR_REPO_NAME} \
# ${AWS_ACCOUNT_ID}.dkr.ecr.${AWS_REGION}.amazonaws.com/${ECR_REPO_NAME}:${arm64}
Manifest 확인
# Manifest Inspection
docker manifest inspect ${AWS_ACCOUNT_ID}.dkr.ecr.${AWS_REGION}.amazonaws.com/${ECR_REPO_NAME}
# Manifest push
docker manifest push ${AWS_ACCOUNT_ID}.dkr.ecr.${AWS_REGION}.amazonaws.com/${ECR_REPO_NAME}
결과
Architecture 별 Docker 실행 및 동작 확인
# Docker run
docker run --platform=linux/arm64 -d -p 8080:8080 2.dkr.ecr.ap-northeast-2.amazonaws.com/ecr-repo-an2-public-st:latest
docker run --platform=linux/amd64 -d -p 8080:8080 2.dkr.ecr.ap-northeast-2.amazonaws.com/ecr-repo-an2-public-st:latest
- Latest 1개의 Tag로 Architecture 별로 분리되어 Img 사용 가능
- 실행 관점으로 여러 Architecture를 관리해야 한다면 명시적으로 선언하는 것이 필요하다고 생각 됨
- 예) --paltform=linux/arm64
- docker run시에 --platform 옵션을 제외하고 실행시에는
- Local Machine의 Architecture Dependent하게 실행하고 동작 됨.
참조
(공식) AWS multi-architecture container images for amazon ECR
Docker manifest 활용하여 Multi-Architecture DockerHub에 올리기
'개발' 카테고리의 다른 글
Fluent Operator 이해하기 (2) | 2024.01.25 |
---|---|
Fluent-bit를 통한 Kubernetes 로그환경 구축 (0) | 2023.04.03 |
Kubernates Rolling Update 무중단 배포 (2) | 2022.12.28 |
MSA 성능 향상을 위한 gRPC 이해 및 적용 (0) | 2022.11.18 |
OIDC Auth2.0 Hydra (0) | 2022.11.09 |