I just digged into the topic of how to use computed properties with Stencil because I had this issue in a project of mine.
This was already discussed here:
This bug report was closed because this feature was added:
I was looking for something better compared to the workaround "don't use computed properties, always set regular properties instead". For example, if you want to pass a struct to Stencil like this and use the sum property:
struct Prices {
let prices: [Decimal]
var sum: Decimal {
prices.reduce(0, +)
}
}
you could use something like this:
struct Prices {
let prices: [Decimal]
var sum: Decimal = 0
mutating func updateSum() {
self.sum = prices.reduce(0, +)
}
}
I didn't like this solution too much, thus this bug report. The only clean alternative would be manually mapping the data types to Dictionary, which would mean a lot of manual busywork for complex types.
I tinkered with DynamicMemberLookup, you could add the sum property yourself, but then you loose the support for accessing other properties via the Mirror approach. One could copy the Mirror#getValue method from Stencil and use that as fallback, but looking at that method and the nil-handling I thought: no, better not.
I wondered:
Would it make sense to fall back to the Mirror-resolving if DynamicMemberLookup doesn't resolve a value? That way one could add code to add computed properties by manually resolving them.
So you could add something like this:
extension Prices: DynamicMemberLookup {
subscript(dynamicMember member: String) -> Any? {
if member == "sum" {
return self.sum
}
return nil
}
}
and could still access the prices property without manually resolving it.
This currently is not possible, if it implements DynamicMemberLookup, it will not resolve via Mirror anymore:
https://github.com/stencilproject/Stencil/blob/4f222ac85d673f35df29962fc4c36ccfdaf9da5b/Sources/Stencil/Variable.swift#L121:L124
Or maybe an extra protocol like DynamicMemberLookup that allows to add dynamic properties on top of the mirrored ones like that?
I just digged into the topic of how to use computed properties with Stencil because I had this issue in a project of mine.
This was already discussed here:
This bug report was closed because this feature was added:
7247d0a
I was looking for something better compared to the workaround "don't use computed properties, always set regular properties instead". For example, if you want to pass a struct to Stencil like this and use the
sumproperty:you could use something like this:
I didn't like this solution too much, thus this bug report. The only clean alternative would be manually mapping the data types to Dictionary, which would mean a lot of manual busywork for complex types.
I tinkered with DynamicMemberLookup, you could add the
sumproperty yourself, but then you loose the support for accessing other properties via the Mirror approach. One could copy theMirror#getValuemethod from Stencil and use that as fallback, but looking at that method and the nil-handling I thought: no, better not.I wondered:
Would it make sense to fall back to the Mirror-resolving if DynamicMemberLookup doesn't resolve a value? That way one could add code to add computed properties by manually resolving them.
So you could add something like this:
and could still access the
pricesproperty without manually resolving it.This currently is not possible, if it implements DynamicMemberLookup, it will not resolve via Mirror anymore:
https://github.com/stencilproject/Stencil/blob/4f222ac85d673f35df29962fc4c36ccfdaf9da5b/Sources/Stencil/Variable.swift#L121:L124
Or maybe an extra protocol like DynamicMemberLookup that allows to add dynamic properties on top of the mirrored ones like that?