sindresorhus / Defaults

💾 Swifty and modern UserDefaults
https://swiftpackageindex.com/sindresorhus/Defaults/documentation/defaults
MIT License
1.97k stars 117 forks source link

Support dynamic default value? #108

Closed sindresorhus closed 1 year ago

sindresorhus commented 2 years ago

Sometimes you cannot define a static default value as it may change during the lifetime of the app. For example, the default value is the current system appearance or a connected device (which may disconnect).

For situations like these, it would be nice if the default value could also be a getter:

extension Defaults.Keys {
    static let camera = Key<AVCaptureDevice?>("camera") { .default(for: .video) }
}

The getter would be executed every time Defaults[.camera] is called.

sindresorhus commented 2 years ago

@hank121314 Thoughts?

hank121314 commented 2 years ago

I think we might be able to create a closure type Getter, ex. typealias Getter = (Value) -> Value. The function parameter of Getter will be a deserialized Value from UserDefaults. And add property getter with Getter type in Defaults.Key.

sindresorhus commented 1 year ago

Sounds good to me 👍

hank121314 commented 1 year ago

I think we might enable this feature only if Value is optional(Value?)?

If Value is not optional, user will need to set defaultValue which will be used in UserDefaults.register. If defaultValue have been registered, UserDefaults._get will always get a Value which will not trigger key.defaultValue.

sindresorhus commented 1 year ago

I think it should be supported for non-optional values too.

sindresorhus commented 1 year ago

If Value is not optional, user will need to set defaultValue which will be used in UserDefaults.register.

UserDefaults.register was useful for legacy use-cases outside of Defaults, but it's not that useful these days. There's not really any good reason to use UserDefaults directly. So I think we can just document that when you use the getter, the default is not set in UserDefaults.register.