简体   繁体   English

定义Case类的Writes,其中包含类型为Map的属性。 Json / Scala / PlayFramework

[英]Defining Writes for case class that contains property whose type is a Map . Json / Scala / PlayFramework

I have a case class defined this way: 我用这种方式定义了一个案例类:

scala> import play.api.libs.json._
  import play.api.libs.json._
scala> import play.api.libs.functional.syntax._
  import play.api.libs.functional.syntax._

scala> type MapIntString = Map[Int, String]
  defined type alias MapIntString

case class Duh(a: MapIntString)
  defined class Duh

When I tried declaring its Writes this way, I got an error: 当我尝试以这种方式声明其Writes时,出现错误:

scala> implicit val duhWrites = Json.writes[Duh]
  <console>:25: error: No implicit Writes for MapIntString available.
  implicit val duhWrites = Json.writes[Duh]

So I resort to this..., still got an error: 所以我诉诸于此...,仍然出现错误:

scala> implicit val duhWrites: Writes[Duh] = (
     |   (JsPath \ "a").write[MapIntString]
     | )(unlift(Duh.unapply _))
  <console>:26: error: overloaded method value write with alternatives:
  (t: MapIntString)(implicit w: play.api.libs.json.Writes[MapIntString])play.api.libs.json.OWrites[play.api.libs.json.JsValue] <and>
  (implicit w: play.api.libs.json.Writes[MapIntString])play.api.libs.json.OWrites[MapIntString]
  cannot be applied to (Duh => MapIntString)
  (JsPath \ "a").write[MapIntString]

Can somebody help me pointing out where I did wrong? 有人可以帮我指出我做错了什么吗?

I feel that my understanding of this reads/writes combinators a bit shaky. 我觉得我对读/写组合器的理解有些不稳定。 I posted related question here (when I was trying to understand what was going on): What is this "and" in ScalaJsonCombinator (when defining a Writes)? 我在这里发布了相关的问题(当我试图了解正在发生的事情时): ScalaJsonCombinator中的“和”是什么(在定义Writes时)?

If you know the best way to implement the Writes and Reads for "Duh" please share. 如果您知道实现“ Duh”读写操作的最佳方法,请分享。

Thanks in advance! 提前致谢!

There are no predefined Writes for Map[Int, String] , only Map[String, A] . 没有Map[Int, String]预定义Writes ,只有Map[String, A] This is because all JSON keys must be a String , to Int keys don't really make any sense. 这是因为所有JSON键都必须是String ,而Int键实际上没有任何意义。 You can fix this by defining one that converts the Int keys to String s. 您可以通过定义一个将Int键转换为String的方法来解决此问题。

type MapIntString = Map[Int, String]

implicit val mapIntWrites = new Writes[MapIntString] {
    def writes(m: MapIntString): JsValue = 
        Json.toJson(m.map { case (k, v) => (k.toString, v)} )
}

scala> implicit val duhWrites = Json.writes[Duh]
duhWrites: play.api.libs.json.OWrites[Duh] = play.api.libs.json.OWrites$$anon$2@50973f47

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM