Designing a configuration system for Swift apps on Linux

Hello,

As a hobbyist coder with some itches to scratch, I seem to find myself building small Swift apps on Raspberry Pi hardware.

I have one app which interfaces with a bit of hardware in the real world and I have it deployed on four devices. I’m in the middle of another project which will be deployed to two instances.

Both of these projects require ‘config’ files as the configuration differs per-install. Foundation’s UserDefaults does not work on Linux, so I have tended to write classes which keep the config properties and can decode/encode to JSON on the filesystem. However, I’m thinking of generalising a solution in a package which could be re-used.

I’m not willing to wait until New Foundation is ready….

A) Can anyone recommend an existing package that does this? I found a suggestion in a forum post from a while ago which uses a Kitura package, but since that project is not active, I’d be wary of using it.

I notice that Vapor has Environment Environment, however it’s inside Vapor and I’d like to keep my solution as a simple, separate package.

B) At the risk of re-inventing the wheel, I was thinking of building my own package which will do this, as it will be a good learning experience.

Assuming B is the correct route, I was thinking of dumping my idea for a design here (which isn’t yet properly formed, but I’m hoping that writing it down will help crystallise it). Then you can all tell me why I’m an idiot and why your ideas are much better :)

Goals:

  • Option to allow ‘factory’ defaults defined by the user/client from a file, or Swift type.
  • Store the config in JSON format in /etc/yourAppName.json
  • Functions to save and load the config
  • Option to set certain config properties to auto-save to file when they are changed in-app. With a coalescing/debounce function so that rapid changes to said properties don’t get bogged-down in file saves.

Design:

  • A simple key-value store (a shell around a dictionary?)
  • Keep a record of all valid keys?
  • Maybe a property wrapper that allows the autosave function.
  • Perhaps use Mirror to make sure that all properties are saved...

What am I missing? Apologies - this is clearly outsourcing the thinking required….

Thanks.

4 Likes

I've made a very basic version here:

1 Like

Just last week we (Apple) released a new configuration language called Pkl (read as "pickle"): https://pkl-lang.org/

It includes Swift compatibility from day one: GitHub - apple/pkl-swift: Pkl bindings for the Swift programming language

The support is basic and the repo could use some help on the SwiftPM plugins side etc. It'd be great to hear if you think this could be viable -- I personally am very excited about configuration files which can be typechecked, rather than the freeform and easy to make typos in JSON files :slight_smile:

As the repo and language is just freshly released, the maintainers I'm sure would love issues and help getting it to a point where it is our go-to configuration language on the server for Swift.

8 Likes

That’s very interesting, thanks!

I think my use case is a little different, I’m looking for a User Defaults-like thing where I can read and write to a persistent key/value store.

1 Like