用自己的编解码器包装 circe 解码器(隐式)
Wrapping circe decoder with own codecs (implicits)
我正在使用 circe 通过 deriveDecoder
提供的半自动解码器推导。我有一些自定义 ADT,我想在其中传递我自己的解码器以供 circe 在解析隐式解码器时使用。
package object json {
implicit val myAdtDecoder: Decoder[MyAdt] = ...
}
虽然我现在需要在调用 circe 的 deriveDecoder
.
文件中导入两个文件,但这是有效的
有没有一种方法可以设置它以便我只需要导入一个?一种 "proxy" 到 circe 的 deriveDecoder
方法,它仍然会使用我的隐式 for MyAdt
?
package object json {
implicit val myAdtDecoder: Decoder[MyAdt] = ...
implicit def deriveDecoder[T]: Decoder[T] = ...
}
请注意,如果我在这里明确指定 T
,我可以毫无问题地解决这个问题,但我想保持它的通用性,以便它适用于任何 T
。
这里deriveDecoder
会是自动的(你不想自己调用它),但你尝试导入半自动版本。
使用自动方法你可以做:
trait ExtendedAuto extends io.circe.generic.AutoDerivation {
implicit val myAdtDecoder: Decoder[MyAdt] = ...
}
package object json extends ExtendedAuto
你必须小心不要(不小心)两次导入相同的隐式,否则推导将失败。但是如果你遵守纪律(例如始终只在任何地方导入你的包对象)那么它应该没问题。
使用 semiauto 会有所不同:
package object json {
implicit val myAdtDecoder: Decoder[MyAdt] = ...
// signatures copy-pasted from io.circe.generic.semiauto
import io.circe.generic.semiauto
final def deriveDecoder[A](implicit decode: Lazy[DerivedDecoder[A]]): Decoder[A] = semiauto.deriveDecoder[A]
final def deriveEncoder[A](implicit encode: Lazy[DerivedObjectEncoder[A]]): ObjectEncoder[A] = semiauto.deriveEncoder[A]
}
但是如果您使用的是 semiauto,您可能会将内容放入伴随对象中以避免同一编解码器的多次派生。在这种情况下,您可以考虑使用 @JsonCodec.
我正在使用 circe 通过 deriveDecoder
提供的半自动解码器推导。我有一些自定义 ADT,我想在其中传递我自己的解码器以供 circe 在解析隐式解码器时使用。
package object json {
implicit val myAdtDecoder: Decoder[MyAdt] = ...
}
虽然我现在需要在调用 circe 的 deriveDecoder
.
有没有一种方法可以设置它以便我只需要导入一个?一种 "proxy" 到 circe 的 deriveDecoder
方法,它仍然会使用我的隐式 for MyAdt
?
package object json {
implicit val myAdtDecoder: Decoder[MyAdt] = ...
implicit def deriveDecoder[T]: Decoder[T] = ...
}
请注意,如果我在这里明确指定 T
,我可以毫无问题地解决这个问题,但我想保持它的通用性,以便它适用于任何 T
。
这里deriveDecoder
会是自动的(你不想自己调用它),但你尝试导入半自动版本。
使用自动方法你可以做:
trait ExtendedAuto extends io.circe.generic.AutoDerivation {
implicit val myAdtDecoder: Decoder[MyAdt] = ...
}
package object json extends ExtendedAuto
你必须小心不要(不小心)两次导入相同的隐式,否则推导将失败。但是如果你遵守纪律(例如始终只在任何地方导入你的包对象)那么它应该没问题。
使用 semiauto 会有所不同:
package object json {
implicit val myAdtDecoder: Decoder[MyAdt] = ...
// signatures copy-pasted from io.circe.generic.semiauto
import io.circe.generic.semiauto
final def deriveDecoder[A](implicit decode: Lazy[DerivedDecoder[A]]): Decoder[A] = semiauto.deriveDecoder[A]
final def deriveEncoder[A](implicit encode: Lazy[DerivedObjectEncoder[A]]): ObjectEncoder[A] = semiauto.deriveEncoder[A]
}
但是如果您使用的是 semiauto,您可能会将内容放入伴随对象中以避免同一编解码器的多次派生。在这种情况下,您可以考虑使用 @JsonCodec.