json - Scala/Play : modify Json. 单个字段的格式宏行为

标签 json scala playframework

我有一个包含 10 多个字段的大案例类,代表来自用户的 JSON 有效负载。大多数字段都是可选的,因此在这种情况下我使用 Option (Option[String] 对于字符串字段。这是一个很好的方法,直到我需要一个可选序列.我认为编写 Option[Seq[String]] 很奇怪,因为空序列足以表明没有数据(出于任何原因)。 不过,我可以通过手动方式处理它:

implicit val reads = new Reads[MyCaseClass] {
  def reads(js: JsValue): JsResult[MyCaseClass] = {
    JsSuccess(MyCaseClass(
      (js \ "unit_code").as[String],
      // other fields omited
      (js \ "positions").asOpt[Seq[String]] match {
        case Some(seq: Seq[String]) => seq
        case None => Seq.empty[String]
      }
    ))
  }
}

但我不想手动编写所有这些内容。可能会有错误,我需要单独测试它,当然,这比编写 implicit val f = Json.format[MyCaseClass] 花费更多时间。

是否有任何选项可以单独处理一个字段,而其他字段则在默认宏上处理 let ?

最佳答案

感谢用户“cchantep”指向 Json transformers 。 这就是我解决问题的方法:

案例类别:

case class MyCaseClass(unit_code: String, positions: Seq[String] = Seq.empty)

伴随对象

object MyCaseClass {
  private val readsTransformer: Reads[JsObject] =  __.json.update(
    __.read[JsObject]
      .map{ o =>
        if (o.keys.exists(p => p.equals("positions"))) {
          o
        } else {
          o ++ Json.obj("positions" -> JsArray())
        }
      }
  )
  implicit val readsImplicit: Reads[MyCaseClass] = readsTransformer.andThen(Json.reads[MyCaseClass])
  implicit val writesImplicit: OWrites[MyCaseClass] = Json.writes[MyCaseClass]
}

这看起来有点麻烦,但是可以编写为精确字段创建变压器的通用函数,因此在每个伴随对象中它不会那么冗长。

关于json - Scala/Play : modify Json. 单个字段的格式宏行为,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/48115419/

相关文章:

json - 在 Julia 中是否值得对 `JSON.parsefile` 返回的字典进行类型缩小

scala - 从 Scala 中的类型检查中删除路径依赖

java - Spark 内存分数与年轻一代/老一代 java 堆拆分

forms - In Play 2.4.0 如何在嵌套表单的多字段约束中命名字段?

mysql - 玩! 2.0 - BoneCP 返回关闭的连接

php - 遍历 JSON NSDictionary

json - ARKit 4.0 – 是否可以将 ARWorldMap 数据转换为 JSON 文件?

python - 如何使用 Python 创建嵌套的 JSON 对象?

scala - Scala 的绝对反向路由?

playframework - Play Framework 的帮助是如何实现的?