Backup data adalah aspek krusial dalam administrasi sistem yang sering diabaikan hingga terlambat. Linux menyediakan tools powerful seperti rsync dan cron untuk membuat sistem backup otomatis yang handal dan efisien. Artikel ini membahas setup backup lengkap dengan berbagai strategi.
Memahami Konsep Backup
Jenis-Jenis Backup
- Full Backup: Backup seluruh data (lambat, tapi comprehensive)
- Incremental Backup: Hanya backup perubahan sejak backup terakhir (cepat, efisien)
- Differential Backup: Backup perubahan sejak full backup terakhir (middle ground)
- Snapshot: Point-in-time backup (berguna untuk database)
3-2-1 Backup Rule
- 3 copies of data
- 2 different media types
- 1 offsite copy
Persiapan Environment Backup
1. Buat Struktur Direktori Backup
# Backup local structure
sudo mkdir -p /backup/{daily,weekly,monthly,logs}
sudo chown -R $USER:$USER /backup
Atau untuk user backup
mkdir -p ~/backups/{daily,weekly,monthly,logs}
2. Install Tools yang Dibutuhkan
# Rsync (biasanya sudah terinstall)
sudo apt install rsync # Debian/Ubuntu
sudo dnf install rsync # Fedora
Untuk backup encryption
sudo apt install gpg
Untuk cloud backup
sudo apt install rclone
Untuk monitoring
sudo apt install mailutils
Dasar-Dasar Rsync
Sintaks Rsync Dasar
# Basic rsync (local)
rsync -av source/ destination/
Rsync dengan verbose
rsync -avz source/ destination/
Rsync via SSH (remote)
rsync -avz -e ssh user@remote:/source/ /local/destination/
Rsync dengan delete (sinkronisasi exact)
rsync -avz --delete source/ destination/
Opsi Rsync Penting
# -a : Archive mode (preserves permissions, timestamps, symlinks)
# -v : Verbose
# -z : Compress during transfer
# --delete : Delete files in destination not in source
# --exclude : Exclude patterns
# --include : Include patterns
# --progress : Show progress
# -n : Dry run (test only)
# --link-dest : Hard links untuk incremental backup
Contoh lengkap
rsync -avz --delete --exclude='*.tmp' --exclude='cache/' \
--progress /home/user/data/ /backup/data/
Exclude Pattern
# Buat file exclude list
cat > /backup/exclude-list.txt <<EOF
*.tmp
*.log
cache/
node_modules/
.git/
.env
*.bak
EOF
Gunakan exclude file
rsync -avz --exclude-from=/backup/exclude-list.txt \
/home/user/project/ /backup/project/
Script Backup Incremental dengan Rsync
1. Daily Backup Script
#!/bin/bash # /usr/local/bin/backup-daily.shKonfigurasi
SOURCE="/home/user/" DESTINATION="/backup/daily/" LOGFILE="/backup/logs/backup-daily-$(date +%Y%m%d).log" DATE=$(date +%Y%m%d)
Pastikan direktori ada
mkdir -p "$DESTINATION" mkdir -p "/backup/logs"
File exclude
EXCLUDE_LIST="/backup/exclude-list.txt"
Backup dengan timestamp
rsync -avz --delete \ --exclude-from="$EXCLUDE_LIST" \ --backup --backup-dir="$DESTINATION../old/$DATE" \ "$SOURCE" "$DESTINATION" >> "$LOGFILE" 2>&1
Log hasil
if [ $? -eq 0 ]; then echo "[$(date)] Backup daily berhasil: $DATE" >> "$LOGFILE"
Send notification (optional)
# mail -s "Backup Daily Success" [email protected] < "$LOGFILE"else
echo "[$(date)] Backup daily GAGAL: $DATE" >> "$LOGFILE"mail -s "Backup Daily FAILED" [email protected] < "$LOGFILE"
fi
Cleanup old logs (keep 30 days)
find /backup/logs -name "backup-daily-*.log" -mtime +30 -delete
# Jadikan executable sudo chmod +x /usr/local/bin/backup-daily.sh2. Weekly Full Backup Script
#!/bin/bash # /usr/local/bin/backup-weekly.shSOURCE="/home/user/" DESTINATION="/backup/weekly/" LOGFILE="/backup/logs/backup-weekly-$(date +%Y%m%d).log" DATE=$(date +%Y%m%d_%H%M%S)
Create timestamped directory
DEST="$DESTINATION$DATE" mkdir -p "$DEST"
Full backup
rsync -avz \ --exclude-from="/backup/exclude-list.txt" \ "$SOURCE" "$DEST/" >> "$LOGFILE" 2>&1
Compress backup lama (backup dari 2 minggu lalu)
OLD_BACKUP=$(find "$DESTINATION" -maxdepth 1 -type d -mtime +14 | head -1) if [ -n "$OLD_BACKUP" ]; then tar -czf "$OLD_BACKUP.tar.gz" -C "$DESTINATION" "$(basename $OLD_BACKUP)" rm -rf "$OLD_BACKUP" fi
Log
echo "[$(date)] Weekly backup selesai: $DATE" >> "$LOGFILE"
Keep only 4 weeks
find "$DESTINATION" -name "20 " -type d -mtime +28 -exec rm -rf {} \; 2>/dev/null find "$DESTINATION" -name ".tar.gz" -mtime +28 -delete
3. Monthly Archive Backup
#!/bin/bash # /usr/local/bin/backup-monthly.shSOURCE="/home/user/" ARCHIVE_DIR="/backup/monthly/" DATE=$(date +%Y%m) LOGFILE="/backup/logs/backup-monthly-$DATE.log"
mkdir -p "$ARCHIVE_DIR"
Create compressed archive
tar -czf "$ARCHIVE_DIR/backup-$DATE.tar.gz" -C / "$(echo $SOURCE | sed 's|^/||')" 2>> "$LOGFILE"
Encrypt archive (optional)
gpg --symmetric --cipher-algo AES256 "$ARCHIVE_DIR/backup-$DATE.tar.gz"
Keep 12 months
find "$ARCHIVE_DIR" -name "backup-*.tar.gz" -mtime +365 -delete
echo "[$(date)] Monthly backup selesai: $DATE" >> "$LOGFILE"
Setup Cron Job untuk Backup Otomatis
1. Edit Crontab
# Edit user crontab crontab -eAtau system-wide cron
sudo nano /etc/crontab
2. Cron Schedule untuk Backup
# Daily backup setiap jam 2 pagi 0 2 * * * /usr/local/bin/backup-daily.shWeekly backup setiap Minggu jam 3 pagi
0 3 0 /usr/local/bin/backup-weekly.sh
Monthly backup tanggal 1 jam 4 pagi
0 4 1 /usr/local/bin/backup-monthly.sh
Cleanup logs setiap minggu
0 5 0 find /backup/logs -name "*.log" -mtime +30 -delete
Format Cron
* * * * * command_to_execute β β β β β β β β β ββββ Day of week (0-7, 0=Sunday) β β β ββββββ Month (1-12) β β ββββββββ Day of month (1-31) β ββββββββββ Hour (0-23) ββββββββββββ Minute (0-59)3. Monitoring Cron Job
# Cek cron job aktif crontab -lCek system cron
ls -la /etc/cron.* cat /etc/crontab
Cek log cron
grep CRON /var/log/syslog sudo tail -f /var/log/cron
Remote Backup dengan Rsync
1. Backup ke Remote Server
#!/bin/bash # Backup ke remote server via SSHLOCAL_SOURCE="/home/user/data/" REMOTE_DEST="user@backup-server:/backups/$(hostname)/" LOGFILE="/backup/logs/remote-$(date +%Y%m%d).log"
SSH dengan key
rsync -avz --delete \ -e "ssh -i /home/user/.ssh/backup_key" \ --exclude-from="/backup/exclude-list.txt" \ "$LOCAL_SOURCE" "$REMOTE_DEST" >> "$LOGFILE" 2>&1
Log status
if [ $? -eq 0 ]; then echo "[$(date)] Remote backup SUCCESS" >> "$LOGFILE" else echo "[$(date)] Remote backup FAILED" >> "$LOGFILE" fi
2. Pull Backup dari Remote
#!/bin/bash # Pull data dari production serverREMOTE_SOURCE="user@production-server:/var/www/html/" LOCAL_DEST="/backup/production/"
rsync -avz --delete \ -e "ssh -i /home/user/.ssh/production_key" \ "$REMOTE_SOURCE" "$LOCAL_DEST"
Backup Cloud dengan Rclone
1. Setup Rclone
# Install rclone sudo -v ; curl https://rclone.org/install.sh | sudo bashKonfigurasi
rclone config
Buat remote (contoh: Google Drive)
Name: gdrive
Type: drive
Follow prompts untuk authentication
2. Backup Script dengan Rclone
#!/bin/bash # /usr/local/bin/backup-cloud.shLOCAL_DIR="/backup/monthly/" REMOTE_DIR="gdrive:Backups/$(hostname)/" LOGFILE="/backup/logs/cloud-$(date +%Y%m%d).log"
Sync ke cloud
rclone sync "$LOCAL_DIR" "$REMOTE_DIR" \ --progress \ --log-file="$LOGFILE" \ --exclude "*.tmp"
Verifikasi
if [ $? -eq 0 ]; then echo "[$(date)] Cloud backup SUCCESS" >> "$LOGFILE" else echo "[$(date)] Cloud backup FAILED" >> "$LOGFILE" fi
3. Cron untuk Cloud Backup
# Backup ke cloud setiap minggu 0 4 * * 1 /usr/local/bin/backup-cloud.shBackup Database
1. MySQL/MariaDB Backup
#!/bin/bash # /usr/local/bin/backup-mysql.shDB_USER="backup_user" DB_PASS="password" BACKUP DIR="/backup/databases/mysql/" DATE=$(date +%Y%m%d%H%M%S)
mkdir -p "$BACKUP_DIR"
Backup semua databases
databases=$(mysql -u "$DB_USER" -p"$DB_PASS" -e "SHOW DATABASES;" | grep -Ev "(Database|information_schema|performance_schema)")
for db in $databases; do mysqldump -u "$DB_USER" -p"$DB_PASS" --single-transaction "$db" | \ gzip > "$BACKUP DIR/${db}$DATE.sql.gz" done
Keep 14 days
find "$BACKUP_DIR" -name "*.sql.gz" -mtime +14 -delete
2. PostgreSQL Backup
#!/bin/bash # /usr/local/bin/backup-postgres.shPG_USER="postgres" BACKUP DIR="/backup/databases/postgres/" DATE=$(date +%Y%m%d%H%M%S)
mkdir -p "$BACKUP_DIR"
Backup dengan pg_dumpall (all databases)
sudo -u "$PG_USER" pg_dumpall | gzip > "$BACKUP_DIR/all databases$DATE.sql.gz"
Atau backup per database
databases=$(sudo -u "$PG_USER" psql -l -t | cut -d'|' -f1 | sed -e 's/ //g' -e '/^$/d')
for db in $databases; do sudo -u "$PG_USER" pg_dump "$db" | gzip > "$BACKUP DIR/${db}$DATE.sql.gz" done
Cleanup
find "$BACKUP_DIR" -name "*.sql.gz" -mtime +14 -delete
3. MongoDB Backup
#!/bin/bash # /usr/local/bin/backup-mongodb.shBACKUP DIR="/backup/databases/mongodb/" DATE=$(date +%Y%m%d%H%M%S)
mkdir -p "$BACKUP_DIR"
Backup dengan mongodump
mongodump --out "$BACKUP DIR/mongo$DATE"
Compress
tar -czf "$BACKUP DIR/mongo$DATE.tar.gz" -C "$BACKUP DIR" "mongo$DATE" rm -rf "$BACKUP DIR/mongo$DATE"
Cleanup
find "$BACKUP_DIR" -name "*.tar.gz" -mtime +14 -delete
Verifikasi dan Restore Backup
1. Verifikasi Backup Integrity
#!/bin/bash # /usr/local/bin/verify-backup.shBACKUP_DIR="/backup/monthly/" LOGFILE="/backup/logs/verify-$(date +%Y%m%d).log"
for archive in "$BACKUP_DIR"/*.tar.gz; do if [ -f "$archive" ]; then if tar -tzf "$archive" > /dev/null 2>&1; then echo "[$(date)] OK: $archive" >> "$LOGFILE" else echo "[$(date)] CORRUPT: $archive" >> "$LOGFILE" fi fi done
2. Restore dari Backup
#!/bin/bash # /usr/local/bin/restore-backup.shBACKUP_FILE="$1" RESTORE_DIR="$2"
if [ -z "$BACKUP_FILE" ] || [ -z "$RESTORE_DIR" ]; then echo "Usage: $0 <backup-file> <restore-directory>" exit 1 fi
Extract backup
if [[ "$BACKUP_FILE" == .tar.gz ]]; then tar -xzf "$BACKUP_FILE" -C "$RESTORE_DIR" elif [[ "$BACKUP_FILE" == .rsync ]]; then rsync -av "$BACKUP_FILE" "$RESTORE_DIR" else echo "Unknown backup format" exit 1 fi
echo "Restore completed to: $RESTORE_DIR"
Advanced: Backup dengan Snapshots (LVM)
Jika menggunakan LVM, Anda bisa membuat snapshots untuk backup konsisten.
#!/bin/bash # LVM Snapshot BackupVG="vg0" # Volume Group LV="data" # Logical Volume SNAP_SIZE="10G" # Snapshot size SNAP_NAME="data_snap" MOUNT_POINT="/mnt/snap" BACKUP_DEST="/backup/snapshot/"
Create snapshot
sudo lvcreate -L "$SNAP_SIZE" -s -n "$SNAP_NAME" /dev/"$VG"/ "$LV"
Mount snapshot
mkdir -p "$MOUNT_POINT" sudo mount /dev/"$VG"/ "$SNAP_NAME" "$MOUNT_POINT"
Backup dari snapshot
rsync -avz "$MOUNT_POINT"/ "$BACKUP_DEST"
Cleanup
sudo umount "$MOUNT_POINT" sudo lvremove -f /dev/"$VG"/ "$SNAP_NAME"
Monitoring dan Alerting
1. Backup Status Report
#!/bin/bash # /usr/local/bin/backup-report.shREPORT="/backup/logs/backup-report-$(date +%Y%m%d).txt"
{ echo "================================" echo "BACKUP REPORT - $(date)" echo "================================" echo "" echo "Daily Backups:" ls -lh /backup/daily/ echo "" echo "Weekly Backups:" ls -lh /backup/weekly/ echo "" echo "Monthly Backups:" ls -lh /backup/monthly/ echo "" echo "Disk Usage:" df -h /backup echo "" echo "Recent Log Entries:" tail -20 /backup/logs/backup-daily-$(date +%Y%m%d).log 2>/dev/null || echo "No daily log found" } > "$REPORT"
Email report
mail -s "Backup Report $(date +%Y-%m-%d)" [email protected] < "$REPORT"
2. Health Check Script
#!/bin/bash # /usr/local/bin/backup-health.shERRORS=0
Check backup directory exists
if [ ! -d "/backup/daily" ]; then echo "ERROR: Daily backup directory missing" ((ERRORS++)) fi
Check recent backup (should be < 25 hours ago)
if [ ! -f "/backup/logs/backup-daily-$(date +%Y%m%d).log" ]; then if [ ! -f "/backup/logs/backup-daily-$(date -d 'yesterday' +%Y%m%d).log" ]; then echo "ERROR: No recent daily backup found" ((ERRORS++)) fi fi
Check disk space (alert if > 90%)
USAGE=$(df /backup | awk 'NR==2 {print $5}' | sed 's/%//') if [ "$USAGE" -gt 90 ]; then echo "WARNING: Backup disk usage at ${USAGE}%" ((ERRORS++)) fi
Exit status
if [ $ERRORS -eq 0 ]; then echo "Backup health: OK" exit 0 else echo "Backup health: $ERRORS issues found" exit 1 fi
Keamanan Backup
1. Encrypt Backup dengan GPG
#!/bin/bash # Encrypt backupBACKUP_FILE="/backup/monthly/backup-$(date +%Y%m).tar.gz" ENCRYPTED_FILE="$BACKUP_FILE.gpg"
Encrypt dengan symmetric cipher
gpg --symmetric --cipher-algo AES256 --compress-algo 1 --s2k-digest-algo SHA512 \ --output "$ENCRYPTED_FILE" "$BACKUP_FILE"
Hapus unencrypted
rm "$BACKUP_FILE"
Decrypt (untuk restore)
gpg --decrypt "$ENCRYPTED_FILE" > backup.tar.gz
2. Secure Transfer
# Transfer dengan encryption rsync -avz --delete -e "ssh -c [email protected]" \ /backup/ user@remote:/secure-backup/Atau dengan specific SSH key
rsync -avz -e "ssh -i /root/.ssh/backup_key -o StrictHostKeyChecking=no" \ /backup/ backup@server:/backups/
Troubleshooting Backup
1. Rsync Permission Denied
# Fix permission sudo chown -R $USER:$USER /backupAtau rsync dengan sudo
sudo rsync -avz /var/www/ /backup/www/
2. Disk Full saat Backup
# Check space df -hCleanup old backups terlebih dahulu
find /backup -name "*.tar.gz" -mtime +30 -delete
Compress dengan level lebih tinggi
rsync -avz --compress-level=9 source/ dest/
3. Backup Terlalu Lama
# Exclude large files rsync -avz --exclude='*.iso' --exclude='*.mp4' --max-size='100M' \ source/ dest/Atau parallel rsync
Gunakan GNU Parallel atau split file lists
Kesimpulan
Dengan setup backup otomatis menggunakan rsync dan cron, Anda mendapatkan:
- Incremental backup yang efisien (hanya backup perubahan)
- Multiple retention policies (daily, weekly, monthly)
- Remote backup capability via SSH atau cloud
- Database backup otomatis untuk aplikasi kritis
- Monitoring dan alerting untuk memastikan backup berjalan
- Encryption untuk keamanan data sensitif
Ingat: Backup yang tidak pernah di-test restore-nya adalah backup yang tidak bisa diandalkan. Lakukan test restore secara berkala untuk memastikan backup Anda valid.
Ditulis oleh
Hendra Wijaya