Проблема сериализации и десериализации Scala (spray) json

Я использую свою собственную неявную реализацию сериализатора и десериализатора JSON для моего объекта case.

Мой класс case выглядит так (это всего лишь фрагмент кода)

sealed trait MyTrait

case object MyCaseClass extends MyTrait

Я хочу написать свой собственный сер. и достоин. JSON для MyTrait

implicit val myTraitFormat = new JsonFormat[MyTrait] {
  override def read(json: JsValue): MyTrait = json.asJsObject.getFields("value") match {
    case Seq(JsString("TEST")) ⇒ MyCaseClass
    case _ ⇒ throw new DeserializationException(s"$json is not a valid extension of my trait")
  }
  override def write(myTrait: MyTrait): JsValue = {
    myTrait match {
      case MyCaseClass => JsObject("value" -> JsString("TEST"))
    }
  }
}

Теперь мой тест терпит неудачу, вызывая исключение DeserializationException:

"The my JSON format" when {
  "deserializing a JSON" must {
    "return correct object" in {
      val json = """{"value": "TEST"}""".asJson
      json.convertTo[MyTrait] must equal (MyCaseClass)
    }
  }
}

Очевидно, что json.asJsObject.getFields("value") не может быть сопоставлено с Seq(JsString("TEST")). Может быть, это связано с использованием трейтов? Но я нашел пример на официальном сайте spray-json https://github.com/spray/spray-json#providing-jsonformats-for-other-types

Любые идеи, как правильно сопоставить поле в JsObject?

Спасибо! Лучший


person zmeda    schedule 06.06.2014    source источник
comment
Я не понимаю: ваш тест проверяет сериализацию, но вы реализовали десериализацию (= метод чтения)?   -  person Christian    schedule 06.06.2014
comment
Извините, неправильная часть кода... вы правы... исправлено!   -  person zmeda    schedule 06.06.2014


Ответы (1)


Напишите имя переменной вместо строки:

  override def read(json: JsValue): MyCaseClass = json.asJsObject.getFields("value") match {
    case Seq(JsString(value)) ⇒ MyCaseClass
    case _ ⇒ throw new DeserializationException(s"$json is not a valid case class")
  }

Это работает для вас?

Обновление: да, ваш тест неверен. Я попробовал это со следующим (обратите внимание на parseJson вместо asJson), и это сработало:

scala> val json = """{"value": "TEST"}""".parseJson
json: spray.json.JsValue = {"value":"TEST"}

scala> json.convertTo[MyCaseClass]
res2: MyCaseClass = MyCaseClass()

Обновление 2: Пробовал с чертой:

scala> import spray.json._
import spray.json._

scala> import spray.json.DefaultJsonProtocol._
import spray.json.DefaultJsonProtocol._

[Your code]

scala> val json = """{"value": "TEST"}""".parseJson
json: spray.json.JsValue = {"value":"TEST"}

scala> json.convertTo[MyTrait]
res1: MyTrait = MyCaseClass
person Christian    schedule 06.06.2014
comment
Неа. Все та же проблема. Если я сделаю еще один case a => println(a)... в моем выводе я получу ArrayBuffer("TEST") Может быть, что-то не так с моим тестом - person zmeda; 06.06.2014
comment
Это все еще не работает для меня. Я расширил пример с использованием типажа (как и в реальном случае использования) - person zmeda; 09.06.2014