score:0

Accepted answer

So, the solution I've come up with is no good for performance intensive code, however it presents a clean interface for mapping.

object ThingReads {
  def reads(source:JsValue) = {
    val names:Seq[String] = (source \ "attributes" \\ "name").map(_.as[String])
    val values:Seq[JsValue] = source \ "attributes" \\ "values"
    val read = reads[TheThing] = (
      ( __ \ "first")(0).as[String] and
      ( __ \ "second").as[List[String]]
    )(TheThing.apply _)
    JsObject(names.zip(values)).as[TheThing](read)
  }
}

The major negatives being that you're required to iterate the json tree twice two build the "nicer form" json, then again when you extract your values.

Also if your key-value pair collection (attributes in this case) has a lot of irrelevant data in it, you're paying the price for transforming that data along with the bits you want to extract.

I'm going to accept this answer as it solves the problem, but I'll keep coming back to see if someone can provide a superior solution (I'm confident there's one out there and I'd love to learn it)


Related Query

More Query from same tag