In a Play application I\'m working on, I\'m trying to improve our system for processing flags, some of which are meant to be persistent options as a user navigates our app v
Update: the FieldPoly
helper actually doesn't do all that much work for you here, and you can accomplish the same thing without it (and without the Witness
implicit):
import shapeless.labelled.{ FieldType, field }
object bind extends Poly1 {
implicit def rpb[T, K]: Case.Aux[
FieldType[K, RequestParamBuilder[T]],
FieldType[K, RequestParam[T]]
] = at[FieldType[K, RequestParamBuilder[T]]](b => field[K](b(requestParams)))
}
It's also worth noting that if you don't mind living dangerously, you can skip the return type (in both implementations):
object bind extends Poly1 {
implicit def rpb[T, K] = at[FieldType[K, RequestParamBuilder[T]]](b =>
field[K](b(requestParams))
)
}
But in general having an implicit method with an inferred return type is a bad idea.
As I mention in a comment above, Case
isn't covariant, which means that your bind
will only work if the elements of the HList
are statically typed as RequestParamBuilder
(in which case you don't have a record).
You could use .values
to get the values out of the record, and you can then map over the result, but (as you note) this would mean you lose the keys. If you want to preserve the keys, you can use Shapeless's FieldPoly
, which is designed to help out in this kind of situation:
import shapeless.labelled.FieldPoly
object bind extends FieldPoly {
implicit def rpb[T, K](implicit witness: Witness.Aux[K]): Case.Aux[
FieldType[K, RequestParamBuilder[T]],
FieldType[K, RequestParam[T]]
] = atField(witness)(_(requestParams))
}
Now options.map(bind)
will work as expected.
I don't think there's a better way to write this at the moment, but I haven't been following the most recent Shapeless developments very closely. In any case this is reasonably clear, not too verbose, and it does what you want.
To answer the other question in your comment: this previous question is a starting point, but I'm not aware of a really good overview of the mechanics of the implementation of polymorphic function values in Shapeless. It's a good idea for a blog post.