2

I am new to scala and trying to map my json to an object. I have found jackson-scala-module but unable to figure out how to use it. A small example might be of help.

val json = { "_id" : "jzcyluvhqilqrocq" , "DP-Name" : "Sumit Agarwal" , "DP-Age" : "15" , "DP-height" : "115" , "DP-weight" : "68"}

I want to map this to Person(name: String, age: Int, height: Int, weight: Int)

Till now I have been trying using this:

import com.fasterxml.jackson.databind.ObjectMapper

Val mapper = = new ObjectMapper();    
val data = mapper.readValue(json, classOf[Person])

Dependency I am using:

"com.fasterxml.jackson.module" % "jackson-module-scala_2.11" % "2.8.4"

Am I missing on anything?

EDIT:

[error] (run-main-4) com.fasterxml.jackson.databind.JsonMappingException: Can not construct instance of models.Person: no suitable constructor found, can not deserialize from Object value (missing default constructor or creator, or perhaps need to add/enable type information?)
Sumit Agarwal
  • 4,091
  • 8
  • 33
  • 49
  • 1
    I would recommend https://circe.github.io/circe/ instead. Doesn't use reflection. – Reactormonk Jan 16 '17 at 11:50
  • The error message suggests that you're missing the default constructor (empty). Jackson works by first creating an empty object, and then it looks at all the attributes in the json struture, and iteratively sets them in the result object. The downside is that you also have to provide setters for each of the object's properties. :( But as Reactormock suggested, I'd also recommend using circe since this provides a more idiomatic approach to deserialisation (in scala at least). – irundaia Jan 16 '17 at 12:09
  • any solution/suggestion/way-around with scala jackson itself? – Sumit Agarwal Jan 16 '17 at 12:15

2 Answers2

10

In order to make it work, you need to register DefaultScalaModule with the object mapper:

val mapper = new ObjectMapper()
mapper.registerModule(DefaultScalaModule)

Also, you need to update your case class and provide Jackson with property name to field name binding:

case class Person(@JsonProperty("DP-Name") name: String, 
                  @JsonProperty("DP-Age") age: Int, 
                  @JsonProperty("DP-height") height: Int, 
                  @JsonProperty("DP-weight") weight: Int)
1
  • The problem is you have not registered DefaultScalaModule with ObjectMapper.
lazy val mapper = new ObjectMapper() with ScalaObjectMapper
 mapper.registerModule(DefaultScalaModule)
  • Please find a working and detailed answer which I have provided using generics here.
Keshav Lodhi
  • 2,641
  • 2
  • 17
  • 23