3

我正在处理我直接控制之外的一些代码,我需要对选项 [Thing] 进行编码,如果 Thing 存在,则情况正常,但是 None 情况必须返回“false”而不是 null。这可以轻松完成吗?我正在查看文档,但没有取得太大成功。

我的代码如下所示:

   case class Thing(name: String)
   case class BiggerThing(stuff: String, thing: Option[Thing])

   implict val ThingEncodeJson: EncodeJson[Thing] =
     EncodeJson(t => ("name" := t.name ) ->: jEmptyObject)

和 BiggerThing 的等价物,json 需要看起来像:

  1. 对于一些:

    "thing":{"name": "bob"} 
    
  2. 对于无:

    "thing": false
    

但目前 None 案例给出:

"thing":null

我如何让它返回false?有人可以指出我正确的方向吗?

干杯

4

1 回答 1

4

您只需要一个自定义CodecJson实例Option[Thing]

object Example {
  import argonaut._, Argonaut._

  case class Thing(name: String)
  case class BiggerThing(stuff: String, thing: Option[Thing])

  implicit val encodeThingOption: CodecJson[Option[Thing]] =
    CodecJson(
      (thing: Option[Thing]) => thing.map(_.asJson).getOrElse(jFalse),
      json =>
        // Adopt the easy approach when parsing, that is, if there's no
        // `name` property, assume it was `false` and map it to a `None`.
        json.get[Thing]("name").map(Some(_)) ||| DecodeResult.ok(None)
    )

  implicit val encodeThing: CodecJson[Thing] =
    casecodec1(Thing.apply, Thing.unapply)("name")

  implicit val encodeBiggerThing: CodecJson[BiggerThing] =
    casecodec2(BiggerThing.apply, BiggerThing.unapply)("stuff", "thing")

  def main(args: Array[String]): Unit = {
    val a = BiggerThing("stuff", Some(Thing("name")))
    println(a.asJson.nospaces) // {"stuff":"stuff","thing":{"name":"name"}}
    val b = BiggerThing("stuff", None)
    println(b.asJson.nospaces) // {"stuff":"stuff","thing":false}
  }
}

如何在BiggerThing没有thing属性的情况下对 a 进行编码thingis None。然后您需要一个自定义EncodeJson[BiggerThing]实例:

implicit val decodeBiggerThing: DecodeJson[BiggerThing] =
  jdecode2L(BiggerThing.apply)("stuff", "thing")

implicit val encodeBiggerThing: EncodeJson[BiggerThing] =
  EncodeJson { biggerThing =>
    val thing = biggerThing.thing.map(t => Json("thing" := t))
    ("stuff" := biggerThing.stuff) ->: thing.getOrElse(jEmptyObject)
  }
于 2015-02-18T02:02:09.773 回答