An rsync backup job that normally finishes in 10 minutes has been running for 3 hours and the destination disk is filling up faster than expected — what are the most likely causes and how do you diagnose which one it is without killing the job blind?
Quick Answer
The most common causes are a broken or newly-added symlink loop, a source directory that grew unexpectedly with new large files or a runaway log, a change in file timestamps or permissions across the whole tree forcing rsync to re-transfer nearly everything instead of matching existing blocks, or a slow or degraded network path. Diagnose live by checking progress output for the current file and transfer rate, comparing source vs. destination directory sizes, and checking for recent bulk chmod/touch/chown operations on the source tree before assuming the transfer itself is broken.
Detailed Answer
This is like a mail-forwarding service that's supposed to only forward new letters, but suddenly every previous letter you ever received starts getting re-forwarded too — either someone re-addressed the entire filing cabinet by changing all the metadata, someone dumped a huge new stack of mail into the cabinet, which is real data growth, or the delivery truck itself is just moving slower than usual due to network degradation even though the amount of mail is normal.
rsync decides whether to skip a file entirely by default using a "quick check" of file size and modification time — if those match between source and destination, it assumes the file is identical and skips it without even reading the contents. This default exists because reading and checksumming every file's contents on every run would be extremely slow for routine incremental backups, so rsync optimizes for the common case where files that haven't been touched also haven't changed. But this same optimization is exactly why a bulk metadata change, such as an anti-virus scan that touches file access times, a permissions-fixing script, or a filesystem migration that resets modification times, can silently defeat the quick check and force rsync to re-transfer the entire tree even though the actual file content is unchanged.
To diagnose live without killing the job, first check what rsync is currently transferring using progress output or by inspecting the process's open file descriptors, and compare the current transfer rate against the historical baseline — a rate that's roughly normal but running for way longer points to volume growth, while a rate that's crawling points to network or disk I/O contention. Next, independently compare source and destination directory sizes to check whether the source genuinely grew, which rules in or out the new-or-large-files theory. Finally, spot-check a handful of files that should have been skipped, old, untouched files, to see if their modification time actually changed recently on the source side, which would confirm the quick check was defeated by a metadata-wide change rather than real data growth.
In production, mature backup pipelines log per-run summary stats, files transferred, bytes transferred, duration, so that three hours instead of ten minutes is immediately visible as an anomaly against history rather than something a human notices only when the disk fills up. Teams should also alert on destination disk usage independently from job duration, since a job that's still running normally but transferring far more data than usual can fill a disk well before the job itself would be flagged as abnormally slow. Using --stats on every run and shipping that output to a metrics system turns rsync into an observable pipeline component instead of a black box.
The non-obvious gotcha is that killing a long-running rsync job mid-transfer is often safe for the destination, since rsync uses temporary files and atomic renames by default, so a killed job leaves the destination in its last-known-good state rather than corrupted, but only if you haven't used --inplace, which writes directly to the destination file instead of a temp file for performance reasons — under --inplace, killing the job mid-write can leave a partially-overwritten, corrupted destination file, which is a dangerous trade-off many engineers make for speed without realizing the safety cost.