-
Notifications
You must be signed in to change notification settings - Fork 546
Closed
Labels
Milestone
Description
问题描述
fastjson2 2.0.56 使用 JSON.toJSONString 出现字段丢失,打印的字符串里出现了字段丢失值为空的情况
测试发现,如果单独运行不会有问题,一旦另外一行JSON.toJSONString先运行了就会出现此情况
示例代码为了测试专门写的 demo,实际在接口的 service 层出现此问题,A单独调用时没有问题,一旦B接口先调用了A 接口就会百分百出现此问题导致业务报错
实测使用 jackson 没有此问题
环境信息
- OS信息: [e.g.:arm MacOS 15.7 & amd Ubuntu 22]
- JDK信息: [e.g.:Openjdk 17]
- 版本信息:[e.g.:Fastjson2 2.0.56]
重现步骤
- 运行示例代码 main 方法
import com.alibaba.fastjson2.JSON;
import lombok.Getter;
import lombok.Setter;
import java.util.ArrayList;
import java.util.Collections;
import java.util.List;
public class FastJson2Test {
public static void main(String[] args) {
SonInDto1 sonInDto1 = new SonInDto1("type.xxxxx1", "xxxxxx1", new SonInDto1.Data("张三"));
SonInDto2 sonInDto2 = new SonInDto2("type.xxxxx2", "xxxxxx2", new SonInDto2.Data("风格"));
System.out.println("sonInDto2: " + JSON.toJSONString(sonInDto2.buildWsRequest()));
System.out.println("sonInDto1: " + JSON.toJSONString(sonInDto1.buildWsRequest()));
}
@Getter
@Setter
public static abstract class BaseInDto {
protected String type;
protected String traceId;
@lombok.Data
public static class Data {
protected String query;
}
public abstract BaseInDto.Data getData();
public OutDto buildWsRequest() {
String[] tp = this.type.split("\\.");
String method = tp[0];
String subMethod = tp[1];
OutDto inDto = new OutDto();
inDto.setMethod(method);
inDto.setSubMethod(subMethod);
OutDto.Input input = new OutDto.Input();
input.setType("text");
input.setData(this.getData().getQuery());
inDto.setInputs(new ArrayList<>(List.of(input)));
return inDto;
}
}
@Getter
@Setter
public static class SonInDto1 extends BaseInDto {
protected SonInDto1.Data data;
public SonInDto1(String type, String traceId, SonInDto1.Data data) {
this.type = type;
this.traceId = traceId;
this.data = data;
}
@Getter
@Setter
public static class Data extends BaseInDto.Data {
protected String name;
public Data(String name) {
this.name = name;
}
}
@Getter
@Setter
public static class Extension extends OutDto.Extension {
private SonInDto1.Data musicInfo;
}
@Override
public OutDto buildWsRequest() {
OutDto inDto = super.buildWsRequest();
SonInDto1.Extension extension = new SonInDto1.Extension();
this.data.setQuery(null);
extension.setMusicInfo(this.data);
inDto.setExtension(extension);
inDto.setInputs(Collections.EMPTY_LIST);
return inDto;
}
}
@Getter
@Setter
public static class SonInDto2 extends BaseInDto {
protected SonInDto2.Data data;
public SonInDto2(String type, String traceId, SonInDto2.Data data) {
this.type = type;
this.traceId = traceId;
this.data = data;
}
@Getter
@Setter
public static class Data extends BaseInDto.Data {
protected String style;
public Data(String style) {
this.style = style;
}
}
@Override
public OutDto buildWsRequest() {
OutDto inDto = super.buildWsRequest();
OutDto.Extension extension = new OutDto.Extension();
extension.setStyle(this.data.style);
inDto.setExtension(extension);
return inDto;
}
}
@Getter
@Setter
public static class OutDto {
private String method;
private String subMethod;
private List<OutDto.Input> inputs;
private OutDto.Extension extension;
@Getter
@Setter
public static class Input {
protected String type;
protected String data;
}
@Getter
@Setter
public static class Extension {
protected String style;
protected List<Object> history;
protected String[] existingMusicIds;
}
}
}期待的正确结果
正确结果:sonInDto1: {"extension":{"musicInfo":{"name":"张三"}},"inputs":[],"method":"type","subMethod":"xxxxx1"}
实际输出为错误的:sonInDto1: {"extension":{},"inputs":[],"method":"type","subMethod":"xxxxx1"}
相关日志输出
sonInDto2: {"extension":{"style":"风格"},"inputs":[{"type":"text"}],"method":"type","subMethod":"xxxxx2"}
sonInDto1: {"extension":{},"inputs":[],"method":"type","subMethod":"xxxxx1"}
附加信息
当示例代码里的 System.out.println("sonInDto2和 System.out.println("sonInDto1 位置对调结果就是正确的
