2026-09-03

Self-Hosted Syncthing: Sync Without the Git Trap

No server, no canonical copy, no monthly bill, and a git repo sitting in the sync path will eventually bite you.

Dropbox and iCloud both do the same basic thing: your files pass through a company's server on the way from one of your machines to another, and you pay by the gigabyte for the privilege. Syncthing does the same job without the middleman. It is an open-source program that runs on each of your own devices and copies changed files directly between them, encrypted, over your own network or the internet, with nothing stored on anyone else's disk in between. No account, no subscription, no storage tier to upgrade when you cross a threshold. I run it across three machines, a Mac and two Windows boxes, to keep a set of notes folders in sync, and it has been solid for that. What it is not solid about, and what nobody warns you about clearly enough, is what happens when one of those synced folders is also a git repository.

How it actually differs from a cloud drive

The mental model that trips people up coming from Dropbox is the idea of a canonical copy. With Dropbox, there is one true version of a file sitting on Dropbox's server, and every device you own is a client that syncs to that version. Syncthing has no server and no canonical copy. Every device holding a folder is a peer, full stop. If you edit a file on your laptop and then edit the same file on your desktop before the laptop's change has propagated, there is no central arbiter deciding which one wins, because there is no centre. Both devices think their own version is current, and Syncthing has to reconcile two edits after the fact rather than one client pushing to one truth. That difference is the whole reason this article exists.

Setting up a shared folder between two devices

The setup itself is genuinely simple, which is part of why people underestimate the sharp edges further down. Each install generates a device ID, a long identifier unique to that instance. You pair two devices by exchanging IDs, either by typing one in manually or scanning a QR code Syncthing generates for you, and each side has to accept the other before anything moves. Once devices are paired, you share a specific folder from one device to the other:

  1. Install Syncthing on both machines and open the web UI (it defaults to localhost:8384).
  2. On device A, add device B using its device ID, and accept the pairing request that appears on device B.
  3. On device A, share a folder and select device B as a recipient.
  4. Accept the incoming folder offer on device B, and choose where on that machine it should live.
  5. Watch the folder state on both sides go from scanning to syncing to idle before you trust it with anything important.

The conflict file Syncthing leaves behind

This is the part that actually matters, because it is silent. If two devices both change the same file before either has synced the other's version, Syncthing does not attempt a merge. It cannot know how to merge a spreadsheet, a photo, or half your files, so it does not try for any of them. Instead it keeps both. One device's version stays under the original filename, and the other gets renamed with a conflict marker baked into the name itself, something like this:

meeting-notes.md.sync-conflict-20260812-153011-ABCDEF2.md

Nothing errors. Nothing pops up a dialog demanding you pick a winner. The folder just quietly gains an extra file, and unless you are the kind of person who periodically greps a folder for sync-conflict in the filename, you find out about it whenever you next stumble across a duplicate you don't remember creating, or never find out at all. For a folder of notes or photos that is an annoyance. For a folder that is also a git repository, it is a genuine hazard, because git will happily let a conflict file get swept into a commit without a second thought.

The part that actually matters: a git repo in the sync path

A folder that is both a git repository and a Syncthing folder has two independent systems trying to reconcile the same content by two completely different mechanisms, and they don't know about each other. Git tracks history through the .git directory. Syncthing does not understand that .git is special: it is just another folder full of files that change, so it syncs the contents of .git itself, index and objects included, between machines. If both machines commit around the same time, you can end up with Syncthing racing to sync a half-written .git/index on top of the other side's, which is a much worse problem than a stray conflict file in your notes.

I hit the tamer version of this myself: a blind git add -A on one of my synced vaults picked up three Obsidian .sync-conflict files that had landed in the working tree and committed them straight into history. Nothing catastrophic, but it meant cleaning conflict artefacts out of a commit after the fact instead of before it, and it only happened because add -A stages everything sitting in the working directory without asking whether any of it is sync debris rather than real work.

The worse version happened on a different occasion: a Syncthing regression on that same class of repo propagated a mass deletion across peers before anyone noticed, and the vault converged down to a fraction of its real size on more than one machine. The recovery principle that came out of it is worth keeping in mind generally: once you know a regression like that has happened, git and its remote become the source of truth, not whatever the working tree currently shows, because the working tree is exactly what got corrupted. Checking out from the last known-good commit undid the damage, but only because git had a full history to check out from in the first place. A synced folder with no git history behind it has no equivalent undo.

A stopped daemon looks exactly like a finished sync

There is a failure mode that is easy to miss because it produces no error at all: Syncthing simply not running on one of your machines. I found a laptop where the Syncthing process had been down for weeks, holding a month's worth of local changes that had never reached any other device, on a repo that was also hundreds of commits behind its own remote. From the outside, a folder with nothing left to sync and a folder whose sync daemon has quietly died look identical: both show as idle, both show no pending transfers. The only way to tell the difference is to check that the process is actually running, not just that the folder state looks settled. If a machine has been offline or asleep for a while, verify the daemon came back up before you assume anything you changed on it has gone anywhere.

Sync is not backup

This is the one that catches people who set Syncthing up specifically to replace a cloud backup and stop there. Sync propagates a deletion exactly as fast and exactly as reliably as it propagates an edit. Delete a file on one device, and by design that deletion reaches every peer that is online. There is no separate deleted-files bin sitting on a server the way there sometimes is with a hosted cloud drive. If you want protection against your own mistake, Syncthing has a file versioner you turn on per folder, which keeps old revisions for some window instead of discarding them the moment a newer version syncs in. That is a real safety net and worth enabling on anything you'd be upset to lose. But it lives on the same devices as the live files, syncing across the same peers, subject to the same daemon-down blind spot above. A version history that lives entirely inside the sync mesh is not the same thing as a copy sitting somewhere outside it. If a folder actually matters, put a real backup behind it too, not just versioning.

Topics

Still stuck? Send it to Emsden Studio and get a straight answer on what it is and what fixing it costs.

More guides

All guides