A CLI tool that performs a two-way sync between two directories, making both sides mirror each other. It is designed to be run repeatedly — as a cron job, for example — to keep two locations in sync.
How syncing works:
- Files that exist in only one directory are copied to the other.
- Files that exist in both directories are compared by content hash. If the content differs, the file with the later modification time wins and overwrites the other.
- Files with identical content are left untouched.
How deletion works:
To delete a file from both directories, create an empty marker file with a .delete extension alongside the original file. On the next sync, both the original file and the marker are removed from both directories, and the deletion is recorded in a manifest (.two-way-merge-deletions.json).
The manifest persists across syncs. If a cloud service or other process restores a deleted file, the manifest will cause it to be deleted again on the next sync run.
npm install -g @briananders/two-way-mergeRequires Node.js >=18.0.0.
twowaymerge merge <dirA> <dirB>Example:
twowaymerge merge ~/Google\ Drive/configs ~/configsCreate an empty file with a .delete extension next to the file you want removed:
touch ~/configs/obsolete-script.sh.deleteOn the next sync, obsolete-script.sh and obsolete-script.sh.delete will be deleted from both directories. A deletion record is written to .two-way-merge-deletions.json in each directory, so the file will not reappear even if an external process (such as a cloud sync) restores it.
The .delete marker can be placed in either directory — it will be picked up from both sides.
The file .two-way-merge-deletions.json is maintained automatically at the root of each synced directory. You do not need to edit it manually. It is excluded from the regular sync process and is instead merged (union) across both directories on every run.
Use absolute paths to both the binary and the directories — the PATH environment variable is not available in cron.
# Example crontab entry (runs every 5 minutes)
*/5 * * * * /Users/yourname/.nvm/versions/node/v22.0.0/bin/node \
/usr/local/lib/node_modules/@briananders/two-way-merge/index.js \
merge \
"/Users/yourname/Google Drive/configs" \
"/Users/yourname/configs"git clone https://github.com/briananders/two-way-merge.git
cd two-way-merge
npm install
npm testnode index.js merge <dirA> <dirB>