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:
- docker volumes
- 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_imagedocker 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:14Penjelasan:
-d: Menjalankan container dalam mode detached (latar belakang).--name postgres-container: Memberikan nama untuk container.-e POSTGRES_USER=your_user: Mengatur nama pengguna PostgreSQL (gantiyour_usersesuai kebutuhan).-e POSTGRES_PASSWORD=your_password: Mengatur kata sandi PostgreSQL (gantiyour_passwordsesuai kebutuhan).-e POSTGRES_DB=your_database: Membuat database default dengan nama yang diberikan (gantiyour_databasesesuai 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
| Aspek | Docker Volume | Bind Mount |
|---|---|---|
| Pengelolaan | Dikelola oleh Docker | Dikelola oleh pengguna |
| Fleksibilitas Path | Lokasi disimpan di direktori default Docker | Path ditentukan secara eksplisit oleh pengguna |
| Portabilitas | Lebih portabel karena Docker yang mengelola | Kurang portabel karena bergantung pada path host |
| Keamanan | Lebih aman, Docker mengontrol akses | Bergantung pada permission direktori host |
Kapan Menggunakan Docker Volume atau Bind Mount
- 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.
- 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).
- 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
- data/
hello.txt
hello world, this is persistent storage tutorialmain.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-apitesting in browser

study case (bind mount)
struktur folder dan file
- ./project_folder/
- data/
- hello.txt
- new_data/
- hello.txt
- main.py
- Dockerfile
- data/
*untuk isi dari masing2 file bisa melihat study case sebelumnya
hello.txt
Hello dari file yang berbedacommand 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/dataketerangan
docker run: perintah untuk menjalankan container dari sebuah image dalam hal inimy-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 bernamamy_volumeke direktori/app/datadi dalam container--volume $(pwd):/backup: Menghubungkan direktori kerja saat ini di host ($(pwd)) ke direktori/backupdi 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 volumemy_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/dataketerangan:
--volume my_volume:/app/data- Menghubungkan (mount) volume Docker bernama
my_volumeke direktori/app/datadi dalam container. - Data yang dipulihkan akan disimpan langsung di dalam volume ini.
- Menghubungkan (mount) volume Docker bernama
--volume $(pwd):/backup- Menghubungkan direktori kerja saat ini di host (
$(pwd)) ke direktori/backupdi dalam container. - File
backup.taryang ada di direktori kerja saat ini akan tersedia di/backupdi dalam container.
- Menghubungkan direktori kerja saat ini di host (
tar xvf /backup/backup.tar -C /app/datataradalah perintah dalam container untuk mengekstrak arsipbackup.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/datasebelum mengekstrak file, sehingga file dipulihkan langsung ke lokasi volume.
Proses Kerja:
- Volume
my_volumeyang terhubung ke direktori/app/datadi container akan menjadi lokasi target untuk data yang dipulihkan. - File
backup.tardari direktori kerja saat ini di host ($(pwd)) di-mount ke container di path/backup. - Perintah
tar xvfdalam container mengekstrak isibackup.tarke/app/data, yang berarti data akan langsung dipulihkan ke volumemy_volume.