I want to generate simple decorator for my type
In Swift it can be cumbersome to write a simple decorator that decorates all the calls to decorated type methods, you basically have to do it manually for each single method. With this template you can generate simple decorator that generate all the methods and property calls automatically, skipping methods and properties already implemented manually.
You can use this template as a starting point for more sophisticated implementations. This template also shows you some powers of swift templates, like using helper methods and whitespace control tags.
Swift template
Available annotations
decorate
- what type to decoratedecorateMethod
- code to decorate each method call withdecorateGet
- code to decorate each property getterdecorateSet
- code to decorate each property setter
Example input:
protocol Service {
var prop1: Int { get }
var prop2: Int { get set }
func foo(f: Int, _ a: Int) throws -> Int
func bar(_ b: String)
}
// sourcery: decorate = "Service"
// sourcery: decorateMethod = "print(#function)"
// sourcery: decorateGet = "print("get: \(#function)")"
// sourcery: decorateSet = "print("set: \(#function)")"
struct ServiceDecorator: Service {
// generated code will go here
}
extension ServiceDecorator {
// manually implemented method
internal func bar(_ b: String) {
decorated.bar(b)
}
}
Example output:
...
// sourcery: decorate = Service
// sourcery: decorateMethod = print(#function)
// sourcery: decorateGet = "print("get: \(#function)")"
// sourcery: decorateSet = "print("set: \(#function)")"
struct ServiceDecorator: Service {
// sourcery:inline:auto:ServiceDecorator.autoDecorated
internal private(set) var decorated: Service
internal init(decorated: Service) {
self.decorated = decorated
}
internal var prop1: Int {
print("get: \(#function)")
return decorated.prop1
}
internal var prop2: Int {
get {
print("get: \(#function)")
return decorated.prop2
}
set {
print("set: \(#function)")
decorated.prop2 = newValue
}
}
internal func foo(f: Int, _ a: Int) throws -> Int {
print(#function)
return try decorated.foo(f: f, a)
}
// sourcery:end
}
...