back port from 2.0.45

This commit is contained in:
shaojin.wensj 2024-01-07 10:09:09 +08:00
parent 427c00e9ff
commit 47335c5f57
12 changed files with 248 additions and 13 deletions

View File

@ -3571,12 +3571,12 @@ public interface JSON {
ObjectWriter<?> objectWriter = writeContext.getObjectWriter(valueClass, valueClass);
if (objectWriter instanceof ObjectWriterAdapter && !writeContext.isEnabled(JSONWriter.Feature.ReferenceDetection)) {
ObjectWriterAdapter objectWriterAdapter = (ObjectWriterAdapter) objectWriter;
return objectWriterAdapter.toJSONObject(object);
return objectWriterAdapter.toJSONObject(object, writeContext.features);
}
String str;
try (JSONWriter writer = JSONWriter.of(writeContext)) {
objectWriter.write(writer, object, null, null, 0);
objectWriter.write(writer, object, null, null, writeContext.features);
str = writer.toString();
} catch (NullPointerException | NumberFormatException ex) {
throw new JSONException("toJSONString error", ex);

View File

@ -217,7 +217,11 @@ public abstract class JSONReader
if (index == list.size()) {
list.add(fieldValue);
} else {
list.set(index, fieldValue);
if (index < list.size() && list.get(index) == null) {
list.set(index, fieldValue);
} else {
list.add(index, fieldValue);
}
}
continue;
}
@ -1675,6 +1679,9 @@ public abstract class JSONReader
if ((contextFeatures & Feature.NonStringKeyAsString.mask) != 0) {
name = name.toString();
}
if (comma) {
throw new JSONException(info("syntax error, illegal key-value"));
}
} else {
if ((contextFeatures & Feature.AllowUnQuotedFieldNames.mask) != 0) {
name = readFieldNameUnquote();
@ -2146,6 +2153,8 @@ public abstract class JSONReader
case '{':
if (context.autoTypeBeforeHandler != null || (context.features & Feature.SupportAutoType.mask) != 0) {
val = ObjectReaderImplObject.INSTANCE.readObject(this, null, null, 0);
} else if (isReference()) {
val = JSONPath.of(readReference());
} else {
val = readObject();
}
@ -2195,11 +2204,11 @@ public abstract class JSONReader
list = new JSONArray();
}
list.add(first);
list.add(second);
list.add(val);
add(list, 0, first);
add(list, 1, second);
add(list, i, val);
} else {
list.add(val);
add(list, i, val);
}
}
@ -2215,10 +2224,10 @@ public abstract class JSONReader
}
if (i == 1) {
list.add(first);
add(list, 0, first);
} else if (i == 2) {
list.add(first);
list.add(second);
add(list, 0, first);
add(list, 1, second);
}
}
@ -2231,6 +2240,15 @@ public abstract class JSONReader
return list;
}
private void add(List<Object> list, int i, Object val) {
if (val instanceof JSONPath) {
addResolveTask(list, i, (JSONPath) val);
list.add(null);
} else {
list.add(val);
}
}
public final BigInteger getBigInteger() {
Number number = getNumber();

View File

@ -228,7 +228,7 @@ class JSONReaderUTF16
ch = chars[offset];
}
if (ch != quote) {
if (ch != quote || (offset + 1 < end && chars[offset + 1] == '#')) {
return false;
}
@ -4708,6 +4708,9 @@ class JSONReaderUTF16
int numDigits = scale > 0 ? offset - 2 - numStart : offset - 1 - numStart;
if (numDigits > 38) {
if (negative) {
numStart--;
}
valueType = JSON_TYPE_BIG_DEC;
stringValue = new String(chars, numStart, offset - 1 - numStart);
} else {

View File

@ -4635,6 +4635,9 @@ class JSONReaderUTF8
int numStart = negative ? start : start - 1;
int numDigits = scale > 0 ? offset - 2 - numStart : offset - 1 - numStart;
if (numDigits > 38) {
if (negative) {
numStart--;
}
valueType = JSON_TYPE_BIG_DEC;
stringValue = new String(bytes, numStart, offset - 1 - numStart);
} else {
@ -6568,7 +6571,7 @@ class JSONReaderUTF8
ch = bytes[offset];
}
if (ch != quote) {
if (ch != quote || (offset + 1 < end && bytes[offset + 1] == '#')) {
return false;
}

View File

@ -149,7 +149,7 @@ public abstract class ObjectReaderBean<T>
String typeName = jsonReader.getString();
filterClass = autoTypeFilter.apply(typeName, expectClass, features);
if (!expectClass.isAssignableFrom(filterClass)) {
if (filterClass != null && !expectClass.isAssignableFrom(filterClass)) {
if ((jsonReader.features(features) & IgnoreAutoTypeNotMatch.mask) == 0) {
throw new JSONException("type not match. " + typeName + " -> " + expectClass.getName());
}

View File

@ -36,6 +36,9 @@ public final class ObjectReaderImplEnum
) {
this.enumClass = enumClass;
this.createMethod = createMethod;
if (valueField instanceof AccessibleObject) {
((AccessibleObject) valueField).setAccessible(true);
}
this.valueField = valueField;
Type valueFieldType = null;
if (valueField instanceof Field) {

View File

@ -0,0 +1,25 @@
package com.alibaba.fastjson2.issues_2100;
import com.alibaba.fastjson2.JSON;
import com.alibaba.fastjson2.JSONObject;
import com.alibaba.fastjson2.JSONReader;
import org.junit.jupiter.api.Test;
import java.nio.charset.StandardCharsets;
import java.util.Map;
import static org.junit.jupiter.api.Assertions.assertEquals;
public class Issue2128 {
@Test
public void testWithUTF8() {
String str = "{\"amt\":-22.1400000000000005684341886080801486968994140625}";
assertEquals(str, JSON.toJSONString(JSONReader.of(str.getBytes(StandardCharsets.UTF_8)).readObject()));
}
@Test
public void testWithUTF16() {
String str = "{\"amt\":-22.1400000000000005684341886080801486968994140625}";
assertEquals(str, JSON.toJSONString(JSONObject.parseObject(str, Map.class)));
}
}

View File

@ -0,0 +1,19 @@
package com.alibaba.fastjson2.issues_2100;
import com.alibaba.fastjson2.JSON;
import com.alibaba.fastjson2.JSONObject;
import org.junit.jupiter.api.Test;
import static org.junit.jupiter.api.Assertions.assertSame;
public class Issue2140 {
@Test
public void test() {
String jsonString = "{\"ProjectAttr\":[{\"ZYAttr\":[{\"ProjectAttrID\":\"4777014153688645650\",\"BidNodeID\":1,\"AttrValue\":\"3.0\"}]}],\"ZYAttr\":[{\"$ref\":\"$.ProjectAttr[0].ZYAttr[0]\"}]}";
JSONObject doc = JSON.parseObject(jsonString);
assertSame(
doc.getJSONArray("ProjectAttr").getJSONObject(0).getJSONArray("ZYAttr").get(0),
doc.getJSONArray("ZYAttr").get(0)
);
}
}

View File

@ -0,0 +1,38 @@
package com.alibaba.fastjson2.issues_2100;
import com.alibaba.fastjson2.JSON;
import com.alibaba.fastjson2.JSONWriter;
import lombok.Data;
import org.junit.jupiter.api.Test;
public class Issue2144 {
@Test
public void test() {
final A a = new A();
B b = a.buildB();
Object json = JSON.toJSON(b);
System.out.println(JSON.toJSONString(json, JSONWriter.Feature.ReferenceDetection));
}
@Data
public class A {
public B buildB() {
return buildB(new B());
}
public <T extends B> T buildB(T b) {
return b;
}
}
@Data
public class B {
public B buildB() {
return buildB(new B());
}
public <T extends B> T buildB(T b) {
return b;
}
}
}

View File

@ -0,0 +1,56 @@
package com.alibaba.fastjson2.issues_2100;
import com.alibaba.fastjson2.JSON;
import lombok.Getter;
import lombok.Setter;
import org.junit.jupiter.api.Test;
import java.io.Serializable;
import java.util.Date;
import static org.junit.jupiter.api.Assertions.assertEquals;
public class Issue2153 {
@Test
public void test() {
String str = "{\"addTime\":1703124696338,\"updateTime\":1703124696338,\"id\":7}";
User user = JSON.parseObject(str, User.class);
assertEquals("{\"id\":7}", JSON.toJSONString(user));
}
public interface ID
extends Serializable {
Serializable getId();
}
public interface Bean<K extends Serializable>
extends ID {
@Override
K getId();
void setId(K id);
}
@Getter
@Setter
public abstract static class BaseEntity
implements Bean<Long> {
Long id;
}
@Getter
@Setter
public abstract static class TimeBaseEntity
extends BaseEntity {
Date addTime;
Date updateTime;
}
@Getter
@Setter
public static class User
extends BaseEntity {
String addr;
Long a, b, c, d, e, f, g;
}
}

View File

@ -0,0 +1,54 @@
package com.alibaba.fastjson2.issues_2100;
import com.alibaba.fastjson2.JSON;
import com.alibaba.fastjson2.annotation.JSONField;
import org.junit.jupiter.api.Test;
import static org.junit.jupiter.api.Assertions.assertEquals;
/**
* @author 张治保
* @since 2024/1/6
*/
public class Issue2154 {
// failure
@Test
public void intEnumDeserialize1() {
Bean1 bean1 = JSON.parseObject("{\"type\":102}", Bean1.class);
assertEquals(102, bean1.type.getCode());
}
// success
@Test
public void intEnumDeserialize2() {
// add this
{
Bean1 bean = new Bean1();
bean.type = Type.S;
JSON.toJSONString(bean);
}
intEnumDeserialize1();
}
class Bean1 {
public Type type;
}
enum Type {
X(101),
M(102),
S(103);
private final int code;
Type(int code) {
this.code = code;
}
@JSONField(value = true)
public int getCode() {
return code;
}
}
}

View File

@ -0,0 +1,16 @@
package com.alibaba.fastjson2.issues_2100;
import com.alibaba.fastjson2.JSONException;
import com.alibaba.fastjson2.JSONObject;
import org.junit.jupiter.api.Test;
import static org.junit.jupiter.api.Assertions.assertThrows;
public class Issue2155 {
@Test
public void test() {
assertThrows(
JSONException.class,
() -> JSONObject.parse("{1,2}"));
}
}