Discord Solution

Syncthing on CasaOS Cannot Create a Sync Folder on Another Physical Drive

A CasaOS user found that Syncthing could work with direct paths but continued to fail when a symbolic link redirected the sync folder to another physical drive, even after permission and ownership changes.

Key conclusion: this is probably not a “keep changing chmod until Syncthing works” problem. The stronger signal is that the folder works when it is on a path Syncthing can see directly, but fails when a symbolic link crosses to another physical drive. In CasaOS, that points first to the container's mounted paths, then to UID/GID permissions.

“I already set permissions all the way through… it works when I target /DATA/AppData/, but not when the link points to a different physical drive.” That test result is more useful than the original permission error because it isolates the failure to the storage path.

Why the symbolic link is the first thing to question

Syncthing does not treat a symlink as “please jump to the target and sync whatever is there.” The documented Syncthing symlink behavior is that symbolic links may be synchronized but are never followed. Its folder configuration also expects a real device-local path: Syncthing Folder Path is the physical path to the folder on the hard drive.

That makes a path such as this suspicious:

/DATA/Documents/Syncthing/SyncFiles → symlink → /some/other/physical/drive

If Syncthing is running in Docker, the host can resolve that link while the container may not be able to see the destination at all.

The CasaOS Syncthing app explains why a second drive can disappear

The official CasaOS App Store definition for Syncthing is unusually helpful here. Its compose file bind-mounts two host paths into the container:

/DATA/AppData/$AppID/config → /config
/DATA                      → /DATA

You can verify the actual volume mapping in the CasaOS Syncthing compose.

That means a target physically available under the host's /DATA tree should also be visible under /DATA inside the Syncthing container. But if the symlink ultimately points to a host mount outside that tree, the container needs a separate bind mount for the real destination. With Docker bind mounts, host directories must be explicitly mounted into the container.

Use this test to distinguish a path problem from a permission problem

Run the checks in this order. Do not start with another recursive chmod.

1. Resolve the real path on the CasaOS host

readlink -f "/DATA/Documents/Syncthing/SyncFiles"

If the command returns a path outside /DATA, you have found an important clue.

2. Ask the Syncthing container whether it can see the same target

docker exec syncthing ls -ld "/DATA/Documents/Syncthing/SyncFiles"

Then test the resolved destination if it is supposed to exist inside the container. If the host can list it but the container cannot, permissions are not yet the primary problem; the path is missing from the container namespace.

3. Inspect the actual container mounts

docker inspect syncthing

Look at the Mounts section. You should be able to identify the host source and container destination for the drive you intend to sync.

The cleaner fix: bind-mount the real drive, then use that container path

If the external drive is outside /DATA, expose it directly to Syncthing instead of hiding it behind a symlink. Conceptually, the compose entry looks like:

volumes:
  - type: bind
    source: /real/host/path/to/external-drive
    target: /sync-drive

Then configure the Syncthing folder path as something explicit, for example:

/sync-drive/Dev Files

This is not a magic path; choose a target that matches your compose configuration. The important part is that the container receives the real host directory as a mounted volume.

The upstream LinuxServer Syncthing image uses the same model and documents separate host-to-container data mappings such as /path/to/data1:/data1 and /path/to/data2:/data2. Its Syncthing PUID/PGID mapping also explains how container identity should match host volume ownership.

Only after the mount is correct should you fix ownership and permissions

The original troubleshooting included a suggestion like:

sudo chmod -R 770 /path/to/folder

770 can be appropriate in some setups, but it only helps if Syncthing is actually running as a user or group that owns, or belongs to the group owning, that directory. The CasaOS app passes PUID and PGID into the LinuxServer image. LinuxServer's own documentation says host volume ownership should match the configured PUID/PGID.

Check the IDs rather than assuming the username casaos is enough:

docker exec syncthing id
stat -c '%u:%g %a %n' /real/host/path/to/external-drive

If the numeric UID/GID do not line up, change ownership or group membership intentionally. Avoid chmod -R 777; it hides the real issue and weakens access control.

What the “file exists” error is really telling you

The message:

mkdir /DATA/Documents/Syncthing/SyncFiles: file exists

does not prove that the final Dev Files directory is the problem. Syncthing is failing while preparing the folder root. When a parent path is a symlink or resolves differently inside the container, the application can encounter a filesystem object where it expected a normal directory path.

The fastest diagnostic is therefore not deleting and recreating the same directory. It is comparing:

  • the host's resolved path;
  • the path visible inside the container;
  • the container's bind mounts;
  • the numeric PUID/PGID against the destination ownership.

For a clean baseline, the CasaOS Syncthing setup shows a normal same-path synchronization flow before multi-drive customization. The ZimaOS app platform is useful when comparing alternative backup or file-sync tools. If the end goal is to consolidate several physical drives instead of bridging them through symlinks, ZimaCube 2 is the storage-focused hardware option.

FAQ

Should I solve this by changing the owner from root to casaos?

Not by itself. Ownership matters only after the container can see the real destination path. Verify the bind mount and the numeric PUID/PGID first.

Why does a direct path work while the symlink to another drive fails?

A direct path under a directory mounted into the container exists in both filesystems. A symlink can resolve to a host location that was never mounted into the container, leaving Syncthing with a path it cannot traverse.

Does Syncthing follow symbolic links to sync the target directory?

No. Syncthing's documentation says symbolic links are never followed. Use a real folder path visible to the Syncthing process.

What should I change first?

Resolve the symlink, inspect the Syncthing container mounts, and bind-mount the actual external-drive directory. Then verify PUID/PGID and permissions.