From 045435239f92fe7e04bb820730eca7a2c4891190 Mon Sep 17 00:00:00 2001 From: seizeh Date: Mon, 31 Aug 2026 15:37:56 +0900 Subject: [PATCH] =?UTF-8?q?fix:=20=EB=B0=B1=EC=97=85=20=EB=B3=B4=EC=A1=B4?= =?UTF-8?q?=207=E2=86=9228=EC=9D=BC(4=EC=84=B8=EB=8C=80)=20+=20=EC=98=A4?= =?UTF-8?q?=ED=94=84=EC=82=AC=EC=9D=B4=ED=8A=B8=20=EC=82=AC=EB=B3=B8(BACKU?= =?UTF-8?q?P=5FOFFSITE=5FDIR)?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit 주 1회 실행 + 7일 회전 = 항상 1~2세대 → 손상 1개가 곧 무백업이었다 (08-31 실제로 1세대뿐). 28일 회전으로 4세대 확보. 백업이 원본과 다른 저장소여도 이 Mac 한 대에만 있으면 재해 복구가 아니다 — gpg 암호화본을 BACKUP_OFFSITE_DIR(iCloud Drive 등)로 복사, 같은 주기로 회전. 미설정 시 경고만 출력하고 진행(백업 자체를 막지 않는다). 삭제 데이터의 백업본 잔존 28일 트레이드오프는 pmlegal 06운영점검주기.md 에 기재. 실행 검증: 08-31 15:37 백업에서 iCloud 사본 생성 확인. Co-Authored-By: Claude Fable 5 --- scripts/backup.env.example | 5 +++++ scripts/backup.sh | 20 +++++++++++++++++++- 2 files changed, 24 insertions(+), 1 deletion(-) diff --git a/scripts/backup.env.example b/scripts/backup.env.example index aeed029..bd5743e 100644 --- a/scripts/backup.env.example +++ b/scripts/backup.env.example @@ -17,3 +17,8 @@ export BACKUP_PASSPHRASE="" # [선택] Storage(이미지) 동기화용 rclone 원격:버킷 — 대시보드 Storage → S3 Connection 로 설정 # export BACKUP_RCLONE_REMOTE="pawmate-s3:media" + +# (선택) 오프사이트 사본 디렉터리 — 미설정 시 사본 생략(경고만 출력). +# 덤프는 gpg 암호화본이므로 iCloud Drive/외장 SSD 등 어디든 가능. +# 예: BACKUP_OFFSITE_DIR="$HOME/Library/Mobile Documents/com~apple~CloudDocs/PawMateBackups" +BACKUP_OFFSITE_DIR= diff --git a/scripts/backup.sh b/scripts/backup.sh index c4bc23f..15c9f52 100755 --- a/scripts/backup.sh +++ b/scripts/backup.sh @@ -30,7 +30,11 @@ set -euo pipefail # --- 설정 --------------------------------------------------------------- SCRIPT_DIR="$(cd "$(dirname "${BASH_SOURCE[0]}")" && pwd)" BACKUP_DIR="${BACKUP_DIR:-$SCRIPT_DIR/../backups}" -RETENTION_DAYS="${RETENTION_DAYS:-7}" +# 보존 28일 = 주 1회 실행 기준 4세대. 종전 7일은 주 1회 주기와 결합하면 항상 +# 1~2세대만 남아 "손상된 백업 1개 = 무백업"이었다(2026-08-31 실제로 1세대뿐이었음). +# 삭제된 개인·위치정보가 백업본에 최대 28일 잔존하는 트레이드오프는 +# pmlegal 06운영점검주기.md 의 백업·파기 절에 함께 기재한다. +RETENTION_DAYS="${RETENTION_DAYS:-28}" STAMP="$(date +%Y%m%d_%H%M%S)" # 초까지 — 같은 분 재실행 시 덮어쓰기 방지 log() { printf '[backup %s] %s\n' "$(date +%H:%M:%S)" "$*"; } @@ -85,6 +89,20 @@ else log "Storage 백업 건너뜀 (BACKUP_RCLONE_REMOTE 미설정 — 이미지 파일은 별도 백업 필요)" fi +# --- 2.5) (선택) 오프사이트 사본 ---------------------------------------- +# 백업이 원본(운영 DB)과 별개여도 이 Mac 한 대에만 있으면 재해 복구가 아니다 — +# 노트북 분실·디스크 고장이 곧 무백업. 덤프는 gpg 암호화본이므로 iCloud Drive 등 +# 클라우드 보관 가능. BACKUP_OFFSITE_DIR 는 backup.env 에서 설정. +if [ -n "${BACKUP_OFFSITE_DIR:-}" ]; then + mkdir -p "$BACKUP_OFFSITE_DIR" + cp "$DB_FINAL" "$BACKUP_OFFSITE_DIR/" + log "오프사이트 사본 → $BACKUP_OFFSITE_DIR/$(basename "$DB_FINAL")" + # 사본 쪽도 같은 보존주기로 회전(파기 정책이 두 위치에 동일하게 적용되어야 한다) + find "$BACKUP_OFFSITE_DIR" -maxdepth 1 -name 'db_*.dump*' -type f -mtime "+$RETENTION_DAYS" -print -delete || true +else + log "⚠ 오프사이트 사본 건너뜀 (BACKUP_OFFSITE_DIR 미설정 — 백업이 이 기기 한 대에만 있음)" +fi + # --- 3) 보존주기 폐기 --------------------------------------------------- log "보존 ${RETENTION_DAYS}일 초과 백업 폐기" find "$BACKUP_DIR" -maxdepth 1 -name 'db_*.dump*' -type f -mtime "+$RETENTION_DAYS" -print -delete || true