fastjson v 1.2.31 反序列化泛型转化莫名其妙的出现了其他类型

lxkprmvk  于 2021-11-27  发布在  Java
关注(0)|答案(1)|浏览(277)

远程接口返回数据
{"code":"0","data":true,"errStatckTrace":[],"flag":true,"fullErrStackTraceStr":"","serviceSucceed":true,"successMsg":"处理成功!"}
java对象为
/**
OutputDTO 类

**/

public class OutputDTO<T> implements Serializable {
    private boolean exceptionTransfer = false;
    private static final int MSG_SHOW_MAX_LENGTH = 1500;
    private static final int START_INDEX = 0;
    private static final long serialVersionUID = -8737311831553176997L;
    private boolean flag;
    private String errorMessage;
    private String successMsg;
    private T data;
    private String code;
    private List<String> errorStackTrace = new ArrayList();
    private List<String> warningInfoLs = new ArrayList();

    public OutputDTO() {
    }
}

/**
SoaTypeReference 类,封装了一层

**/

import com.alibaba.fastjson.TypeReference;
public class SoaTypeReference<T> extends TypeReference<T> {
    public SoaTypeReference() {
    }
}

反序列化操作代码为(没有写具体的泛型,因为客户端不需要使用到data对象)
Object object = JSON.parseObject(data, new SoaTypeReference<OutputDTO>(){});
该代码在单元测试不会出现错误,线上和stg不止一次的报如下的错误

Caused by: com.alibaba.fastjson.JSONException: syntax error, expect {, actual true, pos 19, fieldName data
at com.alibaba.fastjson.parser.deserializer.JavaBeanDeserializer.deserialze(JavaBeanDeserializer.java:367)
at com.alibaba.fastjson.parser.deserializer.JavaBeanDeserializer.parseRest(JavaBeanDeserializer.java:1010)
at com.alibaba.fastjson.parser.deserializer.**FastjsonASMDeserializer_4_MerchantDTO**.deserialze(Unknown Source)
at com.alibaba.fastjson.parser.deserializer.JavaBeanDeserializer.deserialze(JavaBeanDeserializer.java:208)
at com.alibaba.fastjson.parser.deserializer.DefaultFieldDeserializer.parseField(DefaultFieldDeserializer.java:71)
at com.alibaba.fastjson.parser.deserializer.JavaBeanDeserializer.deserialze(JavaBeanDeserializer.java:602)
at com.alibaba.fastjson.parser.deserializer.JavaBeanDeserializer.deserialze(JavaBeanDeserializer.java:212)
at com.alibaba.fastjson.parser.deserializer.JavaBeanDeserializer.deserialze(JavaBeanDeserializer.java:208)
at com.alibaba.fastjson.parser.DefaultJSONParser.parseObject(DefaultJSONParser.java:642)
at com.alibaba.fastjson.JSON.parseObject(JSON.java:350)
at com.alibaba.fastjson.JSON.parseObject(JSON.java:318)
at com.alibaba.fastjson.JSON.parseObject(JSON.java:232)
at com.odianyun.soa.client.business.AbstractSoaClient.decodeResult(AbstractSoaClient.java:132)
at com.odianyun.soa.client.business.AbstractSoaClient.call(AbstractSoaClient.java:282)
... 72 more

反序列化的过程的,data类型不知道为什么变成了MerchantDTO,这个类型在其他的反序列化操作可能会用到,但是该次反序列化操作肯定没有该类型(可以保证这一点,一开始看到这个错以为反序列化类型是OutputDTO <MerchantDTO>那报错理所应当,后来很多小组都反馈有这个问题,并且是在确认泛型没有填写的情况下报错的,单元测试不会重现)

为了不影响业务流程,最终把T 写成了String,不再报错
Object object = JSON.parseObject(data, new SoaTypeReference<OutputDTO<String>>(){});

1.怀疑是不是SoaTypeReference这个类有问题,封装一层以后由fastjson转成jsckson对外api没有任何变化
2.这个和@JSONType(asm = false) 应该没有任何关系吧。

问题描述如上,因为该处代码不止一处,并且分散在各个部门的代码里面,改了一个地方报错其他地方还是会出现,如果有统一的解决途径为好。

slmsl1lt

slmsl1lt1#

使用泛型如果嵌套太深,确实会出问题。
尽量把泛型类型控制到序列化对象本身or上层对象上。

相关问题