Swift Property Wrapper | Quick Note

This weekend, I gave πŸ‘¨πŸ½β€πŸ’» on Property Wrapper to see where I can make use of it, so here are the quick note.

Image credit : https://www.instagram.com/buntylm

Background, Swift properties do contains some extra code (‘get’ and ‘set’) when we want to observe the changes. For example, if we want to add some log to see the new value every time a property changes. The straightforward way of implementing this is

struct Student {
    private var name_: String
    public var name: String {
        get {
            return name_
        } set {
            name_ = newValue
            print("Setting new value \(newValue)")
        }
    }
}

Wait, If we follow this approach for logging more properties, our codebase will become a mess soon, so handle this let’s create a type which will help us to log.

struct Loggable<T> {
    private var value: T

    public init(wrappedValue: T) {
        self.value = wrappedValue
    }

    public var wrappedValue : T {
        get {
            value
        } set {
            value = newValue
            print("Setting new value \(newValue)")
        }
    }
}

Let’s update our implementation.

struct Student {
    private var name_ = Loggable<String>(wrappedValue: "NA")
    public var name: String {
        get {
            return name_.wrappedValue
        } set {
            name_.wrappedValue = newValue
        }
    }
}

Great, looks better and That is the problem, Property Wrapper (require Swift 5.1) is solving. All you need to do is add ‘@propertyWrapper’ to ‘Loggable’, and below the how Loggable and Student class will look like

@propertyWrapper
struct Loggable<T> {
    private var value: T

    public init(wrappedValue: T) {
        self.value = wrappedValue
    }

    public var wrappedValue : T {
        get {
            value
        } set {
            value = newValue
            print("Setting new value \(newValue)")
        }
    }
}

struct Student {
    @Loggable var name: String = "NA"
}

Another way of giving the default value 😬

struct Student {
    @Loggable(wrappedValue: "NA") var name
}

Property Wrapper decorates a property with a custom behaviour (similar like we use annotation in Java/Kotlin).  To note, Property Wrapper

  • always need to defined with ‘@properWrapper’ and must have ‘wrappedValue’ property.
  • cannot be set as ‘lazy’, ‘weak’, ‘unowned’ or ‘@NSManaged’.
  • cannot be declared in protocol or extension.
  • cannot be overridden.
  • cannot have custom ‘get’ or ‘set’.

That’s it, Thanks for reading.
Do give a try and let me know which is the use-case you want to use it. πŸ˜ƒ

Reference
https://github.com/apple/swift-evolution/blob/master/proposals/0258-property-wrappers.md

Leave a Reply

Fill in your details below or click an icon to log in:

WordPress.com Logo

You are commenting using your WordPress.com account. Log Out /  Change )

Google photo

You are commenting using your Google account. Log Out /  Change )

Twitter picture

You are commenting using your Twitter account. Log Out /  Change )

Facebook photo

You are commenting using your Facebook account. Log Out /  Change )

Connecting to %s

This site uses Akismet to reduce spam. Learn how your comment data is processed.