fastjson 处理 json转case class 时默认值不生效,怎么解决
时间: 2024-02-01 19:02:19 浏览: 85
如果你使用的是 Scala 2.11.x,那么默认值不生效是由于 fastjson 库在解析时不会调用 Scala 2.11.x 版本中的默认构造函数。这个问题可以通过实现自定义反序列化器来解决。以下是一个示例代码:
```scala
import com.alibaba.fastjson.{JSON, JSONObject}
import com.alibaba.fastjson.parser.deserializer.ObjectDeserializer
import scala.reflect.ClassTag
class CaseClassDeserializer[T: ClassTag] extends ObjectDeserializer {
override def deserialze(parser: com.alibaba.fastjson.parser.DefaultJSONParser,
`type`: scala.reflect.Type,
fieldName: Any): T = {
val cls = implicitly[ClassTag[T]].runtimeClass
val obj = cls.newInstance().asInstanceOf[T]
val jsonObj = parser.parseObject()
jsonObj.forEach((k, v) => {
val field = cls.getDeclaredField(k)
field.setAccessible(true)
field.set(obj, v)
})
obj
}
override def getFastMatchToken: Int = 0
}
object CaseClassDeserializer {
def apply[T: ClassTag]: CaseClassDeserializer[T] = new CaseClassDeserializer[T]
}
case class Person(name: String, age: Int = 18)
val json = "{\"name\":\"Alice\"}"
val person = JSON.parseObject(json, CaseClassDeserializer[Person].asInstanceOf[ObjectDeserializer])
println(person) // Person(Alice,18)
```
在这个示例代码中,我们实现了一个 `CaseClassDeserializer` 类,该类实现了 `ObjectDeserializer` 接口,并重写了 `deserialze` 方法。在 `deserialze` 方法中,我们首先通过 `implicitly[ClassTag[T]].runtimeClass` 获取到待解析类的 `Class` 对象,然后使用 `newInstance` 方法创建一个对象实例。接着,我们使用 fastjson 解析 JSON 对象,并遍历其中的键值对。对于每一个键值对,我们通过 `cls.getDeclaredField(k)` 获取到该字段在类中的 `Field` 对象,然后使用 `setAccessible` 方法将其设置为可访问状态,并最终使用 `field.set(obj, v)` 将键值对中的值赋值给该字段。最后,我们将解析出的对象返回。
在代码的最后,我们使用 `JSON.parseObject` 方法解析 JSON 字符串,并将 `CaseClassDeserializer[Person]` 作为反序列化器传入该方法。这里需要使用 `asInstanceOf[ObjectDeserializer]` 将 `CaseClassDeserializer[Person]` 转换为 `ObjectDeserializer` 类型。最终,我们可以得到正确的解析结果,即 `Person(Alice,18)`。
阅读全文