지식
Docker
Docker 볼륨 백업과 복원: 데이터 보호 전략
Docker 볼륨에 저장된 데이터를 tar 아카이브로 백업하고 복원하는 방법, 볼륨 간 복사 패턴, 데이터베이스 볼륨 백업 시 주의사항을 설명합니다.
지난 글에서 볼륨 드라이버로 외부 스토리지를 연결하는 방법을 살펴봤다. 이번에는 볼륨 데이터 백업과 복원을 다룬다. Docker는 볼륨을 직접 복사하는 API를 제공하지 않는다. 임시 컨테이너를 통해 볼륨을 마운트한 뒤 tar로 아카이빙하는 방식이 표준 패턴이다.
백업 원리
볼륨 데이터는 호스트의 /var/lib/docker/volumes/<name>/_data에 저장된다. 이 경로를 직접 복사할 수도 있지만, Docker가 관리하는 내부 경로이므로 임시 컨테이너를 통해 접근하는 것이 더 이식성 있고 안전하다.
볼륨 백업
# 볼륨 내용을 tar.gz로 호스트에 저장
docker run --rm \
-v mydb:/data \
-v $(pwd):/backup \
alpine \
tar czf /backup/mydb-$(date +%Y%m%d).tar.gz -C /data .
명령 분해:
-v mydb:/data: 백업할 Named Volume을 컨테이너/data에 마운트-v $(pwd):/backup: 호스트 현재 디렉터리를 컨테이너/backup에 마운트 (아카이브 저장 위치)tar czf /backup/...:/data내용을/backup에 gzip 압축 아카이브로 저장--rm: 완료 후 임시 컨테이너 자동 삭제
볼륨 복원
# 백업 파일에서 볼륨으로 복원
docker run --rm \
-v mydb-restore:/data \
-v $(pwd):/backup \
alpine \
tar xzf /backup/mydb-20260515.tar.gz -C /data
- 대상 볼륨(
mydb-restore)이 없으면 자동 생성 - 기존 볼륨에 복원하면 내용이 덮어씌워짐 → 중요한 경우 새 볼륨으로 복원 후 검증
백업·복원 명령어 한눈에
볼륨 간 직접 복사
다른 이름의 볼륨으로 데이터를 이전할 때:
docker run --rm \
-v source-vol:/from \
-v dest-vol:/to \
alpine \
sh -c "cp -a /from/. /to/"
# rsync를 쓰면 증분 복사도 가능
docker run --rm \
-v source-vol:/from \
-v dest-vol:/to \
alpine sh -c "apk add --no-cache rsync && rsync -av /from/ /to/"
데이터베이스 볼륨 백업 시 주의사항
파일 시스템 레벨에서 DB 데이터 디렉터리를 복사하면 DB가 실행 중일 때는 불일치(inconsistent) 상태의 백업이 생길 수 있다.
PostgreSQL
# 권장: pg_dump로 논리 백업 (DB 실행 중에도 일관성 보장)
docker exec postgres \
pg_dump -U postgres mydb \
> backup-$(date +%Y%m%d).sql
# 전체 데이터베이스 클러스터 (pg_dumpall)
docker exec postgres \
pg_dumpall -U postgres \
> all-dbs-$(date +%Y%m%d).sql
# 복원
cat backup.sql | docker exec -i postgres psql -U postgres mydb
MySQL / MariaDB
# mysqldump로 논리 백업
docker exec mysql \
mysqldump -u root -p"$MYSQL_ROOT_PASSWORD" --all-databases \
> backup-$(date +%Y%m%d).sql
# 복원
cat backup.sql | docker exec -i mysql mysql -u root -p"$MYSQL_ROOT_PASSWORD"
파일 시스템 레벨 백업이 필요하면 DB를 중지하거나 스냅샷 기능(MySQL InnoDB hot backup 등)을 사용한다.
자동화: cron 백업 컨테이너
services:
db:
image: postgres:16
volumes:
- pgdata:/var/lib/postgresql/data
backup:
image: alpine
volumes:
- pgdata:/data:ro
- ./backups:/backup
entrypoint: >
sh -c "while true; do
tar czf /backup/pgdata-$$(date +%Y%m%d-%H%M).tar.gz -C /data .;
find /backup -mtime +7 -delete;
sleep 86400;
done"
volumes:
pgdata:
백업 컨테이너가 볼륨을 :ro(읽기 전용)로 마운트해 데이터를 변경할 위험을 차단한다.
원격으로 백업 전송
# S3로 업로드 (awscli 활용)
docker run --rm \
-v mydb:/data \
-e AWS_ACCESS_KEY_ID="$AWS_ACCESS_KEY_ID" \
-e AWS_SECRET_ACCESS_KEY="$AWS_SECRET_ACCESS_KEY" \
amazon/aws-cli \
s3 cp - s3://my-bucket/backups/mydb-$(date +%Y%m%d).tar.gz \
<<< "$(docker run --rm -v mydb:/data alpine tar czf - -C /data .)"
# 간단히: tar | ssh
docker run --rm -v mydb:/data alpine tar czf - -C /data . \
| ssh user@backup-server "cat > /backups/mydb-$(date +%Y%m%d).tar.gz"
핵심 정리
- Docker는 볼륨 복사 API 없음 → 임시 컨테이너 + tar가 표준 방식
- 백업:
-v vol:/data+tar czf /backup/out.tar.gz -C /data . - 복원:
-v vol:/data+tar xzf /backup/out.tar.gz -C /data - DB 볼륨은 파일 레벨 백업 대신
pg_dump/mysqldump논리 백업 권장 - 백업 컨테이너는 볼륨을
:ro로 마운트해 안전성 확보
지난 글: Docker 볼륨 드라이버: 외부 스토리지 연결하기
다음 글: Docker 볼륨 권한 관리: 컨테이너 내 파일 접근 제어
읽어주셔서 감사합니다. 😊