Syncthing native app for macOS (Synctrain iOS based)

The reddit post is probably related to using relays. You will likely see the exact same warning with just Syncthing itself (see https://docs.syncthing.net/users/faq.html#why-does-syncthing-connect-to-this-unknown-suspicious-address).

The full source code of Synctrain is available here for anyone to review. You may also use the source code to build the app yourself if you do not trust that binary releases match it.

Note that most of the app code concerns rather mundane user interface code (with some significant chunks related to the streaming server as well as photo synchronization). The heavy lifting, including the security-sensitive bits, is done by Syncthing (fully open source here) as well as all the packages it uses (and you’d have to trust as well). All of that is open source as well.

If there are any questions, I am happy to answer them. From my perspective this is about as transparent as it can be, but if you have any further suggestions, happy to hear.

3 Likes

Hi, I just installed this app on my iphone16e with Testflight on ios 18.3. On macos I keep the original Syncthing because I’m 10.13 and 10.14. It synchronized with my existing syncthing “server” : I have a pi with encrypted folder (the “pseudo server” is trusted but just shares 1 encrypted folder for security reason), and my iphone, my android and a laptop share this folder (unencrypted on these devices). The central “pseudo encrypted server” centralizes the shared files when my devices are off. It is exactly what I wanted, and I like closing the app on my iphone when not reaching a specific file in the shared folder

Just 2 questions:

  • I’m French in France, will I get the final appstore version or are laws too restrictive when it’s not in beta anymore?
  • why does my shared folder have another name by default with your app? It automatically gives it’s real name to my other devices with the original syncthing. Here, with synctrain, it proposed something like sdkjsd-2hjk3 : it’s weird but it works like a charm.

Best regards

Sorry for the late reply!

The issue is that to put an app using cryptography on the French market I need to submit a self-declaration that is quite involved (and basically covers all of Syncthing and dependencies, not just my app) and also in French. I think I technically cannot even release the beta version in France, though I cannot restrict countries for TestFlight, and neither can I prevent people in France from downloading the source code. I will say I try to keep the TestFlight builds accurate and somewhat stable.

Folders in Syncthing have an ID and a display name. sdkjsd-2hjk3 looks like an auto-generated folder ID to me. From your explanation it seems that sdkjsd-2hjk3 is the folder ID and you set a different display name in Syncthing afterwards. Synctrain requires the folder name on disk to equal the folder ID (at least for folders inside its own container - you can place folders elsewhere and decide on the folder name yourself). Within Synctrain you can also set your own display name, and inside the app that is what it will show you.

Edit: Scratch that. It was a transient 503 from the App Store CDN.

Separately, though, I’m curious: Since you’ve implemented selective sync, why didn’t you go down the path of implementing the Replicated File Provider API? On iOS especially, that would give your app some background execution time at every optimal moment - browsing the folder, opening a file for the first time, and immediately after writing a new/updated file. That seems like the ultimate seamless integration of a Syncthing client into the OS.

(I know that there have historically been some annoying limitations of File Providers, but they are getting more complete with every release.)

Implementing File Provider (FP) support for Syncthing was actually one of the first things I investigated when I started work on the app. I ultimately decided not to pursue it for the following reasons:

  • The FP APIs are (as far as I understand them at least) heavily based around a model where a central server is available to download content from (in the background, using HTTPS). Our FP extension would tell the system what to download/upload where, instead of doing it by itself. This doesn’t work with Syncthing’s custom protocol.
  • To work properly, the FP extension would have to re-implement/wrap much more Syncthing functionality (i.e. scanning) than the current solution. We would have to maintain a sort of cache in the background because we need the files to stick around for other peers to sync at a later point in time. This gets complicated very quickly. (Especially considering things like folder types, ignore patterns, etc).
  • An FP-based implementation would not allow syncing existing folders (such as Obsidian folders as I see many users doing) so that would require a separate implementation.
  • The FP extension only runs on (user) demand, so doesn’t allow longer periods of syncing with peers (the FP extension closes when your device has all the data it needs, but we want to stick around so that as much other devices as possible have your data). So that would then need to be handled by the app in parallel.
  • The FP extension that handles acces from other apps runs separately from the main app. This requires careful coordination as these are basically two processes concurrently attempting to access Syncthing’s internal database, talk to peers, write files, et cetera.
  • The FP API doesn’t allow for streaming (e.g. video) / block level access as far as I know.

In summary implementing FP is very complicated (if at all possible to do in a good way) and doesn’t add that much value (imo).

1 Like

Hello,

I’ve been playing around with Synctrain for the last few days and I have to say, it’s amazing. Mobius sync was good, but it had its issues and isn’t under active development(as far as I can tell). The major hangup I have with switching away from Mobius Sync and over to Synctrain is the handling of the photo library. I have been able to sync certain albums, but with no ability to customize the folder structure produced. I’d really like options to change the folder structure based on year, month, date, type, etc just like with the photo synchronization in the main settings. The reason I haven’t used that is because I really don’t want to have 2 copies of each photo on the same device. I’m not sure what the liklihood of this is either, but a built in HEIC/HEIF to PNG or JPG/JPEG converter would be amazing. Is there any work being put into any of this or is this on the roadmap for future builds maybe? I really love the project and I can’t wait to see where this goes!

Thanks, Chris

Ah, one other question I forgot to ask in my first post. Is there any way to change the name of a folder in the Files app? I was able to create a new folder with whatever name I wanted outside of the Synctrain main folder and then add it as an external folder, but not inside of the main Synctrain folder. I’d really like to keep all Syncthing stuff inside the main folder, but I also go to the files app a lot and trying to remember which random string of numbers and letters corresponds to which folder is unintuitive. I also realize I could just recreate all my syncthing folders with different, more intuitive, Folder ID’s, but that’s a lot of work and seems like it shouldn’t be nessecery.

Thanks again, Chris

Great to hear you like the app!

The ‘photo folder’ feature has only recently been introduced, so that’s why features like this are not implemented yet. While I can’t make any promises, I think I will eventually implement the options that are currently available for the photo back-up feature for the photo folder feature as well. Maybe you can elaborate a bit on what kind of folder structure you’d like to use and I can see what I can do.

The issue with this is that the app would either need to store the generated PNG/JPG, or would have to generate it each time Syncthing wants to scan the photo folder (to check if there are any changes). The latter obviously drains the battery pretty hard or requires some sort of caching mechanism. I would suggest to look into a solution where the other peer runs a script to convert the HEIF files to PNG/JPG instead.

Currently, no. For backwards compatibility reasons the app requires the name of the folders inside the app-managed folder to correspond to the folder IDs. I don’t really want to change this right now because it runs the risk of breaking the app for users if I don’t get this 100% right.

Maybe this could work as a workaround for you (not sure if iOS supports this at all, worth a shot): Localizing the Name of a Directory

Thanks so much for you’re response!

My personal preference is “Subdirectory/Year/Month/IMG_0001.PNG” which would look like “Reddit/2025/04/IMG_0001.png”, but this is my preference. I like this because I don’t want hundreds of folders with only a few files per folder. It takes forever to find anything specific, but I’m sure other use cases would necessitate a different structure.

The current implementation already provides a subdirectory, so that’s good. Then the ability to choose from one of these options.

  • “Subdirectory/IMG_0001.png”
  • “Subdirectory/Year/IMG_0001.png”
  • “Subdirectory/Year-Month/IMG_0001.png”
  • “Subdirectory/Year-Month-Day/IMG_0001.png”

or these options.

  • “Subdirectory/IMG_0001.png”
  • “Subdirectory/Year/IMG_0001.png”
  • “Subdirectory/Year/Month/IMG_0001.png”
  • “Subdirectory/Year/Month/Day/IMG_0001.png”

Personally I’m leaning toward the second set of options, but implementing both and having too many options is typically a good thing, especially in a community like this.

Another nice feature, might be the option to append dates to the start of the file names. So a photo named “IMG_0001.png” could be renamed to “2025-04-27_IMG_0001.png” This could have another list of possible options like with folder subdirectories.

  • “IMG_0001.png”
  • “Year_IMG_0001.png”
  • “Year-Month_IMG_0001.png”
  • “Year-Month-Day_IMG_0001.png”
  • “Year-Month-Day-Time_IMG_0001.png”

This may not work, but what about generating a file that remembered what has and hasn’t been converted yet? If a new HEIC file pops up, Synctrain can grab that, check the database, see that it hasn’t been seen before, convert it, and then remember the file name of the HEIC and PNG/JPG equivalent. This way, next time it scans, it can check the file names and see that it’s already been converted. If the JPG goes missing, then it can convert a new copy. I’m not a programmer, so I have no idea if this would work.

Thanks again! I hope this project gets offical backing from Syncthing!