我有一个类型类,想为用户提供半自动和自动派生。我有一个基于Magnolia的工作实现,它运行得非常好。有一个 trait 为,和提供定义,那么这两种类型的派生都可以通过Typeclass[A]
combine[A]
dispatch[A]
final object semiauto extends Derivation {
def deriveFormat[A]: Typeclass[A] = macro Magnolia.gen[A]
}
final object auto extends Derivation {
implicit def deriveFormat[A]: Typeclass[A] = macro Magnolia.gen[A]
}
没什么好惊讶的。不足为奇的是,当用户auto._
进入范围时,它会掩盖为特定类型编写的有效派生。
我希望我可以使用 Travis Brown 为 Circe 设计的相同技术,它的工作原理基本上是这样的:
定义一个可以保存任何值的占位符值类
case class Exported[A](instance: A) extends AnyVal
当该类的值在范围内时,为我的类型类提供低优先级自动派生
object DynamoFormat extends LowPriorityDerivation {
// derivation for specific types
...
}
trait LowPriorityDerivation {
implicit def deriveExported[A](implicit e: Exported[DynamoFormat[A]]) =
e.instance
}
最后,隐藏导出对象的自动派生auto
final object auto extends Derivation {
implicit def derive[A]: Exported[DynamoFormat[A]] =
Exported(semiauto.deriveFormat[A])
}
遗憾的是,在尝试调用宏时出现编译错误:
magnolia: could not infer auto.Typeclass for type com.gu.scanamo.DynamoFormat[A]
Exported(deriveDynamoFormat[A])
^
我看这段代码太久了,找不到出路;任何帮助将不胜感激。