Replicate worker¶
/bin/replicate runs Rclone jobs declared in REPLICATE_JOB_FILE. Each
job line is one of:
bisync— bidirectional sync (default), with a recovery procedure on failure.sync— one-way mirror (destination matches source, deletes propagate).copy— one-way additive (destination receives new files, deletes do not propagate).
The legacy name was "sync"; since 2.0.0 the worker, env vars and logs
were renamed to "replicate". /bin/bisync is a compatibility symlink
until 3.0.0; see the 1.18.x → 2.0.0 section of Upgrading.
Variables¶
| Variable | Default | Description |
|---|---|---|
REPLICATE_CRON |
(empty) | Cron schedule. Empty disables replication. |
REPLICATE_JOB_FILE |
/config/replicate_jobs.txt |
Path to the job file (semicolon-separated rows). |
REPLICATE_JOB_ARGS |
(empty) | Global rclone flags appended to every job. Shell-word split. --resync is stripped from routine runs. |
REPLICATE_VERBOSE |
ON |
When ON, also echo to stdout. |
REPLICATE_BISYNC_CHECK_ACCESS |
OFF |
When ON, append --check-access to every bisync run and the recovery resync. |
RCLONE_CONFIG |
/config/rclone.conf |
Rclone configuration file. |
Legacy aliases (SYNC_*) are accepted until 3.0.0 with deprecation
warnings.
Job file format¶
# SOURCE;DESTINATION[;MODE[;EXTRA_ARGS]]
# MODE bisync (default) | sync | copy
# EXTRA_ARGS rclone flags appended after the global REPLICATE_JOB_ARGS for THIS job only
# (--resync is stripped from both for routine runs)
# Two-column legacy form; runs as bisync with global REPLICATE_JOB_ARGS:
/data/inbox;jottacloud:inbox
# Bisync with a per-job exclude file in addition to the global one:
/data/photos;jottacloud:photos;bisync;--exclude-from /config/photos-exclude.txt
# One-way push (rclone sync) — destination is made to mirror the source:
/data/site;s3:my-bucket/site;sync
# One-way copy (rclone copy) — additive, deletes are NOT propagated:
/data/archive;jottacloud:archive;copy;--immutable
| Column | Required | Notes |
|---|---|---|
SOURCE |
yes | Local path or rclone remote path. |
DESTINATION |
yes | Local path or rclone remote path. |
MODE |
no (default bisync) |
bisync keeps both sides in sync (recovery on failure). sync makes destination match source (deletions propagate). copy is additive, no deletes. |
EXTRA_ARGS |
no | Per-job rclone flags, shell-word split, appended after REPLICATE_JOB_ARGS. --resync is filtered out so a routine run can never resync implicitly. |
What it does¶
flowchart TD
A[locked_run replicate] --> B[pre-replicate hook]
B --> C[Parse REPLICATE_JOB_FILE]
C -->|malformed line| F[Count as failed job]
C --> D{For each job}
D --> E{MODE}
E -- bisync --> E1[rclone bisync ARGS]
E -- sync --> E2[rclone sync ARGS]
E -- copy --> E3[rclone copy ARGS]
E1 -->|fail| E1R[Recovery: copy both → bisync --resync]
E2 -->|fail| FailMail
E3 -->|fail| FailMail
E1R -->|still fail| FailMail
D --> G[Aggregate exit code]
G --> H[Write last-replicate.json]
H --> I[Optional METRICS_DIR/.prom]
I --> J{Any failures?}
J -- yes --> FailMail[mail + webhook]
J -- no --> K[post-replicate hook with "$rc"]
FailMail --> K
pre-replicatehook when present.- Parse the job file. Malformed lines (missing
SOURCE/DESTINATIONor unknownMODE) are counted as failed jobs, so a typo cannot produce a silently green run. - For each job, dispatch to
rclone bisync/sync/copywithREPLICATE_JOB_ARGS+ per-jobEXTRA_ARGSappended. - Bisync recovery (only for
bisyncmode failures): copy both directions, thenbisync --resyncto re-establish baselines. See Bisync recovery hardening below. - Aggregate exit code:
0when every job succeeded (counting recoveries), otherwise the count of failed jobs. last-replicate.jsoncapturesreplicate_jobs_processedandreplicate_jobs_failedplus the common fields.- Mail / webhook: replicate mails when at least one job recorded an
unrecoverable error, regardless of
MAILX_ON_ERROR. Webhook followsWEBHOOK_ON_ERRORrules. post-replicatehook with the aggregate exit code.
Bisync recovery hardening¶
The default bisync recovery (copy both → bisync --resync) is
convenient but can be destructive if one endpoint legitimately holds
deletes that you do not want propagated back. Two safety knobs:
1. REPLICATE_BISYNC_CHECK_ACCESS=ON¶
Appends --check-access to every routine bisync run and the recovery
resync. Rclone aborts loudly when the well-known marker file
(RCLONE_TEST by default) is missing on either side — so a remote that
has been wiped no longer looks like "everything got deleted
intentionally" and no one-way deletes propagate.
Seed the marker once on both endpoints before turning the flag on:
2. One-way modes¶
sync and copy explicitly skip the destructive copy-both recovery.
If you do not need bidirectional behaviour, prefer MODE=sync /
MODE=copy so a remote glitch surfaces as a normal failed run instead
of triggering the recovery path.
Credential masking¶
Inline credentials in source/destination URLs
(https://user:pass@host/...) are masked via mask_endpoint in
container logs, last-replicate.json, mail and webhook payloads.
Configured rclone: remotes (rclone:jottacloud:inbox) never had this
problem because credentials live in rclone.conf and the URL itself
does not carry them.
Sample configurations¶
Failure modes¶
The aggregate worker exit code is the count of unrecoverable jobs.
Inspect replicate_jobs_processed / replicate_jobs_failed in
/var/log/last-replicate.json for which jobs failed.
| Per-job exit | Meaning |
|---|---|
0 |
Job succeeded (counting recovery). |
1 |
Generic rclone failure; see replicate-error-last.log. |
2 |
Bad job-line shape (missing column, unknown mode). |
7 (rclone) |
Fatal directory not found — usually a missing RCLONE_TEST marker when --check-access is on. |
8–9 (rclone) |
Bisync abort / max-deletes hit; rclone refused to make changes. |
Run on demand¶
docker exec -ti restic-backup-helper /bin/replicate
docker exec -ti restic-backup-helper cat /var/log/last-replicate.json
Same code path as the cron job. Use /bin/doctor to validate the job
file format before the first scheduled run.
See also¶
- Hooks —
pre-replicate.sh/post-replicate.sh. - Diagnostics — replicate job-file validation with masked endpoints.
- Mail notifications — replicate mail subjects.