fix:issues3170,解决JSONField的DisableCircularReferenceDetect不生效问题 (#3198)

* fix:issues3170,解决JSONField的DisableCircularReferenceDetect不生效问题

* refactor

* add window ci

* windows-2019

* windows-2022

* macos-11

* revert

---------

Co-authored-by: changyi.ccy <changyi.ccy@alibaba-inc.com>
This commit is contained in:
Shaojin Wen 2024-12-08 19:11:05 +08:00 committed by GitHub
parent f3037a49f3
commit 86df010449
No known key found for this signature in database
GPG Key ID: B5690EEEBB952194
4 changed files with 125 additions and 2 deletions

View File

@ -1,5 +1,6 @@
package com.alibaba.fastjson2;
import com.alibaba.fastjson2.codec.FieldInfo;
import com.alibaba.fastjson2.filter.*;
import com.alibaba.fastjson2.util.IOUtils;
import com.alibaba.fastjson2.util.TypeUtils;
@ -245,7 +246,8 @@ public abstract class JSONWriter
}
public final boolean isRefDetect() {
return (context.features & ReferenceDetection.mask) != 0;
return (context.features & ReferenceDetection.mask) != 0
&& (context.features & FieldInfo.DISABLE_REFERENCE_DETECT) == 0;
}
public final boolean isUseSingleQuotes() {
@ -254,6 +256,7 @@ public abstract class JSONWriter
public final boolean isRefDetect(Object object) {
return (context.features & ReferenceDetection.mask) != 0
&& (context.features & FieldInfo.DISABLE_REFERENCE_DETECT) == 0
&& object != null
&& !ObjectWriterProvider.isNotReferenceDetect(object.getClass());
}

View File

@ -241,7 +241,16 @@ public class FieldWriterObject<T>
@Override
public boolean write(JSONWriter jsonWriter, T object) {
long features = this.features | jsonWriter.getFeatures();
JSONWriter.Context context = jsonWriter.context;
long oldFeatures = context.getFeatures();
context.setFeatures(this.features | oldFeatures);
boolean result = writeInternal(jsonWriter, object);
context.setFeatures(oldFeatures);
return result;
}
private boolean writeInternal(JSONWriter jsonWriter, T object) {
long features = jsonWriter.getFeatures();
if (!fieldClassSerializable && (features & JSONWriter.Feature.IgnoreNoneSerializable.mask) != 0) {
return false;

View File

@ -726,6 +726,9 @@ public class ObjectWriterBaseModule
case "WriteBigDecimalAsPlain":
fieldInfo.features |= JSONWriter.Feature.WriteBigDecimalAsPlain.mask;
break;
case "DisableCircularReferenceDetect":
fieldInfo.features |= FieldInfo.DISABLE_REFERENCE_DETECT;
break;
default:
break;
}

View File

@ -0,0 +1,108 @@
package com.alibaba.fastjson2.issues_3100;
import com.alibaba.fastjson.JSON;
import com.alibaba.fastjson.annotation.JSONField;
import com.alibaba.fastjson.serializer.SerializeConfig;
import com.alibaba.fastjson.serializer.SerializerFeature;
import com.alibaba.fastjson.serializer.ToStringSerializer;
import com.alibaba.fastjson.serializer.ValueFilter;
import org.junit.Assert;
import org.junit.jupiter.api.Test;
import java.util.ArrayList;
import java.util.Date;
import java.util.List;
import java.util.Objects;
/**
* Issue3170测试类
* @author changyi.ccy
*/
public class Issue3170Test {
/**
* 测试: Issue3170
*/
@Test
public void testIssue3170() {
IntegerToStringFilter integerToStringFilter = new IntegerToStringFilter();
SerializeConfig stringSerializeConfig = new SerializeConfig();
stringSerializeConfig.put(Integer.class, ToStringSerializer.instance);
stringSerializeConfig.put(Long.class, ToStringSerializer.instance);
People one = new People(10, "aaa", 10000000L);
People two = new People(40, "bbb", 0L);
two.setSon(one);
List<People> peopleList = new ArrayList<>();
peopleList.add(one);
peopleList.add(two);
String jsonText = "[{\"age\":\"10\",\"hairNums\":\"10000000\",\"name\":\"aaa\"},"
+ "{\"age\":\"40\",\"hairNums\":\"0\",\"name\":\"bbb\",\"son\":"
+ "{\"age\":\"10\",\"hairNums\":\"10000000\",\"name\":\"aaa\"}}]";
Assert.assertEquals("JSON文本不一致", jsonText, JSON.toJSONString(peopleList,
stringSerializeConfig, integerToStringFilter));
}
/**
* People类
*/
public static class People {
private Long hairNums;
private String name;
private Integer age;
@JSONField(serialzeFeatures = SerializerFeature.DisableCircularReferenceDetect)
private People son;
@JSONField(format = "yyyy-MM-dd")
private Date applyStartTime;
public People(Integer age, String name, Long hairNums) {
this.age = age;
this.name = name;
this.hairNums = hairNums;
}
public Integer getAge() {
return age;
}
public String getName() {
return name;
}
public Long getHairNums() {
return hairNums;
}
public People getSon() {
return son;
}
public void setSon(People son) {
this.son = son;
}
public Date getApplyStartTime() {
return applyStartTime;
}
public void setApplyStartTime(Date applyStartTime) {
this.applyStartTime = applyStartTime;
}
}
/**
* 整数转字符串过滤器类
*/
public static class IntegerToStringFilter
implements ValueFilter {
@Override
public Object process(Object o, String s, Object v) {
if (Objects.isNull(v)) {
return null;
}
if (v instanceof Integer) {
return v.toString();
}
return v;
}
}
}