-
Notifications
You must be signed in to change notification settings - Fork 547
Closed
Labels
Milestone
Description
问题描述
当一个类中包含了一个 value class 时,fastjson2 序列化为 json 的时候会给这个字段添加一个固定的后缀,即使我通过 JSONField 手动指定名称,仍然会携带该后缀,这样子序列化出来的 json 不方便其它地方解析。
在 fastjson2 解序列化时,却不会添加这个后缀,这导致 fastjson2 无法解序列化自己序列化的 json,这非常的不合理。
更严重的问题是,当 value class 内部是一个基础类型时,fastjson2 永远将 value class 当做基础类型处理,所以在反序列化遇到装箱时就会出现类似的错误:
Caused by: java.lang.IllegalArgumentException: argument type mismatch
at java.base/jdk.internal.reflect.DirectConstructorHandleAccessor.newInstance(DirectConstructorHandleAccessor.java:65)
at java.base/java.lang.reflect.Constructor.newInstanceWithCaller(Constructor.java:502)
at java.base/java.lang.reflect.Constructor.newInstance(Constructor.java:486)
... 32 common frames omitted
Caused by: java.lang.ClassCastException: Cannot cast java.lang.Integer to kotlin.jvm.internal.DefaultConstructorMarker
at java.base/java.lang.Class.cast(Class.java:4067)
at java.base/jdk.internal.reflect.DirectConstructorHandleAccessor.newInstance(DirectConstructorHandleAccessor.java:62)
... 35 common frames omitted
环境信息
- OS信息: macOS 15.1.1 (24B91) 2.6 GHz 六核Intel Core i7
- JDK信息: graalvm 21.0.5
- 版本信息:2.0.53
重现步骤
编写如下代码:
@JvmInline
value class Test(val a: Int)
data class Test2(
// @JSONField(name = "b")
val b: Test
)
fun main() {
println(Test(1).toJSONString())
println(JSON.parseObject("{\"a\":1}", Test::class.java))
println(Test2(Test(1)).toJSONString())
println(JSON.parseObject("{\"b-C9M8Yyk\":2}", Test2::class.java))
println(JSON.parseObject("{\"b\":2}", Test2::class.java))
}最终得到如下输出:
{"a":1}
Test(a=1)
{"b-C9M8Yyk":1} // 取消掉 JSONField 的注释后结果仍为这样
Test2(b=Test(a=0)) // 这两行的结果应该和序列化的行为保持一致,而不是两边使用两个命名规则
Test2(b=Test(a=2))