faster2b
faster2b

Reputation: 672

Create complex Json Object

I need to create a json object, i use play-json lib for Scala.

I have this code:

import play.api.libs.json
import play.api.libs.json._

object Start {
    def main(args: Array[String])
    {
        val GraphDbJson= Json.obj("name"->"father","nodeid"->1,"children"->Json.arr(func1))
        println(Json.prettyPrint(GraphDbJson))
    }

    def func1():JsValue=
    {
        var JObjChildrenNodes=Seq[JsValue]()

        JObjChildrenNodes :+ Json.obj("name"->"child1","nodeid"->2,"children"->Json.arr())
        JObjChildrenNodes :+ Json.obj("name"->"child2","nodeid"->3,"children"->Json.arr())     
        Json.toJson(JObjChildrenNodes)
    }
}

and the output is:

{
    "name" : "father",
    "nodeid" : 1,
    "children" : [ [ ] ]
}

how can I pass an json array ? Why the return value of func1 is empty?

Thank you in advance

Upvotes: 2

Views: 1356

Answers (1)

senia
senia

Reputation: 38045

You should replace :+ with +:= (since the default implementation of Seq is List you should not use :+=).

Seq is immutable. With :+ you are creating a new Seq.

So you should use nodes = nodes :+ Json.obj(...) instead of nodes :+ Json.obj(...), or just nodes :+= Json.obj(...) (see the last part of this answer).

You could use mutable collection like mutable.Seq with += operation: nodes += Json.obj(...).

I would prefer to create a collection this way:

nodes = Seq(
  Json.obj(...),
  Json.obj(...)
)

Note that default implementation of Seq is List and append (:+) operation on List is very inefficient - you should use prepend - +: and +:=.

Alternative solution: there is Json.writes (and Json.reads) in Play, so you could create a class and convert it to JSON this way:

case class MyNode(name: String, nodeid: Int, children: Seq[MyNode] = Nil)
implicit lazy val myNodeWrites = Json.writes[MyNode]

val myNode = MyNode("father", 1, MyNode("child1", 2) :: MyNode("child2", 3) :: Nil)
val graphDbJson = Json.toJson(myNode)
Json.prettyPrint(graphDbJson)
// {
//   "name" : "father",
//   "nodeid" : 1,
//   "children" : [ {
//     "name" : "child1",
//     "nodeid" : 2,
//     "children" : [ ]
//   }, {
//     "name" : "child2",
//     "nodeid" : 3,
//     "children" : [ ]
//   } ]
// }

Also: there is a error in your code: you should replace Json.arr(func1) with func1: Json.arr(func1) creates an array of arrays, since func1 already returns a json array.

Upvotes: 2

Related Questions