2016-05-18 12 views
0

は、私は2つのケースクラスを持って、読み込みテスト:プレイJSONは、再帰的には、NPE

import org.specs2.mutable.Specification 
import play.api.libs.json.{JsError, JsArray, Json} 

class NestedSpec extends Specification { 

    "Nested" should { 

    "jsonReads" in { 

     val personJson = Json.obj(
     "name" -> "alex", 
     "coWorkers" -> Json.arr(
      Json.obj(
      "person" -> Json.obj(
       "name" -> "jack", 
       "coWorkers" -> List.empty[String] 
      ), 
      "position": "developer" 
     ) 
     ) 
    ) 

     val res = personJson.validate[Person].asEither 

     res.left.map(err => println(Json.prettyPrint(JsError.toJson(err)))) 

     res.isRight must beTrue 

    } 

    } 

} 

しかし、そのテストはエラーで失敗します。

> testOnly nested.NestedSpec 
[info] NestedSpec 
[info] 
[info] Nested should 
[error] ! jsonReads 
[error] java.lang.NullPointerException: null (JsConstraints.scala:32) 
[error] play.api.libs.json.PathReads$$anonfun$at$1$$anonfun$apply$2.apply(JsConstraints.scala:32) 
[error] play.api.libs.json.PathReads$$anonfun$at$1$$anonfun$apply$2.apply(JsConstraints.scala:32) 
[error] play.api.libs.json.JsResult$class.flatMap(JsResult.scala:99) 
[error] play.api.libs.json.JsSuccess.flatMap(JsResult.scala:9) 
[error] play.api.libs.json.PathReads$$anonfun$at$1.apply(JsConstraints.scala:32) 
[error] play.api.libs.json.PathReads$$anonfun$at$1.apply(JsConstraints.scala:32) 
[error] play.api.libs.json.Reads$$anon$8.reads(Reads.scala:126) 
[error] play.api.libs.json.OFormat$$anon$2.reads(Format.scala:46) 
[error] play.api.libs.json.Reads$$anon$3$$anon$4.reads(Reads.scala:104) 
[error] play.api.libs.json.OFormat$$anon$2.reads(Format.scala:46) 
[error] play.api.libs.json.OFormat$$anon$5$$anonfun$inmap$1.apply(Format.scala:31) 
[error] play.api.libs.json.OFormat$$anon$5$$anonfun$inmap$1.apply(Format.scala:31) 
[error] play.api.libs.json.OFormat$$anon$1.reads(Format.scala:39) 
[error] play.api.libs.json.Json$.fromJson(Json.scala:125) 
[error] play.api.libs.json.LowPriorityDefaultReads$$anon$2$$anonfun$reads$1.apply(Reads.scala:168) 
[error] play.api.libs.json.LowPriorityDefaultReads$$anon$2$$anonfun$reads$1.apply(Reads.scala:167) 
[error] play.api.libs.json.LowPriorityDefaultReads$$anon$2.reads(Reads.scala:167) 
[error] play.api.libs.json.DefaultFormat$$anon$4.reads(Format.scala:82) 
[error] play.api.libs.json.PathReads$$anonfun$at$1$$anonfun$apply$2.apply(JsConstraints.scala:32) 
[error] play.api.libs.json.PathReads$$anonfun$at$1$$anonfun$apply$2.apply(JsConstraints.scala:32) 
[error] play.api.libs.json.JsResult$class.flatMap(JsResult.scala:99) 
[error] play.api.libs.json.JsSuccess.flatMap(JsResult.scala:9) 
[error] play.api.libs.json.PathReads$$anonfun$at$1.apply(JsConstraints.scala:32) 
[error] play.api.libs.json.PathReads$$anonfun$at$1.apply(JsConstraints.scala:32) 
[error] play.api.libs.json.Reads$$anon$8.reads(Reads.scala:126) 
[error] play.api.libs.json.OFormat$$anon$2.reads(Format.scala:46) 
[error] play.api.libs.json.Reads$$anon$3$$anon$4.reads(Reads.scala:104) 
[error] play.api.libs.json.OFormat$$anon$2.reads(Format.scala:46) 
[error] play.api.libs.json.OFormat$$anon$5$$anonfun$inmap$1.apply(Format.scala:31) 
[error] play.api.libs.json.OFormat$$anon$5$$anonfun$inmap$1.apply(Format.scala:31) 
[error] play.api.libs.json.OFormat$$anon$1.reads(Format.scala:39) 
[error] play.api.libs.json.JsValue$class.validate(JsValue.scala:18) 
[error] play.api.libs.json.JsObject.validate(JsValue.scala:76) 
[error] nested.NestedSpec$$anonfun$1$$anonfun$apply$2.apply(NestedSpec.scala:24) 
[error] nested.NestedSpec$$anonfun$1$$anonfun$apply$2.apply(NestedSpec.scala:10) 
[info] 
[info] 
[info] 
[info] Total for specification NestedSpec 
[info] Finished in 269 ms 
[info] 1 example, 0 failure, 1 error 
[info] 
[error] Error: Total 1, Failed 0, Errors 1, Passed 0 
[error] Error during tests: 
[error]   nested.NestedSpec 
[error] (test:testOnly) sbt.TestsFailedException: Tests unsuccessful 
[error] Total time: 1 s, completed May 18, 2016 12:25:16 PM 

私はそれがカリキュラムの依存関係のエラーのようなものだと仮定します。 CoWorkerはPersonのjsonReadを使用し、PersonはCoWorker jsonReadを使用します。この問題を解決してテストを実行することは可能ですか?

答えて

0

私はドキュメントで見つかった、lazyReadsを使用する必要があります。

再帰的な型の例モデルは を示すものではありません一つの特殊なケースは、読み込み、再帰的なタイプのために書き込みを処理する方法です。

case class User(name: String, friends: Seq[User]) 

implicit lazy val userReads: Reads[User] = (
    (__ \ "name").read[String] and 
    (__ \ "friends").lazyRead(Reads.seq[User](userReads)) 
)(User) 

implicit lazy val userWrites: Writes[User] = (
    (__ \ "name").write[String] and 
    (__ \ "friends").lazyWrite(Writes.seq[User](userWrites)) 
)(unlift(User.unapply)) 

https://www.playframework.com/documentation/2.5.x/ScalaJsonCombinators#recursive-types

: JsPathは、これを処理するために呼び出す名前による パラメータを取るlazyReadとlazyWrite方法を提供します