Scala 尽管导入,但在测试中找不到参数化类型化自定义类的JSONReader
我有一个自定义类,如下所示Scala 尽管导入,但在测试中找不到参数化类型化自定义类的JSONReader,scala,spray,scalatest,spray-json,Scala,Spray,Scalatest,Spray Json,我有一个自定义类,如下所示 object SafeList { def apply[A](x: List[A]): SafeList[A] = if (x == null) EmptyList else HasItems[A](x) } sealed abstract class SafeList[+A] extends Product with Serializable { def get: List[A] } final case class HasItems[+A](x: Li
object SafeList {
def apply[A](x: List[A]): SafeList[A] = if (x == null) EmptyList else HasItems[A](x)
}
sealed abstract class SafeList[+A] extends Product with Serializable {
def get: List[A]
}
final case class HasItems[+A](x: List[A]) extends SafeList[A] {
def get = x
}
case object EmptyList extends SafeList[Nothing] {
def get = Nil
}
安全列表的格式化程序如下所示
...
import spray.json.DefaultJsonProtocol._
trait SafeCollectionFormats {
implicit def safeListFormat[A: RootJsonFormat] = new RootJsonFormat[SafeList[A]] {
def read(json: JsValue): SafeList[A] = {
val list: List[A] = listFormat[A].read(json)
SafeList[A](list)
}
def write(sl: SafeList[A]): JsValue =
listFormat[A].write(sl.get)
}
}
object SafeCollectionFormats extends SafeCollectionFormats
这就是编译
但是当我为我的格式化程序添加一个测试时,就像这样
...
import spray.json.DefaultJsonProtocol._
import marshalling.SafeCollectionFormats._
...
"Unmarshalling a json array with items" should "produce a SafeList with items" in {
val json: JsValue = JsArray(JsString("a"), JsString("b"), JsString("c"))
val list = List("a", "b", "c")
val result = json.convertTo[SafeList[String]]
assertResult(list)(result)
}
...
我得到以下编译错误
Error:(14, 32) Cannot find JsonReader or JsonFormat type class for myapp.types.SafeList[String]
val result = json.convertTo[SafeList[String]]
^
我想也许有什么办法可以帮助我,但这对我来说有点先进。我以为我的隐式safeListFormat是我的SafeList的JsonReader,我正在将它导入到我的规范中。我不知道参数化的类型是否令人困惑
知道我做错了什么吗
编辑:目前我的测试正在创建字符串的安全列表,最终目的是创建域对象的安全列表。我需要添加第二个测试来构建MyObject的JsArray。因此,JSON术语中的A-类型将有所不同。我的安全列表需要处理字符串等简单对象和域对象。我想我可能会把它作为第二个问题提出来,但我在这里提到它是为了上下文,它对我来说只需要一个小小的改变:我制作了
SafeCollectionFormats
extendDefaultJsonProtocol
我还必须将safeListFormat
的上下文绑定更改为[A:JsonFormat]
trait SafeCollectionFormats extends DefaultJsonProtocol {
implicit def safeListFormat[A: JsonFormat] = new RootJsonFormat[SafeList[A]] {
def read(json: JsValue): SafeList[A] = {
val list: List[A] = listFormat[A].read(json)
SafeList[A](list)
}
def write(sl: SafeList[A]): JsValue =
listFormat[A].write(sl.get)
}
}
object SafeCollectionFormats extends SafeCollectionFormats
希望这对您有所帮助。这是一个很大的帮助,谢谢!但你能解释一下原因吗?我的方法是基于spray jsons格式化程序,例如,和互联网上的其他例子,这些例子在traits和扩展这些traits的伴随对象中有其含义。你知道在我的情况下是什么阻止了这一点吗?如果不了解,我将来可能会犯同样的错误:(后续:虽然目前我的测试正在创建一个字符串的安全列表,但最终目的是创建一个域对象的安全列表。我只是尝试添加一个用于构建MyObject的JsArray的测试,并添加第二个扩展RootJsonFormat的隐式格式。但是现在编译器找不到安全列表[String]的JsonReader)同样,我希望是因为这两个隐式方法都创建了新的RootJsonFormat[SafeList[A]],但A的类型会根据安全列表中对象的复杂程度而有所不同。我编辑了我的答案。它也适用于
trait
+伴生对象
,因此它似乎是DefaultJsonProtocol所必需的,而不是使用import spray.json.DefaultJsonProtocol.
。我很想了解是的,就是这样-我还在试着了解隐式作用域,-但我会在喷雾表上单独问这个问题。非常感谢你,首先-你已经解开了我的障碍:)