본문 바로가기
🌴 DevOps/Docker & K8s

[유데미 강의 정리 1] docker 개념 및 도커 네트워킹 통신

by 카프리썬 2024. 3. 31.
728x90

 

아래 내용은 유데미 Docker & Kubernetes 실전강의를 듣고 정리한 도커 개념정리입니다. 

udemy 강의 관련 후기는 아래의 글을 참고 부탁드립니다! 

 

 

https://pearlluck.tistory.com/799 

 

유데미 도커 쿠버네티스 강의추천 [Docker & Kubernetes : 실전 가이드]

수강목적 도커와 쿠버네티스에 대한 간단한 개념은 일하면서 알게 되었지만 이것저것 뒤섞인 느낌이라 기본기를 튼튼하게 다지고 싶었다. 글또 활동 덕분에 Udemy로부터 쿠폰을 지원받아서 고민

pearlluck.tistory.com

 

목차

    Docker 시작하기 

    docker란?

    컨테이너 기술, 컨테이너를 생성하고 관리하기 위한 도구

    코드 패키지, 해당 코드를 실행하는데 필요한 모든게 포함되어 있음

     

    도커는 컨테이너와 같은 개념.
    한 컨테이너의 상품은 다른 컨테이너의 상품과 섞이지 않음.
    즉 statandalone으로 작동.
    컨테이너를 처리할수 있는 모든 선박이나 트럭에도 실을수 있다.

     

    결론적으로 도커는 컨테이너를 구축하는 도구
    - 코드가 포함된 패키지들 보관 가능
    - 동일한 환경에서 동일한 어플리케이션 실행가능.
    - 도커가 실행되는 모든 곳에서 컨테이너를 가지고 올수 있음
    - 어플리케이션을 실행 할 추가도구를 설치할 필요가 없음.

     

    도커관련 좀더 디테일한 개념은 이글을 참고해보면 좋을 것 같다!

    도커의 ㄷ도 몰랐을때 공부했던 내용인데, 지금보니 열심히 공부했네..과거의 나 칭찬해

    https://pearlluck.tistory.com/119

     

    Docker(도커) 기본개념(도커/컨테이너/VM/이미지/도커파일)

    1. 기존의 서버관리 예를 들어 웹서비스 환경을 제공한다라고 하면.. 1. 서버OS설치 (Linux/Ubuntu/CentOS) 2. 애플리케이션 설치(Web/Was/DB/App) 3. 각 애플리케이션의 Configuration 설정 4. 서비스데몬 실행 (도

    pearlluck.tistory.com

     

    docker가 왜 필요한가?

    1. 운영/개발 환경 통일
    dev에서는 잘되던게 prod에서는 환경,버전이 달라서 안될수도 있음. 

    특정 버전을 도커 컨테이너에 넣어서 항상 해당 버전으로만 실행되도록 세팅.


    2. 팀원들과 같은 개발환경 통일


    3. 여러 프로젝트에서 버전 충돌이슈 해결 
    작업중인 프로젝트에서 버전충돌로 패키지 재설치 및 전환 번거로움. 
    프로젝트별 패키지 버전을 컨테이너에 넣고, 프로젝트마다 컨테이너 생성하도록 세팅.

    가상머신과  컨테이너

    가상머신(vm)은 컴퓨터 내부의 컴퓨터

     

    host OS위에 가상의 OS를 올림
    실제 우리 머신 위에 statandalone 컴퓨터를 올려서 가상머신 오버헤드 이슈.
    매번 새로운 컴퓨터를 계속 설치해서 기존 머신의 메모리, CPU 등 리소스 낭비

     

    가상머신 문제점

    - 운영체제에 많은 영향
    - 디스크 공간 많이 차지하고, 속도도 느림
    - 공유 및 재구축 가능하지만 도커보단 까다로움
    - 앱에 필요한 것 이외에 컴퓨터 전체를 캡슐화

     

    이런 문제를 해결해주는 도커 컨테이너
    가상머신처럼 여러대의 머신을 설치하는게 아니라 도커엔진 설치하고, 도커엔진 기반으로 컨테이너를 가동

     

    도커 컨테이너 특징
    - OS와 시스템에 미치는 영향이 적음
    - 최소한의 디스크 공간차지하고, 가볍고 빠름
    - 이미지와 구성파일이 있어서 공유 및 재구축 쉬움
    - 앱에 필요한 것만 캡슐화

     

    가상머신과 컨테이너의 개념은 이글을 참고해보며 좋을 것 같다.

    클라우드의 ㅋ도 몰랐을때 공부했던 내용인데, 지금보니 열심히 공부했네..과거의 나 칭찬해

    https://pearlluck.tistory.com/133

     

    [클라우드흐름 2] VM(Virtual Machine) VS Container

    도커의 개념에서 잠깐 나오는 VM VS Container(도커) 이야기 https://pearlluck.tistory.com/119?category=854935 [Docker1] 도커 기본개념(도커/컨테이너/VM/이미지/도커파일) 기존의 서버관리 예를 들어 웹서비스 환

    pearlluck.tistory.com

    도커 이미지와 컨테이너 

    image와 container

    - 이미지는 컨테이너의 블루프린트, 코드와 애플리케이션 포함 템플릿
    - 컨테이너는 이미지를 기반으로 실행되는 소프트웨어 유닛 인스턴스
    - 하나의 동일한 이미지를 기반으로 하는 여러 컨테이너 실행 가능

    컨테이너 실행하기 

    1.도커 허브 공식 이미지 

    베이스 이미지 (ex:node) 사용
    로컬에서 이미지 찾을수 없으면, 도커허브에서 'node' 이미지를 가지고와서 로컬에 다운로드 후 이를 기반으로 하는 컨테이너 생성


    > 단순 docker run node 만 한다면?
    도커가 생성한 모든 컨테이너의 status를 보면 아무것도 실행되지 않은 상태.
    실행이 되어도 로컬 통신과 컨테이너는 격리된 채 실행된다.

     

    외부와 노출이 되지 않아서 내부 호스팅 머신으로 대화형세션(인터랙티브 모드) 필요.


    > docker run -it node
    터미널로 들어가서 컨테이너 및 컨테이너에 실행중인 노드와 상호작용 가능.
    컨테이너가 실행 된다는건 로컬에 있는 노드와 다른 버전의 노드를 도커에서 실행가능한 상황

     

    2.커스텀 이미지 생성
    dockefile 생성

    자체 이미지를 빌드할때 실행하는 도커 명령
    FROM 운영체제 레이어(시스템에 있거나 도커허브에 있는 베이스 이미지)
    COPY <컨테이너, 이미지 외부 경로> <이미지 내부 경로>
    RUN npm install
    WORKDIR /app

    - 기본적으로 파일 시스템의 root 폴더에서 도커명령 실행
    - 작업디렉토리 변경하면 여기 기준으로 도커명령 실행
    CMD 명령어 이미지가 생성될때 실행되지 않고, 이미지 기반을 컨테이너가 시작될때 실행

    EXPOSE 80
    - 컨테이너 내부(80포트)에서만 수신대기중.
    - 그래서 외부에서 접근을 할수 없는 상황.
    - 특정 로컬 시스템에 특정 포트를 노출하고 싶다는걸 알림
    - 사실 문서화,`docker run -p 외부포트:내부포트` 로 실제로 연결

     

    > dockerfile로 이미지 빌드
    `docker build .` : 도커파일이랑 동일한 경로에 있을때 이미지 빌드

    > 컨테이너 실행
    `docker run [이미지id]` : 빌드한 이미지를 기반으로 컨테이너 실행
    `docker run -p 3000:80 [이미지id]` : 외부3000포트에서 컨테이너내부80포트에 접근해서 실행

    > 컨테이너 접속
    http://localhost:3000 에 접근하면 컨테이너로 띄운 노드서버 접속 가능

     

    이미지와 컨테이너의 동작방식

    이미지와 레이어
    - 이미지 위에 작은 레이어로 컨테이너 실행
    - 이미지에 저장된 코드와 환경을 사용해서 애플리케이션 실행
    - 동일한 애플리케이션을 실행하는 여러 컨테이너가 시스템에서 매우 적은 공간 차이, 분리되어 실행

    코드에 변경사항이 생기면 다시 이미지를 빌드해야한다.
    - 컨테이너를 재시작한다고 해도 변경사항이 적용되지 않음.
    - 이미지를 만들떄 파일의 스냅샷이 생겨서 컨테이너 재실행을 해도 이전의 스냅샷 사용하기 떄문에

    레이어를 캐시한다
    - 다시 빌드할때는 캐시된 레이어 덕분에 빌드속도가 조금더 빠르다
    - dockerfile로 이미지 구축을 위한 한줄한줄 명령어는 캐시가능한 레이어

    여러 컨테이너가 동일한 이미지를 기반으로 하지만, 서로 완전히 격리된 상태
    - 같은 이미지로 여러 컨테이너를 만들수 있음
    - 하지만 그 컨테이너들은 완전히 격리되서 실행되고 공유데이터가 없다.
    - 각 컨테이너들은 독립적으로 실행된다
    - 각 컨테이너는 새 컨테이너나 새 파일로 복사하는게 아니라 이미 저장된 환경을 사용한다.그 위에 레이어를 추가할 뿐
    - 하나의 이미지와 두개의 컨테이너가 있을경우, 이미지와 컨테이너에 한번만 존재하고 코드는 이미지 활용

    도커 네트워킹 통신

    www (world wide web) 통신

    컨테니어화된 앱에 연결하고자 하는 다른 더미웹 API 연결 케이스. 


    localhost:3000 접속 -> 성공! 더미 웹 repsonse

    어떤 추가 설정 없이 월드와이드웹과 통신가능
    도커화된 애플리케이션 내부에서 웹API와 HTTP 통신이 가능하다.

    로컬 호스트머신과의 통신

    컨테이너화된 앱에 로컬에 있는 mongoDB에 연결 케이스.

    로컬에 있는 몽고디비와 연결하는 주소는?
    - mongodb://localhost:27017로 mongoDB 연결 -> 실패!
    - mongodb://host.docker.internal:27017 로 연결 -> 성공! 


    "특수 도메인주소(host.docker.internal)"로 변경해야 로컬호스트머신과 통신가능

    - localhost를 도커 내부에서 이해할 수 있는 특수 도메인으로 변경 필요.
    - 도커가 알아서 호스트머신의 ip주소로 변환되어 사용.
    - 도메인이나 url이 필요한 어느곳에서 사용할 수 있음.

    컨테이너간 통신

    컨테이너화된 앱과 데이터베이스용 컨테이너(mongoDB) 간 연결 케이스

    mongoDB 컨테이너 IP 확인 

    docker container inspect mongodb
    - NetworkSettings > IPAddress (ex:172.17.0.2)

    또 다른 컨테이너에 있는 몽고디비와 연결하는 주소는?
    - mongodb://172.17.0.2:27017 로 연결 -> 성공! 

     

    컨테이너의 "내부 IP"로 변경해야 컨테이너간 통신가능

    - 컨테이너 내부 IP를 한번더 확인해봐야함 
    - 컨테이너 IP주소가 변경될때마다 매번 새 이미지 빌드
    - 그래서 이렇게 직접 IP주소를 하드코딩하는 방식은 이상적이지 않음.

     

    이상적인 컨테이너간 통신 : 컨테이너 네트워크 생성 

    모든 컨테이너가 서로 통신할 수 있는 네트워크 생성

     

    컨테이너간 통신을 위한 내부 네트워크 생성

    - `docker network create my_network`
    - 도커에 의해 네트워크 설정 및 생성 
    - 이전에 직접 했던 내부IP를 확인하는 작업을 도커가 자동으로 수행.

    내부 네트워크 조회 
    - `docker network ls`
    - 커스텀 네트워크 뿐만 아니라 내장된 디폴트 네트워크 조회가능

    내부 네트워크를 사용하는 mongoDB 컨테이너 실행 
    - `docker run -d -name mongodb --network my_network`
    - network 옵션 추가 
    - 직접내가 컨테이너의 내부 IP를 확인하지 않아도 됌.
    - 이떄, 포트를 노출하지 않아도 된다! 
        - 어차피 같은 네트워크간에 컨테이너간 연결이
        - 컨테이너 내부에서 서로 자유롭게 통신할 수 있기 때문에. 
        - 포트노출은 로컬이나 외부에서 컨테이너에 연결할때만 필요.

    그럼, 다른 컨테이너에 있는 몽고디비와 연결하는 주소는?
    - mongodb://`mongodb`:27017 로 연결 -> 성공! 

     

    `"컨테이너 이름"으로 변경해야 컨테이너간 통신가능`
    - 하드코딩하던 컨테이너의 내부 IP주소 대신 컨테이너 이름을 쓴다  
    - 도커가 알아서 컨테이너 이름을 내부ip주소로 변환해서 사용


    내부 네트워크를 사용하는 앱 컨테이너 실행
    - `docker run --name favorites -network my_network -d --rm -p 3000:3000 favorites_app`
    - network 옵션 추가 (mongodb와 같은 내부 네크워크로 연결)

     

    Docker가 IP주소를 해결하는 방법 

    - 도커는 소스코드를 읽지 않는다.
    - 컨테이너의 이름을 보고 컨테이너 IP주소와 연결한다. 
    - 컨테이너에서 요청을 전송할때만 자동IP변환

     

     

    끝! 다음엔 유데미 강의2, 쿠버네티스 관련 글로 돌아오겠습니다!

    반응형

    $(document).ready(function() { var $toc = $("#toc"); $toc.toc({content: ".tt_article_useless_p_margin", headings: "h2,h3,h4"}); });