본문 바로가기
스터디/docker 스터디

도커 이미지 만들기

by xladmt 2025. 3. 13.

1. 도커 이미지 살펴보기

> docker image 내려받기

docker image pull [내려받을 이미지의 이름]

ex) docker image pull diamol/ch03-web-ping

  • 이미지 이름 : diamol/ch03-web-ping
  • 이 이미지는 도커가 가장 먼저 이미지를 찾기 위해 접근하는 저장소인 도커 허브에 저장되어 있음
  • 도커 허브는 무료로 제공되는 공개 레지스트리 
    • 레지스트리(registry) : 이미지를 제공하는 저장소

 

docker image

  • 도커 이미지는 논리적으로는 하나의 대상이다.
    • 애플맄이션 스택 전체가 하나의 파일로 압축된 압축 파일을 생각하면 쉽게 이해할 수 있다.
  • 이미지를 내려받는 과정을 보면 여러 파일을 동시에 내려받는다.
    • 이들 각각의 파일을 레이러라고 부른다.
    • 도커가 이들 파일을 조립해 컨테이너의 내부 파일 시스템을 만든다.
    • 모든 레이어를 내려받고 나면 전체 이미지를 사용할 수 있게 된다.

 

> 내려받은 이미지로 컨테이너 실행하기

docker container run -d --name web-ping diamol/ch03-web-ping
  • -d : --detach의 축약형. 이 컨테이너는 백그라운드에서 동작.
    • 이 컨테이너는 네트워크를 통해 요청을 받지 않음. 고로, 포트를 외부로 공개할 필요 없음.
  • --name : "web-ping" 이라는 이름을 붙임.
    • 컨테이너를 조작하려면 처음 실행할 때 임의로 생성된 컨테이너 ID를 입력해 대상 컨테이너를 지정해줘야함.
    • 하지만, --name 플래그를 사용하면 컨테이너에 원하는 이름을 붙아고 이 이름으로 컨테이너를 지칭할 수 있음

 

> 도커에 수집된 log 보기

docker container logs web-ping

log를 보면 blog.sixeyed.com에 HTTP 요청을 보내고 있음을 알 수 있다. 

  • 웹 요청을 보내고 해당 애플리케이션은 요청에 대한 응답 시간, 웹 사이트 동작 여부 등을 확인할 수 있다.
  • 애플리케이션에서 대상 URL과 요청 간격, 요청 타입 등을 설정할 수 있다.
  • 시스템의 환경 변수 값에서 설정값을 읽어 온다.
  • 환경변수는 운영체제에서 제공하는 키-값 쌍이다.

 

> 실행 중인 컨테이너를 삭제하고 환경 변수 TARGET의 값을 다른 값으로 지정한 새로운 컨테이너를 실행

docker rm -f web-ping
docker container run --env TARGET=google.com diamol/ch03-web-ping

=> 아까와 같은 이미지로 생성한 컨테이너이지미나, 이번에는 google.com에 요청을 보낸다.

--env TARGET=google.com : 애플리케이션에서 사용할 환경 변수 값을 지정한 부분

 

도커 이미지는 설정값의 기본값을 포함해 패키징되지만, 컨테이너를 실행할 때 이 설정값을 바꿀 수 있어야 한다!

 

 

2. Dockerfile 작성하기

Dockerfile이란? 애플리케이션을 패키징하기 위한 간단한 스크립트

  • Dockerfile은 일련의 인스트럭션으로 구성돼 있는데, 인스트럭션을 실행한 결과로 도커 이미지가 만들어진다.
  • Dockerfile 문법은 배우기 쉬우며 어떤 애플리케이션이라도 패키징할 수 있다.

 

> web-ping 애플리케이션의 Dockerfile 스크립트

FROM diamol/node

ENV TARGER="blog.sixeyed.com"
ENV METHOD="HEAD"
ENV INTERVAL="3000"

WORKDIR /web-ping
COPY app.js .

CMD ["node", "/web-ping/app.js"]
  • FROM : 모든 이미지는 다른 이미지로부터 출발한다. 이 이미지는 diamol/node 이미지를 시작점으로 지정했다. diamol/node 이미지에는 web-ping 애플리케이션을 실행하는 데 필요한 런타임인 Node.js가 설치 돼 있다.
  • ENV : 환경 변수 값을 지정하기 위한 인스트럭션이다. 값을 지정하기 위해 키="벨류" 형식을 따른다. 이 스크린트에는 ENV 인스트럭션이 세 번 사용돼 세 개의 환경 변수를 설정했다.
  • WORKDIR : 컨테이너 이미지 파일 시스템에 디렉터리를 만들고, 해당 디렉터리를 작업 디렉터리로 지정하는 인스트럭션이다. 즉, 리눅스 컨테이너에서는 /web-ping 디렉터리를 만들고, 윈도우 컨테이너에서는 C:/web-ping 디렉터리를 만든다.
  • COPY : 로컬 파일 시스템의 파일 혹은 디렉터리를 컨테이너 이미지로 복사하는 인스트럭션이다. [원본 경로] [복사 경로] 형식으로 지정하면 된다. 로컬 파일 시스템에 있는 app.js 파일을 이미지의 작업 디렉터리로 복사했다.
  • CMD : 도커가 이미지로부터 컨테이너를 실행했을 때 실행할 명령을 지정하는 인스트럭션이다. 여기서는 Node.js 런타임이 애플리케이션을 시작하도록 app.js를 지정했다.

 

> Dockerfile을 직접 작성할 필요는 없다. 코드 저장소를 복제한 경로에서 이미지를 빌드하기 위한 모든 파일이 갖춰졌는지 다음 명령을 실행해보자.

cd ch03/exercises/web-ping
ls
  • Dockerfile(확장자 없음)
  • app.js : web-ping 애플리케이션을 구현한 Node.js 코드가 담긴 파일이다.
  • README.md : 이 이미지에 대한 정보가 적힌 문서 파일이다.

 

 

3. 컨테이너 이미지 빌드하기

이미지를 빌드하려면 Dockerfile 스크립트 외에도 필요한 것이 있다. 이미지의 이름, 패키징에 필요한 파일의 경로를 추가로 지정해 주어야 한다. 

> docker image build 명령을 사용해 Dockerfile 스크립트로 이미지 빌드하기

docker image build --tag web-ping .
  • --tag : 태그는 새로 빌드되는 이미지의 이름
  • . : 여기에 이미지에 들어갈 파일이 위치한 디렉터리를 기재한다. "."은 현재 디렉터리를 의미.

 

> 태그명으로 이미지 확인하기

docker image ls w*
  • w* : 'w'로 시작하는 태그명을 가진 이미지 목록을 확인해라.

 

> 새로 빌드한 이미지로부터 컨테이너를 실행해 도커 웹 사이트에 5초마다 요청을 보내보자.

docker container run -e TARGET=dockercom -e INTERVAL=5000 web-ping

- 환경변수로 대상 URL과 요청 간격을 지정한다.

 

 

4. 도커 이미지와 이미지 레이어 이해하기

> web-ping 이미지의 히스토리 확인하기

docker image history web-ping

- 이 명령을 입력하면 한 줄마다 한 레이어에 대한 정보가 나온다.

 

 

> 이미지 목록에서 각 이미지의 용량 확인하기

docker image ls

* 이미지 목록의 size 항목에 나오는 수치는 이미지의 논리적 용량이지 해당 이미지가 실제로 차지하는 디스크 용량을 나타내는 것이 아니다. 다른 이미지와 레이어를 공유하면 여기에 나온 수치보다 디스트 용량을 훨씬 덜 차지한다.

docker system df

*이미지 저장에 실제 사용된 디스트 용량은 system df 명령으로 확인할 수 있다.

 

5. 이미지 레이어 캐시를 이용한 Dockerfile 스크립트 최적화

  • 이미지 내의 파일을 수정하고 미이지를 다시 빌드하면, 새로운 이미지 레이어가 생긴다.
  • 레이어가 변경되면 변경된 레이어보다 위에 오는 레이어를 재사용 할 수 없다.

 

> ch03-web-ping 디렉터리에 있는 app.js 파일을 수정해보자. (빈 줄 추가만 해도 됨)

docker image build -t web-ping:v2
  • Dockerfile 스크립트의 인스트럭션은 각각 하나의 이미지 레이어와 1:1로 연결된다.
  • 그러나 인스트럭션의 결과가 이전 빌드와 같다면, 이전에 캐시된 레이어를 재사용한다.
  • 이런 방법으로 똑같은 인스트럭션을 다시 실행하는 낭비를 줄일 수 있다.

 

  • 도커는 캐시에 일치하는 레이어가 있는지 확인하기 위해 해시값을 이용한다.
  • 해시는 입력값이 같은지 확인할 수 있는 일종의 디지털 지문이다.
  • 해시값은 Dockerfile 스크립트의 인스트럭션과 인스트럭션에 의해 복사되는 파일의 내용으로부터 계산되는데, 기존 이미지 레이어에 해시값이 일치하는 것이 없다면 캐시 미스가 발생하고 해당 인스트럭션이 실행된다.
    • 한 번 인스트럭션이 실행되면 그 다음에 오는 인스트럭션은 수정된 것이 없더러가도 모두 실행된다.
  • 이러한 이유로 Dockerfile 스크립트의 인스트럭션은 잘 수정하지 않는 인스트럭션이 앞으로 오고 자주 수정되는 인스트럭션이 뒤에 오도록 배치돼야 한다.
    • 이렇게 해야 캐시에 저장된 이미지 레이어를 되도록 많이 재사용할 수 있다.
    • 이미지를 공유하는 과정에서 시간은 물론이고 디스크 용량, 네트워크 대역폭을 모두 절약할 수 있는 방법이다.

 

> 스크립트 최적화한 결과

FROM diamol/node

CMD ["node", "/web-ping/app.js"]

ENV TARGER="blog.sixeyed.com" \
    METHOD="HEAD" \
    INTERVAL="3000"

WORKDIR /web-ping
COPY app.js .

 

 

[참고 도서]

< 도커 교과서 > (저)엔튼 스톤맨, (옮김) 심효섭

 

'스터디 > docker 스터디' 카테고리의 다른 글

컨테이너 가상화  (0) 2024.10.06