먼저 알아 둘 것: Zeabur에 기본 백업이 있지만 충분하지 않을 수 있다
Zeabur 문서에 따르면 데이터베이스 서비스의 Backup 탭에서 Backup 버튼을 누르면 몇 분 뒤 내려받을 수 있습니다. 이 기능은 유료 플랜(Dev Plan 이상) 전용이며, 백업은 7일간 보관된 뒤 자동으로 삭제됩니다.
| 데이터베이스 | Zeabur 기본 백업 형식 | 복원 도구 |
|---|---|---|
| PostgreSQL | pg_dumpall로 만든 .sql, 서비스 안의 모든 데이터베이스 포함 | psql |
| MySQL / MariaDB | .sql, 시스템 외 모든 데이터베이스 포함 | mysql |
| MongoDB | 여러 개의 .bson 파일 | mongorestore |
권장: 기본 백업을 내려받고, 아래 명령어로 직접 하나 더 받아 두세요. 이유는 PostgreSQL 부분에 있습니다. 관리형 DB로 옮길 때 기본 백업 형식은 오류가 납니다.
접속 정보는 어디에 있나
Zeabur PostgreSQL 템플릿 설명에 따르면, 데이터베이스 서비스의 Instruction 탭 안 Public (External) 영역에 외부 접속용 Connection String과 접속 명령어가 있습니다. 호스트 이름은 hkg1.clusters.zeabur.com 같은 형태이고, 포트는 Zeabur가 배정한 번호입니다.
zeabur.internal로 끝나는 호스트 이름은 Zeabur 내부 전용이라 내 컴퓨터에서는 접속할 수 없습니다.
아래 명령어는 모두 Docker로 실행하므로 로컬에 데이터베이스 도구를 설치할 필요가 없습니다.
PostgreSQL
1. 먼저 서버 버전 확인
docker run --rm postgres:17 psql "postgresql://USER:PASS@HOST:PORT/DB" -tAc "show server_version"
pg_dump 버전은 서버와 같거나 더 높아야 합니다. 버전 15의 pg_dump로 버전 16 서버를 백업하면 바로 중단됩니다.
pg_dump: error: aborting because of server version mismatch
pg_dump: detail: server version: 16.15 ...; pg_dump version: 15.19 ...
그러니 아래 이미지 버전(postgres:16)을 서버와 같거나 더 새로운 메이저 버전으로 바꾸세요.
2. 백업 (custom 형식 권장)
docker run --rm -v "$PWD:/out" postgres:16 \
pg_dump "postgresql://USER:PASS@HOST:PORT/DB" -Fc -f /out/backup.dump
3. Neon, Supabase 같은 관리형 DB로 복원
관리형 DB가 주는 계정은 superuser가 아니고, Zeabur의 테이블 소유자는 root입니다. 그대로 복원하면 다음 오류가 납니다.
pg_restore: error: could not execute query: ERROR: role "root" does not exist
--no-owner --no-acl을 붙이면 피할 수 있습니다. 테스트 결과 오류 0건, 행 수 정상, 새로 넣은 id도 원래 시퀀스에서 제대로 이어졌습니다.
docker run --rm -v "$PWD:/out" postgres:17 \
pg_restore --no-owner --no-acl -d "새 DB 접속 문자열" /out/backup.dump
Zeabur 기본 백업 data.sql로 복원하기
Zeabur 문서의 방법은 압축을 푼 뒤 다음을 실행하는 것입니다.
psql -h 호스트 -p 포트 -U 사용자 postgres < data.sql
같은 형식(pg_dumpall)으로 테스트한 결과:
- 직접 관리하는 PostgreSQL(superuser 있음)로 복원: 성공, 데이터 완전
- 관리형 DB(superuser 없음)로 복원: 실패,
ERROR: permission denied to alter role발생. 이 경우 위의pg_dump -Fc를 쓰세요
보안 주의:
data.sql앞부분에 다음 두 줄이 있습니다.
CREATE ROLE root;ALTER ROLE root WITH SUPERUSER ... PASSWORD 'SCRAM-SHA-256$...';즉, 복원하면 데이터베이스 비밀번호가 Zeabur의 옛 비밀번호로 돌아갑니다. Zeabur에서 보안 사고가 있었으니 복원 후 바로 비밀번호를 바꾸세요.
ALTER ROLE root WITH PASSWORD '새로운-긴-비밀번호';Zeabur 문서에도 현재 비밀번호를 유지하려면 복원 전에
data.sql에서CREATE ROLE과ALTER ROLE줄을 지우면 된다고 나와 있습니다.
백업 검증 (5분, 강력 권장)
로컬에 빈 데이터베이스를 띄우고 백업을 복원한 뒤 테이블과 행 수를 확인합니다.
docker network create restore-net
docker run -d --name restore-test --network restore-net -e POSTGRES_PASSWORD=x postgres:17
# 데이터베이스가 뜰 때까지 몇 초 기다리기
docker run --rm --network restore-net -v "$PWD:/out" postgres:17 \
pg_restore --no-owner --no-acl -d "postgresql://postgres:x@restore-test:5432/postgres" /out/backup.dump
docker exec restore-test psql -U postgres -tAc "select count(*) from 테이블명"
# 확인이 끝나면 정리
docker rm -f restore-test && docker network rm restore-net
왜
-p 5433:5432로 포트를 열지 않나요? 처음 테스트는 그렇게 했는데, 테스트 컴퓨터의 5433 포트에 마침 다른 로컬 PostgreSQL이 떠 있어서 백업이 그쪽에 복원되어 버렸습니다. Docker 네트워크를 쓰면 테스트 DB가 외부로 포트를 열지 않으니 엉뚱한 DB에 접속할 일이 없습니다.
MySQL / MariaDB
# 백업: --single-transaction은 테이블을 잠그지 않고, --routines --triggers는 저장 프로시저와 트리거까지 포함
docker run --rm -v "$PWD:/out" mysql:8 sh -c \
'mysqldump -h HOST -P PORT -u USER -pPASS --single-transaction --routines --triggers DB > /out/backup.sql'
# 복원
docker run --rm -v "$PWD:/out" mysql:8 sh -c 'mysql -h NEW_HOST -P NEW_PORT -u USER -pPASS DB < /out/backup.sql'
테스트 결과: 데이터, 저장 프로시저 1개, 트리거 1개가 모두 그대로 옮겨졌습니다.
MongoDB
docker run --rm -v "$PWD:/out" mongo:7 \
mongodump --uri "mongodb://USER:PASS@HOST:PORT/?authSource=admin" --archive=/out/backup.archive --gzip
docker run --rm -v "$PWD:/out" mongo:7 \
mongorestore --uri "새 접속 문자열" --archive=/out/backup.archive --gzip
테스트 출력: 50 document(s) restored successfully. 0 document(s) failed to restore.
Redis
대부분 Redis를 캐시로만 쓰는데, 그렇다면 옮길 필요가 없습니다. 새 Redis가 돌기 시작하면 캐시는 알아서 다시 쌓입니다. 큐나 랭킹처럼 정말로 Redis에 데이터를 저장한다면:
docker run --rm -v "$PWD:/out" redis:7 redis-cli -h HOST -p PORT -a PASS --rdb /out/dump.rdb
성공하면 Transfer finished with success가 표시됩니다. dump.rdb를 새 Redis의 데이터 폴더(공식 이미지는 /data)에 넣고 시작하면 자동으로 불러옵니다. 테스트에서 키 개수가 일치했습니다.
복원 후 꼭 할 일
- 새 접속 문자열(
DATABASE_URL등)로 바꾸고 데이터베이스 비밀번호를 변경하기 - 중요한 테이블 몇 개의 행 수를 대조하기
- 새 플랫폼에서 매일 자동 백업을 켜고, 실제로 한 번 내려받아 꺼낼 수 있는지 확인하기