tutorial

Docker Persistent Storage

What is persistent storage in Docker?

Penyimpanan persisten dalam konteks Docker merujuk pada cara menyimpan data sehingga ia tetap ada meski kontainer dihentikan atau dihapus. Secara default, data yang disimpan dalam kontainer akan hilang saat kontainer dihapus. Namun, dengan menggunakan volume atau penyimpanan persisten lain, data ini bisa tetap ada.

ada 2 metode persistent storages:

  1. docker volumes
  2. bind mount

Docker volumes

Docker volume adalah mekanisme bawaan Docker untuk menyimpan data dalam penyimpanan yang persisten. Volume ini dikelola oleh Docker dan terisolasi dari sistem file host dan kontainer. Anda bisa membuat volume dengan menggunakan perintah docker volume create dan kemudian memasangnya ke kontainer dengan menggunakan opsi -v atau --volume saat menjalankan perintah docker run.

command:

# Membuat volume
docker volume create <volume_name>
docker volume create my_volume

# Menjalankan kontainer dari image dengan volume
docker run -v <volume_name>:<path/in/container> <image_name> 

#versi lengkap
docker run --name <container_name> -v <volume_name>:<path/in/container> -p <port_ext>:<port_int> -d <image_name>:<tag>
docker run --name fast-api -v my_volume:/app/data -p 7000:8000 -d my-fastapi-app:v1.1

#cek list volume
docker volume ls

Bind Mount

Anda juga bisa memasang direktori dari sistem file host ke dalam kontainer. Ini memungkinkan data untuk disimpan secara persisten dan bisa diakses baik oleh host maupun kontainer.

command :

docker run -d -v </path/on/host>:</path/in/container> <image_name>
docker run -d -v "/home/learn_docker/storage_persistent":"/app/data" my_image

docker run -d \
  --name postgres \
  -e POSTGRES_USER=your_user \
  -e POSTGRES_PASSWORD=your_password \
  -e POSTGRES_DB=your_database \
  -v /home/learn_docker/postgresql/data:/var/lib/postgresql/data \
  -p 5432:5432 \
  postgres:14

Penjelasan:

  • -d: Menjalankan container dalam mode detached (latar belakang).
  • --name postgres-container: Memberikan nama untuk container.
  • -e POSTGRES_USER=your_user: Mengatur nama pengguna PostgreSQL (ganti your_user sesuai kebutuhan).
  • -e POSTGRES_PASSWORD=your_password: Mengatur kata sandi PostgreSQL (ganti your_password sesuai kebutuhan).
  • -e POSTGRES_DB=your_database: Membuat database default dengan nama yang diberikan (ganti your_database sesuai kebutuhan).
  • -v /path/to/postgresql/data:/var/lib/postgresql/data: Bind mount direktori host ke dalam container untuk penyimpanan data persisten.
  • -p 5432:5432: Memetakan port 5432 di container ke port 5432 di host.
  • postgres:14: Menggunakan image PostgreSQL versi 14.

Docker Volume vs Bind Mount

AspekDocker VolumeBind Mount
PengelolaanDikelola oleh DockerDikelola oleh pengguna
Fleksibilitas PathLokasi disimpan di direktori default DockerPath ditentukan secara eksplisit oleh pengguna
PortabilitasLebih portabel karena Docker yang mengelolaKurang portabel karena bergantung pada path host
KeamananLebih aman, Docker mengontrol aksesBergantung pada permission direktori host

Kapan Menggunakan Docker Volume atau Bind Mount

  1. Gunakan Docker Volume Jika:
    • Anda ingin penyimpanan dikelola oleh Docker.
    • Data harus tetap ada setelah container dihapus.
    • Anda memerlukan berbagi data antar-container dengan mudah.
  2. Gunakan Bind Mount Jika:
    • Anda memerlukan kontrol penuh atas path penyimpanan di host.
    • Anda ingin container mengakses direktori spesifik di host (misalnya, log file atau konfigurasi).
  3. Gunakan Persistent Storage (NFS/Cloud Storage) Jika:
    • Anda menjalankan aplikasi terdistribusi atau multi-host.
    • Anda memerlukan penyimpanan terpusat yang dapat diakses dari beberapa host.

study case (docker volume)

Siapakan folder dan file

struktur folder dan file

  • ./project_folder/
    • data/
      • hello.txt
    • main.py
    • Dockerfile

hello.txt

hello world, this is persistent storage tutorial

main.py

from fastapi import FastAPI

app = FastAPI()

@app.get("/")
def read_root():
    with open('data/hello.txt', 'r') as f: 
        return {"message": f.read()}

Dockerfile

# layer 1 : Gunakan based image
FROM python:3.10

# layer 2 : Atur direktori kerja
WORKDIR /app

# layer 3 : Pasang dependensi
RUN pip install fastapi uvicorn

# layer 4: Salin folder data ke direktori kerja /app/data
COPY data /app/data

# layer 5: Salin file main.py ke direktori kerja /app
COPY ./main.py /app/

# layer 6 : Jalankan aplikasi
CMD ["uvicorn", "main:app", "--host", "0.0.0.0", "--port", "8000"]
  • jika dilihat dari dockerfile, kita menyimpan data di app/data di container.
  • seiring pemakaian aplikasi data akan bertambah atau berkurang.
  • namun ketika container mati atau terhapus data di container jg hilang.
  • ketika kita melakukan build ulang containernya, data di app/data berisi data awal saja yg kita salin
  • oleh nya itu kita data di container kita duplikat jg datanya ke docker volume atau bind mount penyimpanan local.

command line

# 0. path project
cd path/to/project_folder

# 1. make docker image
docker build -t my-fastapi-app:v1.1 .

# 1.1 cek image
docker images 

# 2. make docker volume
docker volume create my_volume

# 2.1 cek volume
docker volume ls

# 3. make container with <docker_volume> link <container_volume>
docker run --name fast-api -v my_volume:/app/data -p 7000:8000 -d my-fastapi-app:v1.1

# 3.1 cek container
docker container ls

# 3.2 cek log
docker logs fast-api

testing in browser

study case (bind mount)

struktur folder dan file

  • ./project_folder/
    • data/
      • hello.txt
    • new_data/
      • hello.txt
    • main.py
    • Dockerfile

*untuk isi dari masing2 file bisa melihat study case sebelumnya

hello.txt

Hello dari file yang berbeda

command line

docker stop fast-api
docker rm fast-api

# 3. make container with bind mount
docker run --name fast-api -v "$(pwd)/new_data/":/app/data -p 7000:8000 -d my-fastapi-app:v1.1

#keterangan
$(pwd): Mengambil path direktori kerja saat ini (current directory)
example current directory : root@root:/home/learn_docker/storage_persistent# 

test in browser

ketika kita melakukan edit pada filenya kemudian kita refresh halamannya, maka otomatis tulisan yang ditampilkan akan berubah tanpa harus merestart container nya

Backup and restore data in Docker volumes

Untuk membuat cadangan (backup) data dari volume Docker, Anda bisa menggunakan berbagai metode, termasuk docker cp untuk menyalin data antara kontainer dan host, atau menggunakan perintah dari sistem operasi seperti tar untuk membuat arsip dari volume.

backup

#move to project directory
cd path/to/project_directory

# Membuat backup
docker run --rm --volume my_volume:/app/data --volume $(pwd):/backup my-fastapi-app:v1.1 tar cvf /backup/backup.tar /app/data

keterangan

  • docker run : perintah untuk menjalankan container dari sebuah image dalam hal ini my-fastapi-app:v1.1
  • --rm : menyebabkan container dihapus secara otomatis setelah selesai dijalankan. berguna untuk container yang digunakan sementara, seperti untuk backup atau operasi 1x
  • --volume my_volume:/app/data : menghubungkan docker volume yang bernama my_volume ke direktori /app/data di dalam container
  • --volume $(pwd):/backup : Menghubungkan direktori kerja saat ini di host ($(pwd)) ke direktori /backup di dalam container. File hasil backup akan disimpan di direktori kerja saat ini pada host.
    • jika pada path current directory ada yg menggunakan spasi maka gunakan tanda petik agar tidak error : “$(pwd)”
  • tar cvf /backup/backup.tar /app/data :
    • tar : tools untuk membuat file arsip .tar
    • cvf : Opsi untuk membuat arsip (c), menampilkan proses (v), dan menyimpan output ke file (f).
    • /backup/backup.tar: File arsip (tar file) yang akan dibuat di direktori /backup (yang terhubung ke direktori host)
    • /app/data: Direktori sumber yang akan dibackup, yaitu data yang ada di volume my_volume.

hasilnya seperti gambar di bawah, folder app/data berhasil diubah kedalam format .tar (backup.tar) dan disimpan di current directory (storage_persistent)

restore

#move to project directory
cd path/to/project_directory

# Restore dari backup
docker run --rm --volume my_volume:/app/data --volume $(pwd):/backup my-fastapi-app:v1.1 tar xvf /backup/backup.tar -C /app/data

keterangan:

  • --volume my_volume:/app/data
    • Menghubungkan (mount) volume Docker bernama my_volume ke direktori /app/data di dalam container.
    • Data yang dipulihkan akan disimpan langsung di dalam volume ini.
  • --volume $(pwd):/backup
    • Menghubungkan direktori kerja saat ini di host ($(pwd)) ke direktori /backup di dalam container.
    • File backup.tar yang ada di direktori kerja saat ini akan tersedia di /backup di dalam container.
  • tar xvf /backup/backup.tar -C /app/data
    • tar adalah perintah dalam container untuk mengekstrak arsip backup.tar:
      • x: Mengekstrak file dari arsip.
      • v: Menampilkan daftar file saat diekstrak (verbose).
      • f: Menentukan nama file arsip (/backup/backup.tar).
      • -C /app/data: Mengubah direktori kerja ke /app/data sebelum mengekstrak file, sehingga file dipulihkan langsung ke lokasi volume.

Proses Kerja:

  1. Volume my_volume yang terhubung ke direktori /app/data di container akan menjadi lokasi target untuk data yang dipulihkan.
  2. File backup.tar dari direktori kerja saat ini di host ($(pwd)) di-mount ke container di path /backup.
  3. Perintah tar xvf dalam container mengekstrak isi backup.tar ke /app/data, yang berarti data akan langsung dipulihkan ke volume my_volume.

Related Articles

Back to top button
Index