Docker&K8s

CH_02 컨테이너 배포 (1)

dding-shark 2025. 7. 21. 15:56
728x90

Chapter 2 컨테이너 배포

2.1 컨테이너로 애플리케이션 실행하기

  • 컨테이너 이미지 & 컨테이너
    • 컨테이너 이미지 : 컨테이너를 구성하는 FileSystem과 Application및 설정들을 모은것, 컨테이너를 생성하기 위해 사용하는 템플릿
    • 컨테이너 : 컨테이너 이미지를 기반으로, 생성되고, 구현된 FileSystem과 Application이 실행되는 상태
     

2.1.1 컨테이너 이미지와 컨테이너 기초

  • 컨테이너 레지스트리와 이미지 지정
    • 컨테이너 이미지 -> 컨테이너 레지스트리에서 다운
      • 컨테이너 레지스트리
        • 도커허브(Docker Hub)
          • golang / golang:1.20.5 / mysql ....
        • 기타 레지스트리 :
          • ghcr.io/jpudocker/echo... 기타 도메인들(ghcr.io -> GitHub Container Registry)

  • 이미지 가져오기
<이미지 가져오기 (Docker Hub, Ubuntu:23.10)
  docker image pull ubuntu:23.10
<실행 결과>  
cd0bff360add: Pull complete
Digest: sha256:fd7fe639db24c4e005643921beea92bc449aac4f4d40d60cd9ad9ab6456aec01
Status: Downloaded newer image for ubuntu:23.10
docker.io/library/ubuntu:23.10 

  • 컨테이너 실행하기

<컨테이너 실행하기> 
docker conatiner run [컨테이너 이미지] [컨테이너에서 실행할 커맨드]
docker container run ubuntu:23.10 uname -a

<실행 결과>
Linux c0f180a0e540 6.6.87.1-microsoft-standard-WSL2 #1 SMP PREEMPT_DYNAMIC Mon Apr 21 17:08:54 UTC 2025 x86_64 x86_64 x86_64 GNU/Linux

  • 이미지 가져와서 실행하기
<이미지 가져와서 실행하기 (기타 레지스트리:ghcr.io/jpubdocker/echo:v0.1.0)>  
docker container run --name echo -it -p 9000:8080 ghcr.io/jpubdocker/echo:v0.1.0

<실행 결과>  
PS C:\\Users\\soh10> docker container run --name echo -it -p 9000:8080 ghcr.io/jpubdocker/echo:v0.1.0  
Unable to find image 'ghcr.io/jpubdocker/echo:v0.1.0' locally  
v0.1.0: Pulling from jpubdocker/echo  
6a299ae9cfd9: Pull complete  
e08e8703b2fb: Pull complete  
68e92d11b04e: Pull complete  
4105062d1ee6: Pull complete  
23e7e6e9302a: Pull complete  
e30a39fc6986: Pull complete  
4f4fb700ef54: Pull complete  
29cb5667800e: Pull complete  
b79ec5314518: Pull complete  
e5849aee2f7e: Pull complete  
Digest: sha256:acb116c8915502ef7a858f0c3522d342cb17c4dccc15c6bc71f1c9cf10438613  
Status: Downloaded newer image for ghcr.io/jpubdocker/echo:v0.1.0  
2025/07/21 05:21:08 Start server

<호출>  
PS C:\\Users\\soh10> curl [http://localhost:9000](http://localhost:9000)

StatusCode : 200  
StatusDescription : OK  
Content : Hello Container!!  
RawContent : HTTP/1.1 200 OK  
Content-Length: 17  
Content-Type: text/plain; charset=utf-8  
Date: Mon, 21 Jul 2025 05:23:05 GMT


                Hello Container!!


Forms : {}  
Headers : {\[Content-Length, 17\], \[Content-Type, text/plain; charset=utf-8\], \[Date, Mon, 21 Jul 2025 05:23:05 GMT\]}  
Images : {}  
InputFields : {}  
Links : {}  
ParsedHtml : mshtml.HTMLDocumentClass  
RawContentLength : 17

-p 9000:8080의 의미 :

  • 포트포워딩
    • -p [Host Port] : [Container Port]
      • 컨테이너 가상화 기법으로 인해 파일 시스템에서 완전히 OS와 분리가 되어있기때문에 서로 다른 기기라고 보는것이 타당하다.
      • 그럼... Host의 포트를 같이 쓰는것도... 말이안된다.
      • 따라서 저런 설정이 나온 이유는 Host의 9000번 포트로 어떤 요청이 들어오면, 컨테이너에서의 8080포트로 포워딩 해준다.

  • localhost:9000 으로 어떤 요청이오면 -> 컨테이너에서 localhost:8080 으로 넘겨준다!
  • 둘다 같은 PC 에서 127.0.0.1을 사용하고있지만... 혼동하면 안된다.
  • 이때, localhost:8080으로 크롬키고 눌러보면 아무 반응이 없디 -> 왜? Host의 8080포트에는 아무것도 읎다!

한때 이걸로 뭔가... 시행착오가 많았어서...

  • 시나리오 :
    • 현제 컴퓨터에 mysql이 3306번 포트에서 실행중이다.
    • 하지만 도커로 mysql을 하나더 켜야하는 상황이 일어나 버렸다,
    • 이때,
      • mysql을 docker run --name mysql -it -p 3307:3306 mysql
    • 이렇게 실행했을때 로컬 PC의 HeidiSQL 로 도커에서 실행 시키는 db를 불러오고 싶으면 ->
      • localhost:3307으로 접속해야한다.
    • 도커 내부 쉘에서 도커에서 실행중에 mysql 내부로 들어가고 싶으면,
      • localhost:3306으로 접속해야한다.

  • 컨테이너 종료
<컨테이너 종료>  
docker container stop \[컨테이너명| 컨테이너ID\]

<작동중인 컨테이너 확인>  
docker ps

<결과>  
PS C:\\Users\\soh10> docker ps  
CONTAINER ID IMAGE COMMAND CREATED STATUS PORTS NAMES  
fcd729e7268e ghcr.io/jpubdocker/echo:v0.1.0 "go run main.go" 3 minutes ago Up About a minute 0.0.0.0:9000->8080/tcp echo

<컨테이너 종료>  
docker container stop scho

<작동중인 컨테이너 확인>  
PS C:\\Users\\soh10\\Desktop\\DDING\\Book\\Docker&K8s> docker ps  
CONTAINER ID IMAGE COMMAND CREATED STATUS PORTS NAMES  
PS C:\\Users\\soh10\\Desktop\\DDING\\Book\\Docker&K8s>

간단한 애플리케이션과 컨테이너 이미지 만들기

FROM golang:1.20.5

WORKDIR /go/src/github.com/jpubdocker/echo
COPY main.go .
RUN go mod init

CMD ["go", "run", "main.go"]
  • 인스트럭션(Instruction)
    • DockerFile은 도메인 특화언어(DSL)을 사용해 이미지 구성을 정의한다.
    • FROM/COPY/RUN 과 같은 키워드를 인스트럭션이라고 한다.
  • FROM :
    • 생성할 컨테이너 이미지의 기본이미지(baseImage)를 지정하낟.
      • 컨테이너를 생성할때 가장 먼저 다운로드 하고 실행한다.
    • FROM golang:1.20.5
      • golang <- 도커 허브에 등록되어 있는 이미지
      • :1.20.5 <- 버전관리 식별자 / 미입력시 latest
  • WORKDIR
    • 컨테이너 내 현제 디랙터리를 지정한다. / 디랙토리가 없으면 새로 생성
      WORKDIR컨테이너 내부의 작업 디렉터리를 지정하는 명령어. 이후에 실행되는 , CMD, COPY, ADD 와 같은 명령어들이 해당 디렉터리를 기준으로 동작
  • COPY
    • 빌드 콘텍스트 파일과 디랙토리를 컨테이너 내 복사하는 인스트럭션,
      • COPY[빌드 콘텍스트의 경로][새 컨테이너 내 작업 디렉터리] 의 형식으로 정의
      • COPY main.go .
        • main.go 를 .에 복사
  • RUN
    • 컨테이너 이미지를 빌드할때 컨테이너에서 실행하는 커맨드를 정의
    • 패키지 매니저를 사용한 도구의 설치나, 애플리케이션 빌드등을 처리
    • RUN go mod init
      • go run main.go 를 실행하기 위해 go.mod 파일이 필요 <- go mod init 실행해서 받아옴
  • CMD
    • 컨테이너를 실행할때 컨테이너에서 실행할 프로세스를 지정하낟.
    • RUN 과 달리 컨테이너 시작시 한번만 실행
    • CMD ["go", "run", "main.go"]
      • 컨테이너 내부에서 go run main.go 를 실행시키기 위해 공백 단위로 분리하여 작성
      • 인수 작성 방식
        • CMD["실행 파일", "인수1","인수2"]
        • CMD 커맨드 인수1 인수2
        • CMD["인수1","인수2] <- ENTRYPOINT 사용시 / 실행 파일이 이미 적혀있는거!

  • RUN VS CMD
구분 RUN CMD
실행 시점 docker build 명령어로 이미지를 빌드할 때. docker run 명령어로 컨테이너를 시작할 때
목적 애플리케이션 및 라이브러리 설치, 소스코드 빌드 등 이미지 자체를 구성하기 위해 빌드된 이미지 기반의 컨테이너 안에서 실제 애플리케이션을 실행하기 위해
사용 횟수 Dockerfile 내에서 여러 번 사용할 수 있으며, 각 명령어는 이미지에 새로운 레이어(layer)를 추가 RUN Dockerfile 내에서 여러 번 작성할 수 있지만, 가장 마지막 CMD 하나만 적용
재정의 이미지의 일부이므로 docker run 시점에 변경할 수 없음. docker run [이미지] [다른 명령어] 형식으로 컨테이너 시작 시 쉽게 변경(override)가능
  • 간단한 비유
    • RUN: 집을 짓는 과정(build)에서 벽지를 바르고, 가구를 설 치하는 것. (환경 설정)
    • CMD: 다 지어진 집에 들어가서(run) TV를 켜거나 음악을 트는 것 (애플리케이션 실행)
  • 추가 인터럽트
    • ENTRYPOINT 커맨드
      • ENTRYPOINT 커맨드를 지정하면, CMD의 인수는, ENTRYPONT로 실행하는 파일의 인수가 된다.
      • ENTRYPOINT 의 서브커맨드 부분만 전달 할 수 있다 -> 제한적 사용에서 사요
    • LABEL
      • 이미지 생성자 정보 기입
    • ENV
      • 환경 변수 지정
    • ARG
      • 이미지 빌드시에만 사용 할 수 있는 임시변수

  • 이미지 실행
  • <dockerfile 로 이미지 빌드하기> docker image build -t [이미지 명][:테그명] [dockerfile의 디렉터리 경로] (dockerfile 있는 디렉토리)~ docker image build --no-cache -t ch02/echo:latest .

<실행 결과>  
PS C:\\Users\\soh10\\Desktop\\DDING\\Book\\Docker&K8s> docker image ls  
REPOSITORY TAG IMAGE ID CREATED SIZE  
ch02/echo latest 7b569d5d6c4f 3 minutes ago 845MB  
mongo 6 bb8c079588cc 6 weeks ago 749MB  
redis 7 2379f7f02dd7 7 weeks ago 117MB  
confluentinc/cp-kafka 7.2.15 84a31887ee3b 2 months ago 770MB  
confluentinc/cp-zookeeper 7.2.15 8d40b332b4f9 2 months ago 770MB  
nginx stable-alpine 936a1208f403 2 months ago 48.2MB  
mysql 8 8fbbf951246a 3 months ago 777MB  
ghcr.io/jpubdocker/echo v0.1.0 a066b46d7e63 9 months ago 815MB  
ubuntu 23.10 77081d4f1e72 13 months ago 71.1MB

2.2.2 컨테이너 실행하기

  <컨테이너 실행하기>

  docker container run -it ch02/echo:latest

  REPOSITORY                  TAG             IMAGE ID       CREATED          SIZE
ch02/echo                   latest          7b569d5d6c4f   11 minutes ago   845MB <요거 실행>
  • docker container run -it ch02/echo:latest
    • it 다음 이미지이름과 테그를 갖는 커테이너 이미지를 컨테이너 실행
  • docker container run -d ch02/echo:latest
    • -d : 백그라운드로 실행 (보통 서버 어플리케이션)

2.3 이미지 다루기

  • 컨테이너 이미지 빌드 :
    • DockerFile <- 이미지를 생성하기 위한 순서를 기술한 파일 (템플릿)
    • 템플릿에서 이미지를 생성하는 것을 컨테이너 이미지빌드
  • docker image build -t [이미지명][:테그명] dockerfile 경로
    • 뭐.. 이앷 했다.
  • 기타 다른 옵셩
    • -f
      • 일반적으로 dockerfile 경로에서 dockerfile 을 찾는다.
      • docker image build -f dockerfile-test -t ch02/echo
        • dockerfile 대신 dockerfile-test 파일을 찾아서 빌드한다.
    • pull
      • dockerfile 에서 FROM 에 지정된 이미지를 베이스로 새로운 이미지를 만든다
        • 한번 다운 받으면 그냥 재사용하는데 -> 이걸 강제로 다시 가져오게 할 수 있다.
      • docker image build --pull=ture -t ch-2/echo

2.3.2 docker search

  • docker search [options] 키워드
    • [options]
      • --limit 5 : 5개만 보기 / star 내림차순이 디폴트

2.3.3 docker image pull

  • docker image pull [options] 리포지토리명[:테그명]

2.3.4 docker image tag

  • 시나리오 *
    • latest 로 이미지를 만들었다 ->
    • 시간이 흘러 V2를 lastest로 만들었다 ->
    • 기존의 latest는...?
    • 리포지토리가 NONE 으로 처리가 된다.
      • 따라서,
        • docker image tag [기존이미지명][:태그] 새이미지명[:태그]
          • 이런식으로버전관리를 하고 업데이트를 하던지,
        • 처음부터 그냥 버전명으로 쓰자....;;;;
728x90