[배포]Docker

해피데빙·2022년 3월 29일
0

TIL

목록 보기
43/45

Docker 설치
https://docs.docker.com/desktop/mac/install/

가장 쉽게 배우는 도커
https://www.youtube.com/watch?v=hWPv9LMlme8

왜 Docker인가

컨테이너 기술과 Docker의 탄생 배경

실제 컨테이너의 장점

  • 물자를 싣고 내릴 때 선박이 입항해 있는 시간을 단축시킴 [입항 시간 단축]
  • 물자를 싣고 내릴 때 필요한 인력을 대폭 감소시킨다 [인력 감소]
    즉 물자의 수송에 획기적인 단축을 가져다 준다

컴퓨터에서 사용하는 컨테이너
sw 수송 즉 배포에서 단축을 위해 사용된다
리눅스 컨테이너(Ixc)가 나타남

리눅스 컨테이너의 문제
: 애플리케이션을 쉽게 컨테이너화할 수 있는 생태계 / 커뮤니티가 없음

해결책으로 Docker + Docker Hub(sw 저장소) 탄생
Docker Hub이 있기 때문에,
1)쉽게 애플리케이션 포장
2)컨테이너 방식으로 실행 가능
=> 실행 환경에 구애받지 않고 애플리케이션을 실행할 수 있다

cf. 즉 애플리케이션 실행은 어떠한 환경에 구애를 받는다

컨테이너 방식의 장점

1.의존성 충돌 문제 해결
2.개발과 배포 환경 일치
3.수평 확장 쉽게
4.각 서버에 새로운 내용을 배포하기 쉽게 만들어준다

1. 의존성 충돌 해결

앱 중에는 실행하기 위해 특정 환경을 필요로 하는 앱들이 있다
ex. 윈도우용 프로그램 실행하려면 윈도우 운영체제 필요하듯

이렇게 어떤 프로그램A 실행에 다른 프로그램B이 반드시 필요한 경우
"프로그램 A는 프로그램 B에 의존 관계를 가지고 있다"고 한다
이때 의존성 충돌이 일어날 수 있다

의존성 충돌이란?

프로그램 c와 d가 프로그램 Z에 의존할 때 각기 다른 버전을 요구할 수 있다
하지만 일반적으로는 한 컴퓨터에 여러 버전의 동일한 앱을 설치할 수 없다
그러므로 둘 중 하나는 제대로 실행 되지 않을 때 "의존성 충돌"이 일어났다고 한다

컨테이너 기술은 앱c와 앱d를 각각 다른 컨테이너에 넣어 다른 버전으로 Z를 실행할 수 있게 한다.
즉, 컨테이너 내에서 앱을 실행하면 의존성(c의 z에 대한, d의 z에 대한)을 공유하지 않고 각자 고유의 의존성을 포함하고 있다
EX.

정리

컨테이너 기술이 있는 컴퓨터 안에 여러 대의 컨테이너 존재
이를 통해 앱 실행 환경 격리
컨테이너 하나하나가 앱 실행 관련 격리 제공하기 때문에 가능!

컨테이너의 호스트와 격리하는 것들

  1. 프로세스
  • 특정 컨테이너에서 작동하는 프로세스는 기본적으로 그 컨테이너 안에서만 엑세스 가능
  • 컨테이너 안에서 실행되는 프로세스는 다른 컨테이너의 프로세스에게 영향 X
  1. 네트워크
  • 기본으로 컨테이너 하나에 하나의 IP 주소 할당
    : 컨테이너 각각 별도의 localhost가 있다
  1. 파일 시스템
  • 컨테이너 안에서 사용되는 파일 시스템은 구획화되어 있다
  • 해당 컨테이너에서의 명령이나 파일 등의 엑세스 제한 가능
  • 각 컨테이너마다 루트가 다르다

호스트와 공유하는 것들

CPU성능, 리눅스 커널, 메모리

가상머신 vs 컨테이너

가상머신이란?
하나의 호스트(주인) 컴퓨터 위에 여러 개의 독립적인 컴퓨터가 작동할 수 있게 하는 기술
ex. VMware, VirtualBox, Parallels

macOS[hostPC] 안에 window10, windowXP를 틀었다
이렇게 여러 운영체제를 열 수 있는 방법은 VMware를 써서 가능하다

공통점
비슷한 수준의 격리성을 제공한다
: 프로세스, 네트워크, 파일 시스템을 격리할 수 있다
하지만 VM은 컴퓨터 단위의 격리
Docker는 애플리케이션 단위 격리

차이점
1. 자원
VM: 만들고 실행하는 과정이 많은 컴퓨팅 자원 필요 (ex. 8gb인 컴퓨터에서는 그 이하의 vm만 사용 가능)
도커 : 한 호스트 컴퓨터에 여러개의 컨테이너를 띄워도 큰 무리 X

  1. 이미지
    도커 : 이미지는 보통 애플리케이션 단위로 만들어져 있다
    (Docker Hub Registry 통해 이미지를 살표보면 알수 있다)
    VM :해당 VM 위에 운영체제를 설치해야 한다

  1. OS

    VM : OS 존재
    컨테이너 : OS는 안에 없고 호스트로 존재
    -> 즉 각 컨테이너는 호스트 OS의 커널을 공유하고 있음
    도커는 호스트 OS를 사용하는 것이 아니라 리눅스를 사용하고 있다

ex. exec (컨테이너 안으로 들어갈 수 있다 ) ls : 파일 이름 볼 수 있다

cf. 커널이란?
시스템 콜과 같이 OS의 핵심 기능을 구현한 프로그램

도커는 애플리케이션을 컨테이너화해서 실행하는 데에 주 목적이 있다
그러므로 특별히 컨테이너에 OS를 올려서 사용하지 않는다
호스트 OS 입장에서 컨테이너 하나는 프로세스 하나에 불과

컨테이너에 OS를 올리지 않는데 Docker Hub에 존재하는 각종 OS 이미지는 뭘까?

잘 알려진 리눅스 배포판인 우분투, CentOS는 각자가 고유의 디렉토리 구조, 패키지 시스템, 쉘 등을 사용했을 뿐 결국 동일한 리눅스 커널 위에 만들어진 것
OS이미지는 컨테이너 내 애플리케이션 구성의 편의를 위해 존재하는 이미지
우분투, CentOS 이미지를 사용한다고 해도 결코 컨테이너에 커널 수준의 OS가 올라가지 않는다

리눅스가 아닌 운영체제(윈도우, macOS)에서 도커 컨테이너 안쪽은 리눅스로 작동할 수 있는 이유?

윈도우나 macOS는 근본적으로 리눅스 커널을 쓰고 있지 않으므로,
해당 운영체제의 경우 리눅스 커널을 VM 형태로 실행시키는 하이퍼바이저를 자체적으로 구동
윈도우용 또는 macOS용 도커는 하이퍼바이저 위의 리눅스 커널 사용
윈도우용 도커는 윈도우 커널을 사용한 윈도우 전용 컨테이너를 실행할 수 있는 기능 제공
컨테이너는 커널을 공유하므로 윈도우 커널을 사용하는 컨테이너는 리눅스용 도커에서 사용할 수 없다

하이퍼바이저란?
VM을 생성하고 구동하는 SW

2.개발과 배포 환경 일치

여러 개발자가 하나의 앱을 만들 때 발생하는 문제

1.버전
2.런타임 환경
3.시스템 환경변수 등 변수가 많음
4. 프로그램 설치 중 발생하는 실수
5.사전설치 항목의 부재

Ex.

도커로 해결 가능
앱 구성 자체가 컨테이너화되면 (Docker Compose 사용) YAML 파일 하나 + 명령어 하나로 모든 앱 실행 환경 구성 완료

docker-compose up   

-OS 상관 없이 즉시 앱 실행 환경 만들 수 있다
-개발을 컨테이너 위에서 진행할 경우, 모든 개발팀이 동일한 환경 하에 개발 진행 가능

배포 시의 문제
실행 및 개발 환경의 일치 이슈는 서비스 배포 환경에서도 동일하게 적용 가능
배포란 어떤 앱이 특정 런타임 환경 위에서 실행되고 사용자에게 이를 제공한다는 것
즉 실행 환경 구성과 본질적으로 다를 것이 없다
그저 서비스를 인터넷상에 공개적으로 노출하느냐 내 컴퓨터 상에서 프라이빗하게 작동하느냐의 차이!

배포의 패러다임이 달라짐
서버에 파일 하나하나 업로드하는 방식은 물자를 하나하나 배에 옮기는 이전 방식

서버는 이제 컨테이너에 담긴 앱을 실행하는 방식으로 서비스 제공
컨테이너에 담긴 앱의 형태로 EC2에 설치 or ECS(EC2 + 컨테이너) 사용

방법#1. AWS의 EC2 상에 도커를 설치
방법#2. 좀 더 편리하게 도커 컨테이너를 EC2 서버에서 실행할 수 있게 하는 서비스인 ECS를 이용

3. 수평 확장 쉽게 + 4. 각 서버에 새로운 내용 배포하기 쉽게 만들어준다


각기 다른 OS, 버전 등
Docker 안에 container를 만들고 이미지화하면 레지스트리에 올라간다
그러므로 동료 개발자나 배포 서버에서도 그대로 가져가서 사용할 수 있다

글로벌 웹 서비스는 전 세계인들이 사용하므로 트래픽이 장난 아니다
ex. google.com
그러므로 검색 서버가 한개면 안된다
트래픽 분산을 위해 프록시 서버를 사용한다
프록시 서버는 여러 대의 동일한 검색 서버 중 한 군데를 이용할 수 있도록 돕는다
-> 이런 서버를 리버스 프록시의 한 종류인 로드 밸런서라고 한다

이렇게 여러 서버에서 사용하기 때문에 실행환경 일치를 시켜주기 위해 컨테이너 사용
동일한 앱 구성을 바탕으로 새로운 서버에 해당 앱을 컨테이너로 실행하고 로드 밸런서에 이 서버를 추가
aws는 서버를 만들고 삭제하는 일을 자동으로 해준다

여러 서버 중 몇대만 운영해서 테스트 가능
쿠버네티스 같이 오케스트레이션 도구라고 부르는 것들

Docker 핵심 키워드

  1. 컨테이너
    앱이 의존성, 네트워크 환경, 파일 시스템에 구애받지 않고 도커라는 기술 위에 실행할 수 있도록 만든 앱 상자

이미지를 바탕으로 컨테이너가 생성된다 (이미지가 앱, 컨테이너가 앱 상자)

클래스라는 템플릿으로 인스턴스를 만들고
AMI라는 템플릿으로 EC2 인스턴스를 만들고
이미지라는 애플리케이션 템플릿으로 격리된 환경 안에서 앱을 실행시키는 컨테이너를 만든다

그러므로 이미지 : 컨테이너 = 1 : 다

  1. 이미지
    앱 및 앱 구성을 함께 담아놓은 탬플릿
    이를 통해 즉시 컨테이너 생성 가능 (모든 컨테이너는 이미지로부터 생성)

이미지 이용해 여러 개의 컨테이너 생성 가능
-> 이를 통해 앱 수평 확장 가능

이미지는 기본 이미지로부터 변경 사항을 추가/커밋해서 또 다른 이미지를 만들 수 있다
ex. node.js로 작성된 앱을 이미지로 만들고 싶은 경우 node.js 이미지를 기본 이미지로 삼고
원하는 앱 추가하고 이미지화할 수 있다

Self Guided Lessons의 Node.js 웹 앱의 도커라이징 레퍼런스를 참고해 보세요.

  1. 레지스트리
    이미지는 레지스트리에 저장
    ex. Docker Hub, Amazon ECR
    도커 CLI에서 이미지를 이용해 컨테이너를 생성할 대 호스트 컴퓨터에 이미지 존재 X 시
    기본 레지스트리로부터 다운로드
    ex. aquarium을 직접 다운받지 않아도 실행할 수 있는 이유는 레지스트리에 해당 이미지가 있기 때문에 받아올 수 있다

컨테이너는 프로세스, 네트워크, 파일 시스템을 개별적으로 소유할 수 있다
CPU, 커널 등은 소유할 수 없다

Docker CLI

Docker Image 및 Container 다루기 위한 CLI

실습 과정에서 permission denied 메시지가 포함된 오류를 만난다면,
sudo 를 명령어 앞에 붙여서 관리자 권한을 부여합니다.

Docker docs
https://docs.docker.com/engine/reference/commandline/container_run/
명령어, 옵션 등 사용법
사용법 : Docker CLI, Docker-Compose CLI, API Reference
환경 및 빌드 파일 구성 : DockerFile, Docker-Compose File

제공된 이미지 읽는 방법

  • 레지스트리(Registry)

Docker Hub : https://hub.docker.com/
도커 이미지를 관리하는 공간
default : 도커 허브(Docker Hub)를 기본 레지스트리로 설정
종류 : Docker Hub, Private Docker Hub, 회사 내부용 레지스트리 등

-레포지토리(Repository)

레지스트리 내에 도커 이미지가 저장되는 공간
이미지 이름이 사용되기도 함
GitHub의 레포지토리와 유사

  • 태그(Tag)

같은 이미지라고 할지라도 버전 별로 다름
해당 이미지를 설명하는 버전 정보
특별히 다른 것을 지정하지 않는다면 latest 태그를 붙인 이미지를 가져옴

EX. docker/whalesay:latest

Docker Hub라는 레지스트리에서
docker라는 유저가 등록한 whalesay 이미지 혹은 레포지토리에서
latest 태그를 가진 이미지

이미지 사용 방법

Docker Hub
: Docker Image를 찾을 때
: Docker Image의 사용방법을 확인할 때 사용 가능

도커 이미지 만드는 방법(1) 로컬 파일과 도커 이미지 연결

  1. 이미지를 컨테이너로 실행하고 변경사항을 다시 이미지로 만든다

  2. Dockerfile을 이용해서 실행환경을 구성한다
    ???다시 보기


이미지로 build해서 commit

그 다음에 사용할 때는 이미지를 컨테이너로 실행

도커 이미지에 로컬 파일 추가하는 경우

웹 서버는 도커 컨테이너로 실행
웹 서버를 구성하는 파일은 직접 만들거나 가져온 파일 구성

장점

  • 서버에 문제가 생기는 것을 호스트와 별개로 파악할 수 있음
  • 문제가 생긴 서버를 끄고, 마치 공장 초기화를 하듯 도커 이미지로 서버를 재구동할 수 있음

연결하는 방법 두가지
1. CP 이용 방법 : 호스트와 컨테이너 사이에 파일 복사
2. Docker Volume 이용 방법 : 호스트와 컨테이너 사이에 공간을 마운트

마운트란?
저장 공간을 다른 장치에서 접근할 수 있도록 경로를 허용해서 하나의 저장공간을 이용하는 것처럼 보이게 하는 작업

사용할 도커 이미지: httpd
Apache HTTP Server를 실행할 수 있는 오픈소스 웹 서버 소프트웨어

Sprint

Docker 컨테이너에 로컬 파일 복사하기

sebcontents/part1 이미지 이용

  1. docker hub에서 이미지를 가져온다
  2. git clone으로 로컬에 파일을 가져온다
  3. container를 실행한다
  4. cp로 로컬 파일을 container안에 넣는다
  5. 해당 포트로 가서 확인한다
  1. docker hub에서 이미지를 가져온다
    docker image pull docker/whalesay:latest
  2. git clone으로 로컬에 파일을 가져온다
  3. container를 실행한다
  4. cp로 로컬 파일을 container안에 넣는다
  5. 해당 포트로 가서 확인한다

sebcontents/part1은 아파치 웹 서버 이미지(httpd)를 기반으로 commit된 새로운 이미지 입니다.

SpaceInvaders % docker container cp ./ 컨테이너 이름:/usr/local/apache2/htdocs/

cp할 파일 디렉토리 안에 들어가서 docker container 안에 디렉토리를 복사한다

cp [복사할 파일][복사할 위치]
그러므로 ./ 를 만들어놓은 컨테이너 안의 apache

docker-compose


별도의 뭔가가를 깔지 않아도 할 수 있다

각각의 클라, 서버, 디비에서 사용하는 이미지를 정의를 한다

실무 속 도커

node.js 웹앱의 도커라이징

공식 문서로 보기
node:12 말고 node:16-alpine 사용

3333 로컬
8080 컨테이너


3333으로 접속하면 8080으로 연결을 한다
컨테이너 멈추려면 docker stop [dockerid]
컨테이너 지우려면 docker rm [dockerid]

s3 말고도 httpd, nginx 를 통해서도 정적 웹 사이트 호스팅을 할 수 있다
Dockerfile을 만들고

클라이언트와 서버를 같이 띄우려면 docker-compose를 쓴다

포트 바인딩

컨테이너가 두개가 있을 때
호스트의 IP와 컨테이너의 IP가 다 다름
프론트 컨테이너에서 apache app server가 80
백 컨테이너에서는 node server
내부로 직접 접속이 안되어서 바깥으로 노출이 안되면 로컬에서 얘로 접속을 할 수 없어서
어떤 특정 포트를 1:1로 매핑을 해주는 것

안 80 : 밖 8080
안 8080 : 밖 3333
밖은 로컬호스트의 포트
안은

codebuild phase(buildspec.yml)

log를 보면 이 순서대로 나타나는 것을 볼 수 있다
빌드를 완료하면 마지막에 upload artifact (s3에 담는다)
그러므로 버킷 가서 확인하면 객체가 들어있는 것을 확인할 수 있다

=> install > pre_build > build > post_build

CodeDeploy 역할 리뷰

  • 배포과정
  1. 기존 서버 중단
  2. 새 버전의 서버 번들 다운로드
  3. 실행 관련 dependency 설치

CodeDeploy

  • 배포 과정 자동화
  • 서버 실행과 관련한 런타임 제공

https://uxgjs.tistory.com/73
ending with 255 등과 같은 에러 해결하는 방법

환경변수

.env는 로컬, 소스 코드 등에 넣어서 사용
하지만 이대로 EC2에 올리면 큰일남! 환경변수 뺏어갈 수 있음 그러므로 AWS Systems Manager에서 파라미터 스토어에서 host, port, user, pw를 env 파일에 설정하듯이 설정해준다 (보안용도로 aws에서 만들어주는 것)


EC2와 aws parameter에 넣은 환경변수 연결하는 과정
위의 그림에서 .Value까지 하면 환경변수 값을 알 수 있다

IAM


개인은 root 계정을 사용한다 : 이메일로 로그인
회사 소속이면 IAM을 주고 이에 맞는 번호를 부여한다

엑세스 관리 > 사용자 > 역할그룹
역할 그룹의 내용을 보면 adminAccess 등을 통해 role에 대한 권한을 허용한다

  • 역할 안에 하나하나의 policy가 있다
  • 역할 여러 개를 합쳐서 그룹으로 쓸 수 있다
profile
노션 : https://garrulous-gander-3f2.notion.site/c488d337791c4c4cb6d93cb9fcc26f17

0개의 댓글