Automated Rsync Backup from Synology NAS to USB via Proxmox LXC
Automated Incremental Contingency System using rsync between Synology DSM and an LXC Container.
Context and Architecture
đź”™ Main Context: This guide is part of the extensive architecture detailed in the Infrastructure MOC.
Objective: Create an automated, local, and internet outage-resistant backup system that incrementally copies folders Dropbox and G-Drive from the Synology NAS (Source) to an external hard drive.
Target Hardware: 320GB External HDD. The exFAT format is used for portability, allowing the disk to be disconnected and read natively and immediately on the main system (Hackintosh).
Architecture: Synology NAS -> Local Network -> Proxmox Node -> Privileged LXC Container -> 320GB USB HDD.
Phase 1: Preparation of the Mother Source (Synology DSM)
To maintain security and the principle of least privilege, the container will not access with an administrator account, but rather with a unique and restricted user account.
- Go to Control Panel > User and Group > Create.
- Credentials: * User:
backupjd- Secure password assigned (e.g.
Generic2026Sys).
- Secure password assigned (e.g.
- Shared Folder Permissions: Assign Read-Only strictly to the folder
Drive(where data resides). - Application Permissions: Ensure that the SMB service is marked as Allowed.
Phase 2: Persistent Mounting of HDD on Proxmox (Host)
Avoid the common mistake where Proxmox changes the letter of the unit (from /dev/sdb to /dev/sde) when reconnecting the USB hot. It is necessary to anchor by its unique identity (UUID).
- Get the disk’s UUID:
blkid /dev/sde2 # Reemplazar por la particiĂłn correctaNote the alphanumeric code, e.g., 69A3-7677.
- Edit the system assembly table:
nano /etc/fstab- Add the mounting rule (At the end of the file):
UUID=69A3-7677 /mnt/backup_contingencia exfat defaults,nofail 0 0Note: The nofail flag is crucial. If the server restarts after a power outage and the USB is not connected, Proxmox will ignore the mount and continue booting without getting stuck in a kernel panic.
- Reload the daemon and mount:
systemctl daemon-reload
mount -aPhase 3: Container Creation and Configuration (LXC)
The container that acts as an intermediary must have elevated permissions to interact with network protocols at the kernel level.
-
Create the LXC:
- ID:
102(Name:rsync backup) - OS: Debian 12
- Resources: 1 Core, 1024MB RAM, DHCP Network.
- CRITICAL: In the General tab, DISABLE the option
Unprivileged containermandatorily.
- ID:
-
Enable Network Features:
- With the LXC created (but turned off), go to Options > Features.
- Enable the SMB/CIFS checkbox. Without this, AppArmor will block any attempt to use
mount.cifs.
-
Create the bridge (Bind Mount) from the Host to LXC:
Run in the main console of the Proxmox node (not inside the LXC):
pct set 102 -mp0 /mnt/backup_contingencia,mp=/mnt/usb_contingenciaPhase 4: Internal Scripting and Automation (LXC)
- Start the LXC, open its console and install dependencies:
apt update && apt install rsync cifs-utils nano -y
mkdir -p /mnt/dsm_drive- Create the Bash script:
nano /root/backup.sh- Definitive code (
backup.sh):
#!/bin/bash
LOG_GENERAL="/var/log/backup_estado.log"
echo "========================================" >> $LOG_GENERAL
echo "Iniciando contingencia: $(date)" >> $LOG_GENERAL
# Se agregaron echo_interval=60 y serverino para mantener vivo el tunel CIFS
if mount -t cifs -o username=[TU_USUARIO], password=[TU_PASSWORD], ro,vers=3.0,echo_interval=60,serverino //192.168.X.X/Drive /mnt/dsm_drive; then
echo "Conexion OK. Copiando..." >> $LOG_GENERAL
# Espejar Dropbox con tolerancia a latencia de I/O (--timeout)
rsync -rtvh --delete --timeout=600 --log-file=/var/log/backup_archivos.log /mnt/dsm_drive/Dropbox/ /mnt/usb_contingencia/Dropbox/
# Espejar G-Drive con tolerancia a latencia de I/O (--timeout)
rsync -rtvh --delete --timeout=600 --log-file=/var/log/backup_archivos.log /mnt/dsm_drive/G-Drive/ /mnt/usb_contingencia/G-Drive/
umount /mnt/dsm_drive
echo "Exito total. Red desconectada: $(date)" >> $LOG_GENERAL
else
echo "ERROR CRITICO: No se pudo conectar a DSM." >> $LOG_GENERAL
exit 1
fi- Grant execution permissions:
chmod +x /root/backup.sh- Scheduling the Cron Job (Every day at 1:00 AM):
crontab -e- Add to the end of the file:
0 1 * * * /root/backup.sh > /var/log/cron_backup.log 2>&1Troubleshooting Log and Solutions
During the development of this architecture, multiple roadblocks emerged. Below is the documentation for each error code and its resolution:
-
Error:
mount error(1): Operation not permitted-
Diagnostic: The container was created as “Unprivileged” (Without privileges). The Linux kernel prohibits mounting network file systems (SMB/CIFS) for perimeter security reasons.
-
Solution: Remove the LXC and recreate it by untitled “Unprivileged container” in the initial configuration.
-
-
Error:
mount error(13): Permission denied(With 100% correct credentials).-
Diagnosis (AppArmor): The internal security module of Proxmox was blocking the operation. It was checked by reviewing kernel logs (
dmesg | tail -n 10), which showed:apparmor="DENIED" operation="mount" fstype="cifs". -
Solution: In the LXC options > Features, check the box
SMB/CIFS. Restart the container.
-
-
Error:
mount error(13): Permission denied(Protocol rejection).-
Diagnostic: Conflict between NTLM dialects between Debian 12 (modern) and Synology DSM.
-
Solution: Inject the parameter
vers=3.0into themount.cifscommand in the script.
-
-
Error:
rsync error: some files/attrs were not transferred (code 23)-
Diagnosis: The standard flag
-a(archive) was used with rsync, which attempts to replicate the owners (chown) and permissions (chmod) of Linux. The target disk, formatted in exFAT, does not understand permissions and returns an error at the end of the transfer. -
Solution: Modify the rsync line by changing
-avhto-rtvh(recursive, preserves modification times, verbose, human-readable).
-
-
Error: Disconnecting the USB to verify data and reconnecting it throws “can’t find in /etc/fstab” when trying to mount.
-
Diagnostic: Dynamic block assignment (/dev/sdb became /dev/sde).
-
Solution: Extract the UUID with
blkidand permanently embed it in/etc/fstab(Phase 2).
-
-
Error:
rsync: [sender] write error: Broken pipe (32)andcode 23constant.- Diagnostic: Network micro-cuts due to timeouts between the LXC container and Synology DSM when processing thousands of small files (e.g., Python virtual environments). The connection closes due to inactivity.
- Solution: Modify the CIFS tunnel by adding
echo_interval=60,serverinoto themountcommand to keep ping active. In the rsync command, inject the parameter--timeout=600to tolerate latency spikes in reading.
-
Error:
rsync: [receiver] mkstemp ... failed: Invalid argument (22)- Diagnosis: Format conflict. The contingency disk uses exFAT, which prohibits the use of special characters in file names (
?,",|,<,>,*,:,\,/) due to architecture restrictions. Rsync is unable to write them and aborts the file. - Solution: Rename problematic files in the source master (Synology/Local) by removing prohibited characters.
- Diagnosis: Format conflict. The contingency disk uses exFAT, which prohibits the use of special characters in file names (
Automated translation (technical mode).