بکاپ خودکار و رمزنگاری‌شده سرور با Restic

بکاپ خودکار و رمزنگاری‌شده سرور با Restic

جدول محتوا 👇

بکاپی که روی همان سرور نگهداری شود، با خرابی دیسک، باج‌افزار یا حذف اشتباهی سرور همراه با سرور از بین می‌رود. Restic یک ابزار متن‌باز و تک‌فایلی بکاپ است که داده را پیش از ارسال رمزنگاری می‌کند، فقط تغییرات را می‌فرستد (Deduplication) و با مخازن SFTP، S3 و چندین سرویس دیگر کار می‌کند. در این آموزش بکاپ سرور با restic را روی Ubuntu راه‌اندازی می‌کنیم: ساخت مخزن، بکاپ فایل و دیتابیس، زمان‌بندی خودکار با systemd، سیاست نگهداری نسخه‌ها و مهم‌تر از همه، تست بازیابی.

چرا Restic؟

  • رمزنگاری سمت مبدأ: داده با AES-۲۵۶ روی سرور شما رمزنگاری می‌شود؛ مقصد بکاپ محتوای فایل‌ها را نمی‌بیند.
  • Deduplication و فشرده‌سازی: بعد از اولین بکاپ، فقط تکه‌های تغییرکرده ارسال می‌شود؛ بکاپ روزانه سریع و کم‌حجم است.
  • Snapshotهای مستقل: هر بکاپ یک Snapshot کامل است که می‌توان آن را مستقل بازیابی کرد.
  • مقصدهای متنوع: پوشه محلی، SFTP، S3 و سازگارهای آن، REST Server و از طریق rclone ده‌ها سرویس دیگر.
  • تک‌فایل و بدون وابستگی: نصب و انتقال آسان.

اگر هنوز تفاوت Snapshot ماشین مجازی و بکاپ برایتان روشن نیست، چرا Snapshot بکاپ نیست را بخوانید.

چه چیزی را کجا بکاپ بگیریم؟

قبل از دستورات، فهرست کنید چه چیزی برای بازگرداندن سرویس لازم است:

  • فایل‌های سایت و برنامه (/var/www، /srv، /opt/app)
  • Dump دیتابیس (فایل‌های خام دیتابیس در حال اجرا بکاپ قابل‌اعتماد نیستند)
  • تنظیمات (/etc، فایل‌های docker-compose.yml و .env)
  • Volumeهای Docker با داده پایدار

مقصد بکاپ باید خارج از سرور اصلی و ترجیحاً در دیتاسنتر یا ارائه‌دهنده دیگری باشد. قانون رایج ۳-۲-۱ یعنی سه نسخه از داده، روی دو نوع رسانه، و یک نسخه خارج از محل. برنامه کامل‌تر در طرح بازیابی از فاجعه.

نصب Restic

sudo apt update
sudo apt install -y restic
restic version
sudo restic self-update   # به‌روزرسانی به آخرین نسخه رسمی

نسخه مخازن توزیع ممکن است قدیمی باشد؛ self-update فایل اجرایی رسمی را از GitHub دریافت می‌کند. اگر دسترسی به GitHub ندارید، نسخه مخزن هم برای این آموزش کافی است.

ساخت مخزن روی SFTP یا S3

ابتدا رمز مخزن را بسازید و در فایلی با دسترسی محدود نگه دارید:

sudo mkdir -p /etc/restic
openssl rand -base64 32 | sudo tee /etc/restic/password >/dev/null
sudo chmod 600 /etc/restic/password

این رمز را جای دیگری هم (مثلاً Password Manager) ذخیره کنید. بدون آن، بازیابی بکاپ غیرممکن است؛ حتی برای سازنده Restic.

گزینه ۱: سرور دوم با SFTP

یک کاربر مخصوص بکاپ روی سرور مقصد بسازید و کلید SSH سرور اصلی را به آن اضافه کنید. سپس فایل /etc/restic/env:

RESTIC_REPOSITORY=sftp:backup@10.0.0.20:/srv/restic/web01
RESTIC_PASSWORD_FILE=/etc/restic/password

اگر سرور بکاپ در همان دیتاسنتر است، اتصال از طریق شبکه خصوصی سریع‌تر و بدون مصرف ترافیک عمومی است؛ اما برای محافظت در برابر فاجعه دیتاسنتر، یک نسخه هم در مکان دیگر داشته باشید.

گزینه ۲: فضای ذخیره‌سازی سازگار با S3

RESTIC_REPOSITORY=s3:https://s3.example.com/my-bucket/web01
AWS_ACCESS_KEY_ID=...
AWS_SECRET_ACCESS_KEY=...
RESTIC_PASSWORD_FILE=/etc/restic/password

سپس مخزن را مقداردهی کنید:

sudo chmod 600 /etc/restic/env
sudo bash -c 'set -a; . /etc/restic/env; restic init'

اولین بکاپ

فایل فهرست استثناها /etc/restic/excludes بسازید تا کش‌ها و فایل‌های موقت بکاپ نشوند:

/var/www/*/wp-content/cache
/var/www/*/node_modules
*.log
/var/lib/docker/overlay2
sudo bash -c 'set -a; . /etc/restic/env; restic backup /var/www /etc /srv \
  --exclude-file /etc/restic/excludes --tag daily'
sudo bash -c 'set -a; . /etc/restic/env; restic snapshots'

اولین بکاپ کامل است و زمان بیشتری می‌گیرد؛ بکاپ‌های بعدی فقط تغییرات را می‌فرستند.

بکاپ دیتابیس

Restic می‌تواند خروجی یک دستور را مستقیم از stdin بکاپ کند؛ بدون اینکه فایل Dump روی دیسک بماند:

sudo bash -c 'set -a; . /etc/restic/env; \
  mysqldump --single-transaction --routines --all-databases \
  | restic backup --stdin --stdin-filename all-databases.sql --tag db'

برای PostgreSQL از pg_dumpall با کاربر postgres استفاده کنید. گزینه --single-transaction برای جداول InnoDB یک نسخه سازگار بدون قفل کردن سایت می‌گیرد. روش‌های دیگر بکاپ دیتابیس در بکاپ و انتقال دیتابیس.

زمان‌بندی خودکار با systemd

یک اسکریپت /usr/local/sbin/restic-backup.sh بسازید:

#!/bin/bash
set -euo pipefail
set -a; . /etc/restic/env; set +a

mysqldump --single-transaction --routines --all-databases \
  | restic backup --stdin --stdin-filename all-databases.sql --tag db
restic backup /var/www /etc /srv --exclude-file /etc/restic/excludes --tag daily
restic forget --keep-daily 7 --keep-weekly 4 --keep-monthly 6 --prune
restic check --read-data-subset=1%
sudo chmod 700 /usr/local/sbin/restic-backup.sh

فایل سرویس /etc/systemd/system/restic-backup.service:

[Unit]
Description=Restic backup
After=network-online.target

[Service]
Type=oneshot
ExecStart=/usr/local/sbin/restic-backup.sh
Nice=10
IOSchedulingClass=idle

و تایمر /etc/systemd/system/restic-backup.timer:

[Unit]
Description=Daily restic backup

[Timer]
OnCalendar=*-*-* 03:30
RandomizedDelaySec=30m
Persistent=true

[Install]
WantedBy=timers.target
sudo systemctl daemon-reload
sudo systemctl enable --now restic-backup.timer
sudo systemctl start restic-backup.service   # اجرای آزمایشی
journalctl -u restic-backup.service -n 50

چرا systemd به‌جای cron؟ لاگ در journal ثبت می‌شود، Persistent=true اجرای جاافتاده را پس از روشن شدن سرور انجام می‌دهد و اولویت IO پایین بار سرور را کم می‌کند. مقایسه در Cron و systemd timers. برای اطلاع از شکست بکاپ، اجرای موفق را با یک Push Monitor در Uptime Kuma یا Zabbix پایش کنید.

سیاست نگهداری و پاک‌سازی

دستور forget مشخص می‌کند کدام Snapshotها بمانند و --prune داده‌های بلااستفاده را واقعاً حذف می‌کند. سیاست بالا یعنی ۷ بکاپ روزانه، ۴ هفتگی و ۶ ماهانه؛ یعنی می‌توانید تا ۶ ماه عقب برگردید. restic check سلامت مخزن را بررسی می‌کند و --read-data-subset هر بار بخشی از داده را واقعاً می‌خواند تا خرابی دیسک مقصد زود کشف شود. اجرای prune زمان‌بر است؛ در سرورهای بزرگ آن را هفتگی جداگانه اجرا کنید.

بازیابی و تست

بکاپی که بازیابی آن آزمایش نشده، بکاپ مطمئنی نیست. ماهی یک بار بازیابی را تمرین کنید:

# فهرست Snapshotها
sudo bash -c 'set -a; . /etc/restic/env; restic snapshots'

# بازیابی یک پوشه در مسیر موقت
sudo bash -c 'set -a; . /etc/restic/env; restic restore latest \
  --target /tmp/restore-test --include /var/www/example.ir'

# بازیابی دیتابیس
sudo bash -c 'set -a; . /etc/restic/env; restic dump --tag db latest /all-databases.sql' > /tmp/all.sql

# مرور Snapshot مثل یک پوشه
sudo mkdir -p /mnt/restic
sudo bash -c 'set -a; . /etc/restic/env; restic mount /mnt/restic'   # تا Ctrl+C فعال می‌ماند

هیچ‌وقت مستقیم روی مسیر اصلی بازیابی نکنید مگر در زمان بحران؛ ابتدا در مسیر موقت بازیابی و بررسی کنید. زمان کامل بازیابی را هم اندازه بگیرید؛ این عدد RTO واقعی شماست.

محافظت در برابر باج‌افزار

اگر مهاجم به سرور اصلی دسترسی root بگیرد، به اطلاعات مخزن بکاپ هم دسترسی دارد و می‌تواند Snapshotها را حذف کند. راه‌های محافظت:

  • rest-server با حالت append-only: سرور اصلی فقط می‌تواند بکاپ اضافه کند و حذف (forget/prune) فقط از یک سیستم مدیریتی جدا انجام می‌شود.
  • Object Lock در S3: اگر ارائه‌دهنده پشتیبانی کند، Snapshotها تا مدت مشخص قابل حذف نیستند.
  • کلید با حداقل دسترسی: کلید SFTP یا S3 فقط به همان مسیر بکاپ دسترسی داشته باشد.

سوالات متداول

Restic بهتر است یا BorgBackup؟

هر دو عالی‌اند. Borg در فشرده‌سازی و سرعت روی SSH بسیار خوب است اما سمت مقصد هم باید Borg نصب باشد. Restic مستقیم با S3 و سرویس‌های ابری کار می‌کند و انعطاف بیشتری در مقصد دارد.

بکاپ چقدر فضا می‌گیرد؟

اولین بکاپ نزدیک به حجم داده (پس از فشرده‌سازی) است. بکاپ‌های بعدی فقط تغییرات را اضافه می‌کنند؛ برای یک سایت معمولی با تغییرات روزانه کم، ۶ ماه نسخه معمولاً کمتر از دو برابر حجم اصلی فضا می‌گیرد.

اگر رمز مخزن را گم کنم؟

داده قابل بازیابی نیست. رمز را حتماً در دو جای امن و جدا از سرور نگه دارید.

Snapshot ماشین مجازی کافی نیست؟

Snapshot روی همان زیرساخت ذخیره می‌شود و جایگزین بکاپ خارج از سرور نیست؛ اما برای برگشت سریع قبل از به‌روزرسانی مفید است. توضیح در Snapshot یا بکاپ.

سرور دوم برای نگهداری بکاپ

یک سرور مجازی تراست هاست با دیسک کافی را به‌عنوان مقصد بکاپ در کنار سرور اصلی قرار دهید. اگر طراحی و پیاده‌سازی بکاپ و بازیابی را به متخصص می‌سپارید، پشتیبانی سرور را ببینید.

سرور مجازی ابری تراست هاست

مشاوره تراست‌هاست​

با متخصصان و کارشناسان به صورت رایگان!

دیدگاهتان را بنویسید

نشانی ایمیل شما منتشر نخواهد شد. بخش‌های موردنیاز علامت‌گذاری شده‌اند *