🐳 Docker 시리즈 살펴보기 🐳
      1. Docker와 Container
      2. Dockerfile과 Docker Image
➡️  3. Docker Volume
      4. Docker Network
      5. Docker Compose

 

🐳 Docker Volume 이란?

  • 호스트의 파일 시스템을 컨테이너에 마운트 시켜 컨테이너가 삭제되어도 데이터가 남아있게 하는 것이다.
    • 마운트란, 대상을 연결해 운영체제 또는 소프트웨어의 관리 하에 두는 일을 말한다. (ex. usb 연결)
  • Docker를 사용할 때, 데이터를 저장하는 방법에는 volume, bind mounts, tmpfs 3가지 방법이 있다. Data가 Docker Host 내에서 '어디에 존재하는지'에 따라 구분하며, docker에선 volume을 권장한다.

 

volume

  • Docker Volume은 도커 컨테이너에서 도커가 관리하는 영역에 도커 엔진이 관리하는 볼륨을 생성하는 것이다.
  • bind mount 보다 OS나 호스트에 덜 의존적이고, 도커가 완전히 관리하기 때문에 백업이나 migrate 가 편하다.
    • 볼륨을 도커 CLI 로 컨트롤 할 수 있다.
    • 여러개의 컨테이너에서 공유하기에 가장 안전하다.

 

✅ bind mount

  • volume에서 선택적인 기능을 제공하는것이 bind mount이다.
  • 호스트 머신의 특정 디렉토리나 파일이 마운트된다.
  • 호스트 머신의 절대 경로를 기입해야 한다.
  • 호스트 머신의 파일 시스템에 의존적이다.
  • Docker CLI 로 완벽히 컨트롤 할 수 없다.

 

✅ tmpfs

  • 리눅스에서 도커를 실행하는 경우에만 사용할 수 있는 기능이다.
  • 호스트의 파일 시스템이 아닌 메모리에 저장하는 방식을 사용한다.
  • 따라서 임시적으로만 사용할 수 있고, 호스트의 메모리에 한해서만 데이터의 영속성이 유지된다.
  • 컨테이너가 정지하면  tmpfs 마운트를 이용한 data는 사라진다.

 

🐳 Volume의 필요성

  • 여러 개의 Docker 컨테이너가 하나의 저장 공간을 공유해야 한다.
  • 컨테이너에 쓰여진 데이터는 기본적으로 컨테이너가 삭제될 때 함께 사라져, 데이터의 영속성이 보장되지 않는다.

  • 컨테이너는 read-only 레이어들을 순서대로 쌓은 다음(=image) 마지막에 writable 레이어를 추가하여 생성/실행된다.
  • 쓰기 가능(writable) 레이어가 있어 컨테이너 내의 파일을 생성/수정할 수 있다.
  • 하지만 쓰기 가능 레이어에서 생성한 파일들은 컨테이너 삭제시 모두 사라지게 된다.
  • 기록 가능 레이어는 컨테이너와 같은 생명 주기를 갖는다.
  • 즉, Docker에서 돌아가는 많은 애플리케이션이 컨테이너의 생명 주기와 관계없이(독립적으로) 데이터를 영속적(persistent)으로 저장해야 한다.

 

🐳 Docker Volume CLI

명령어 설명
docker volume create  볼륨을 생성한다.
이렇게 생성되는 볼륨은 도커가 관리하는 영역인
/var/lib/docker/volumes~ 하위에 생성된다
docker volume inspect 볼륨에 대한 세부 정보를 볼 수 있다.
docker volume ls 볼륨 리스트를 볼 수 있다.
docker volume prune 사용하지 않는 local 볼륨을 삭제한다.
docker volume rm 볼륨을 제거한다.

 

🐳 설명

  • 아래 소개하는 방법보다 더 간단하게는 docker compose 를 활용하는 방법도 있다. (사실 대부분 compose를 사용하지만.. 기본적인 사용법은 알아야 하므로 정리)
  • 컨테이너를 시작하거나 생성할 때, 볼륨을 지정할 수 있다.
  • 볼륨은 지정할땐 크게 '-v' 나 '-mount' 를 사용할 수 있다.
  • -v 구문은 모든 옵션을 하나의 필드로 결합하는 반면, -mount는 더 세부적으로 옵션을 줄 수 있다.
  • -v 를 통해 볼륨을 지정했을때, 다른 컨테이너 실행시 --volumes-from <CONTAINER-NAME> 으로 볼륨을 복제할 수 있다.

💡 -mount

$ docker run -d \
  --name <CONTANER-NAME> \
  --mount source=<VOLUME-NAME>,target=<CONTAINER-PATH> \
  <IMAGE>
  • <key>=<value> 쌍으로 작성한다
  • type 으로 마운트 할 타입을 설정하는데 bind, volume, tmpfs가 있다.
  • source 나 src 로 볼륨 이름을 지정한다. 익명볼륨일 경우 생략한다.
  • destination, dst, target 으로 컨테이너의 path 를 지정한다.
  • readonly, ro 로 read-only 로 할지 설정한다.
  • volume-opt 로 볼륨 선택 옵션을 지정한다.
  • 볼륨 드라이버에 어떤 옵션을 주려면 무조건 -mount 로 사용해야 한다.

💡 -v

$ docker run -d \
  --name <CONTANER-NAME> \
  -v <VOLUME-NAME>:/<CONTAINER-PATH> \
  <IMAGE>
  • 위와 같은 형식으로 볼륨을 지정한다.
  • ':' 로 구분하며
  • 첫번째는 볼륨 이름이다. 생략할 경우 익명 볼륨으로 설정된다.
  • 두번째는 컨테이너에 마운트되는 경로이다.

 

✅ -v 로 볼륨 지정할 때

형식은 아래와 같다. docker run / create .. 도커 CLI 에서 볼륨을 지정하는 경우 사용할 수 있다.

-v <HOST> : <CONTAINER>

이때 콜론( : ) 앞에 어떻게 지정하냐에 따라 경우의 수가 3가지로 나뉜다.

 

💡 생략

  • 아예 지정하지 않으면 /var/lim/docker/volumes 아래 임의로 생성된 값으로 볼륨이 생긴다.

컨테이너에 /tmp/etc/test 라는 경로는 현재 존재하지 않는다.

익명 볼륨이 생성된다. 추적하기 어려우므로 사용하지 않는것이 좋다.

 

💡 Non-path

  • 도커는 볼륨의 이름을 적었다고 추정한다
    • volume create 로 만든 볼륨이 있거나, 다른 컨테이너를 실행시킬 때 만들었던 볼륨을 설정하면 있는 볼륨으로 설정되고
    • 로컬에 없는 볼륨 이름을 적으면 볼륨이 새로 생성된다.

현재 test-volume2라는 볼륨은 없다. 하지만 이렇게 입력했을때

docker inspect로 확인 해보면,

볼륨 타입으로 마운트 되었다.

 

💡 path

  • 도커는 이것을 볼륨 타입으로 인식하지 않고, bind 타입으로 인식한다

호스트와 컨테이너에 현재 /tmp 라는 경로는 없다

이렇게 설정하여 컨테이너를 실행시키면 docker inspect 로 조회했을때

  • 주의할 점은, 컨테이너 경로를 지정했을때, 지정한 경로에 이미 데이터가 있을 경우
  • 마운트된 호스트 경로에 있는 것으로 덮어씌워진다는 것이다. 주의해서 사용해야 한다.