如何使用 circe 将缺失的 json 数组解码为空列表

How to decode missing json array as empty List with circe

比如我们有一些案例class

case class Foo(a: Int, b: List[String])

我们想从 json {"a": 1} 中反序列化 Foo 的实例,用 Nil

替换丢失的 b 数组

我们可以为此类行为创建自定义解码器

implicit val fooDecoder: Decoder[Foo] = (c: HCursor) => 
  for {
    a <- c.downField("a").as[Int]
    b <- c.downField("b").as[Option[List[String]]
  } yield Foo(a, b.getOrElse(Nil))

但是,不幸的是,以这种方式创建的解码器不会累积所有解码失败。

是否有任何方法可以创建具有失败累积的解码器或任何方法来替换标准列表反序列化行为?

尝试使用 circe-generic-extras 提供 b: List[String] = Nil

import io.circe.parser._
import io.circe.generic.extras.Configuration
import io.circe.generic.extras.auto._

implicit val config: Configuration = Configuration.default.withDefaults
case class Foo(a: Int, b: List[String] = Nil)
val raw = """{"a": 1}"""
decode[Foo](raw) // res0: Either[io.circe.Error,Foo] = Right(Foo(1,List()))

其中

libraryDependencies ++= Seq(
  "io.circe" %% "circe-core" % "0.12.0-M3",
  "io.circe" %% "circe-parser" % "0.12.0-M3",
  "io.circe" %% "circe-generic-extras" % "0.12.0-M3",
  "io.circe" %% "circe-generic" % "0.12.0-M3"
)

你也可以用.map(_.getOrElse(List.empty))

implicit val fooDecoder: Decoder[Foo] = (c: HCursor) => 
  for {
    a <- c.downField("a").as[Int]
    b <- c.downField("b").as[Option[List[String]].map(_.getOrElse(List.empty))
  } yield Foo(a, b)