diff --git a/scripts/backup-app.sh b/scripts/backup-app.sh new file mode 100644 index 0000000..22d5066 --- /dev/null +++ b/scripts/backup-app.sh @@ -0,0 +1,44 @@ +#!/bin/bash +# B23: ежедневный прикладной бэкап ВЕКТОРа (без planet_osm_*; OSM восстанавливается b16-import.sh). +# +# ВАЖНО: дампить ТОЛЬКО /usr/lib/postgresql/16/bin/pg_dump. pg_wrapper в контейнере +# postgres:16 указывает на клиент PG18: pg_dump 18 создаёт архив версии 1.16, +# который pg_restore 16 не читает ("unsupported version"), и пишет +# "SET transaction_timeout", отсутствующий в PG16-сервере. +# См. setup грабли: scripts/restore-app.sh. +set -u +DATE=$(date +%F) +LOG=/var/log/vector-backup.log +KEEP_DAYS=14 +PG16=/usr/lib/postgresql/16/bin + +log() { echo "[$(date '+%F %T')] $*" >> "$LOG"; } + +log "backup start $DATE" + +# 1. Дамп прикладных таблиц (маленький, ~80 КБ) +docker exec vector-postgres "$PG16/pg_dump" -U postgres -d vector_mchs \ + --exclude-table='planet_osm_*' -F c -f "/tmp/vector_app_${DATE}.dump" \ + || { log "PG_DUMP FAILED"; exit 1; } + +# 2. Выгрузка из контейнера +mkdir -p /root/backups +docker cp "vector-postgres:/tmp/vector_app_${DATE}.dump" "/root/backups/" \ + || { log "DOCKER_CP FAILED"; exit 1; } +docker exec vector-postgres rm -f "/tmp/vector_app_${DATE}.dump" + +# 3. .env и compose-конфигурация (JWT_SECRET, пароль БД, CONTOUR_TOKEN) +tar czf "/root/backups/vector_env_${DATE}.tar.gz" -C /root/vector .env docker-compose.yml 2>/dev/null +chmod 600 /root/backups/vector_env_*.tar.gz + +# 4. Проверка дампа: pg_restore 16 читает оглавление (формат/целостность) +docker cp "/root/backups/vector_app_${DATE}.dump" vector-postgres:/tmp/verify.dump +docker exec vector-postgres "$PG16/pg_restore" --list /tmp/verify.dump > /dev/null 2>&1 \ + || { log "DUMP VERIFY FAILED"; exit 1; } +docker exec vector-postgres rm -f /tmp/verify.dump + +# 5. Чистка старше KEEP_DAYS +find /root/backups -name "vector_app_*.dump" -mtime +$KEEP_DAYS -delete +find /root/backups -name "vector_env_*.tar.gz" -mtime +$KEEP_DAYS -delete + +log "backup ok: $(du -h "/root/backups/vector_app_${DATE}.dump" | cut -f1)" \ No newline at end of file diff --git a/scripts/restore-app.sh b/scripts/restore-app.sh new file mode 100644 index 0000000..d1cccf3 --- /dev/null +++ b/scripts/restore-app.sh @@ -0,0 +1,37 @@ +#!/bin/bash +# B23: восстановление прикладного дампа ВЕКТОРа в живую БД. +# +# Грабли (реальный прогон 2026-09): +# 1. pg_dump/pg_restore в контейнере postgres:16 — pg_wrapper ведёт на клиент PG18: +# pg_restore 18 создаёт архив версии 1.16, который pg_restore 16 НЕ читает +# ("unsupported version"), и пишет "SET transaction_timeout", отсутствующий +# в PG16-сервере. Лечение: ТОЛЬКО /usr/lib/postgresql/16/bin/pg_*. +# 2. --clean дропает postgis → падение на зависимостях planet_osm_*. +# EXTENSION-строки фильтруются из TOC (postgis стоит, OSM-данных в дампе нет). +# Использование: restore-app.sh /root/backups/vector_app_2026-09-25.dump +set -eu +LOG=/var/log/vector-restore.log +PG16=/usr/lib/postgresql/16/bin +log() { echo "[$(date '+%F %T')] $*" >> "$LOG"; } + +if [ $# -lt 1 ] || [ ! -f "$1" ]; then + echo "usage: restore-app.sh " >&2 + exit 1 +fi +log "restore start from $1" + +docker cp "$1" vector-postgres:/tmp/restore.dump + +# TOC без EXTENSION postgis (уже установлен; дамп OSM-таблиц не содержит) +docker exec vector-postgres "$PG16/pg_restore" --list /tmp/restore.dump | grep -v EXTENSION > /tmp/restore.toc + +if docker exec vector-postgres "$PG16/pg_restore" -U postgres -d vector_mchs \ + --clean --if-exists --no-owner --use-list=/tmp/restore.toc /tmp/restore.dump; then + log "restore ok" +else + log "RESTORE FAILED" + exit 1 +fi + +docker exec vector-postgres rm -f /tmp/restore.dump /tmp/restore.toc +log "done" \ No newline at end of file