We all know that generic types are subject to type erasure in Java and Scala. But we ran into a strange problem in Scala using Jackson and the Scala Jackson module.
I created a little test to show the problem.
import com.fasterxml.jackson.databind.ObjectMapper import com.fasterxml.jackson.module.scala.DefaultScalaModule object GenericTest { case class TestWithInt(id: Option[Int]) case class TestWithInteger(id: Option[Integer]) def main(args: Array[String]) { val mapper = new ObjectMapper() mapper.registerModule(DefaultScalaModule) // Test with scala Int val test = mapper.readValue[TestWithInt]("""{ "id" : 5 }""", classOf[TestWithInt]) print("Test 1: ") println(test.id.get + 1) val test2 = mapper.readValue[TestWithInt]("""{ "id" : "5" }""", classOf[TestWithInt]) print("Test 2: ") try { println(test2.id.get + 1) } catch { case e: ClassCastException => println(e.getMessage) } // Test with java.lang.Integer val test3 = mapper.readValue[TestWithInteger]("""{ "id" : 5 }""", classOf[TestWithInteger]) print("Test 3: ") println(test3.id.get + 1) val test4 = mapper.readValue[TestWithInteger]("""{ "id" : "5" }""", classOf[TestWithInteger]) print("Test 4: ") println(test4.id.get + 1) } }
The conclusion above:
Test 1: 6 Test 2: java.lang.String cannot be cast to java.lang.Integer Test 3: 6 Test 4: 6
Where does this other behavior come from? Generic Type Erasure, Jackson, Jackson Scala Module?
source share