我正在使用Scala Play编写Web服务。功能还可以,但我正在重构一些部分,以使我的代码更具可读性和清洁性。
我已经为每个实体类使用了隐式,使它们可以转换为Json。我还将toJson
函数注入Seq[MyEntityClass]
,以便能够通过调用单个函数来生成Json数组。
看起来像这样:
case class MyModel(id: Option[Int], foo: String, bar: String)
object MyModel {
implicit val writer = Json.writes[MyModel]
implicit val reader: Reads[MyModel] = new Reads[MyModel] {
def reads(json: JsValue): JsResult[MyModel] = {
for {
foo <- (json \ "foo").validate[String]
bar <- (json \ "bar").validate[String]
} yield MyModel(None, foo, bar)
}
}
implicit def richMyModelSeq(apps: Seq[MyModel]) = new {
def toJson:JsValue = Json.toJson(apps)
}
// ...
}
如何在超类中定义此代码,以便不为每个实体类重复此代码?
为什么这不起作用?
abstract class Jsonable {
implicit val writer = Json.writes[Jsonable]
implicit def richMyModelSeq(apps: Seq[MyModel]) = new {
def toJson:JsValue = Json.toJson(apps)
}
}
case class MyModel(id: Option[Int], foo: String, bar: String)
object MyModel extends Jsonable{
implicit val reader: Reads[MyModel] = new Reads[MyModel] {
def reads(json: JsValue): JsResult[MyModel] = {
for {
foo <- (json \ "foo").validate[String]
bar <- (json \ "bar").validate[String]
} yield MyModel(None, foo, bar)
}
}
// ...
}
答案 0 :(得分:0)
您可以使用以下内容: 类可以扩展特征,伴随对象可以扩展MyModelComp。
import play.api.libs.json._
trait MyModel {
def id: Option[Int]
def foo: String
def bar: String
}
trait MyModelComp[M <: MyModel] {
def cons: MyModel => M
implicit val writer = Json.writes[MyModel]
implicit def reader[M]: Reads[M] = new Reads[M] {
def reads(json: JsValue): JsResult[M] = {
for {
foo <- (json \ "foo").validate[String]
bar <- (json \ "bar").validate[String]
} yield cons(new MyModel {
override def foo: String = ???
override def bar: String = ???
override def id: Option[Int] = ???
})
}
}
}