Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

[BUG] testParseObjectWithImmutableCollectionField #2532

Closed
stc-W opened this issue May 7, 2024 · 6 comments
Closed

[BUG] testParseObjectWithImmutableCollectionField #2532

stc-W opened this issue May 7, 2024 · 6 comments
Labels
bug Something isn't working fixed
Milestone

Comments

@stc-W
Copy link

stc-W commented May 7, 2024

问题描述

简要描述您碰到的问题。
序列化Immutable的collection类直接crash

环境信息

请填写以下信息:

  • OS信息: [Ubuntu 22.04.3 LTS]
  • JDK信息: [openjdk 11.0.22 2024-01-16]
  • 版本信息:[Fastjson 2.0.49 兼容1.x.x]

重现步骤

Test case

import com.alibaba.fastjson.JSON;
import com.alibaba.fastjson.parser.Feature;
import com.alibaba.fastjson.parser.ParserConfig;
import org.junit.Test;

import java.io.ByteArrayInputStream;
import java.io.IOException;
import java.io.InputStream;
import java.nio.charset.StandardCharsets;
import java.util.ArrayList;
import java.util.Arrays;
import java.util.Collection;
import java.util.Collections;

import static org.junit.Assert.assertEquals;

public class Test512 {

    @Test
    public void testParseObjectWithImmutableCollectionField() {
        String jsonString = "{\"collectionField\": [1, 2, 3]}";

        class ImmutableCollectionExample {
            private final Collection<Integer> collectionField;

            public ImmutableCollectionExample(Collection<Integer> collectionField) {
                this.collectionField = Collections.unmodifiableCollection(new ArrayList<>(collectionField));
            }

            public Collection<Integer> getCollectionField() {
                return collectionField;
            }
        }

        try {
            InputStream inputStream = new ByteArrayInputStream(jsonString.getBytes(StandardCharsets.UTF_8));
            ImmutableCollectionExample result = JSON.parseObject(inputStream, StandardCharsets.UTF_8,
                    ImmutableCollectionExample.class, new ParserConfig(), Feature.SupportArrayToBean, Feature.DisableCircularReferenceDetect);

            assertEquals(Arrays.asList(1, 2, 3), new ArrayList<>(result.getCollectionField()));
        } catch (IOException e) {
            // Handle or log the exception
        }
    }
}

期待的正确结果

希望能够正常反序列化

相关日志输出

*java.lang.UnsupportedOperationException
at java.base/java.util.Collections$UnmodifiableCollection.add(Collections.java:1067)
at com.alibaba.fastjson2.reader.FieldReaderCollectionMethodReadOnly.accept(FieldReaderCollectionMethodReadOnly.java:93)
at com.alibaba.fastjson2.reader.ObjectReaderNoneDefaultConstructor.readObject(ObjectReaderNoneDefaultConstructor.java:356)
at com.alibaba.fastjson.JSON.parseObject(JSON.java:666)
at com.alibaba.fastjson.JSON.parseObject(JSON.java:687)
at Test512.testParseObjectWithImmutableCollectionField(Test512.java:37)
at java.base/jdk.internal.reflect.DirectMethodHandleAccessor.invoke(DirectMethodHandleAccessor.java:104)
at java.base/java.lang.reflect.Method.invoke(Method.java:578)
at org.junit.runners.model.FrameworkMethod$1.runReflectiveCall(FrameworkMethod.java:59)
at org.junit.internal.runners.model.ReflectiveCallable.run(ReflectiveCallable.java:12)
at org.junit.runners.model.FrameworkMethod.invokeExplosively(FrameworkMethod.java:56)
at org.junit.internal.runners.statements.InvokeMethod.evaluate(InvokeMethod.java:17)
at org.junit.runners.ParentRunner$3.evaluate(ParentRunner.java:306)
at org.junit.runners.BlockJUnit4ClassRunner$1.evaluate(BlockJUnit4ClassRunner.java:100)
at org.junit.runners.ParentRunner.runLeaf(ParentRunner.java:366)
at org.junit.runners.BlockJUnit4ClassRunner.runChild(BlockJUnit4ClassRunner.java:103)
at org.junit.runners.BlockJUnit4ClassRunner.runChild(BlockJUnit4ClassRunner.java:63)
at org.junit.runners.ParentRunner$4.run(ParentRunner.java:331)
at org.junit.runners.ParentRunner$1.schedule(ParentRunner.java:79)
at org.junit.runners.ParentRunner.runChildren(ParentRunner.java:329)
at org.junit.runners.ParentRunner.access$100(ParentRunner.java:66)
at org.junit.runners.ParentRunner$2.evaluate(ParentRunner.java:293)
at org.junit.runners.ParentRunner$3.evaluate(ParentRunner.java:306)
at org.junit.runners.ParentRunner.run(ParentRunner.java:413)
at org.junit.runner.JUnitCore.run(JUnitCore.java:137)
at com.intellij.junit4.JUnit4IdeaTestRunner.startRunnerWithArgs(JUnit4IdeaTestRunner.java:69)
at com.intellij.rt.junit.IdeaTestRunner$Repeater$1.execute(IdeaTestRunner.java:38)
at com.intellij.rt.execution.junit.TestsRepeater.repeat(TestsRepeater.java:11)
at com.intellij.rt.junit.IdeaTestRunner$Repeater.startRunnerWithArgs(IdeaTestRunner.java:35)
at com.intellij.rt.junit.JUnitStarter.prepareStreamsAndStart(JUnitStarter.java:232)
at com.intellij.rt.junit.JUnitStarter.main(JUnitStarter.java:55)
*

@stc-W stc-W added the bug Something isn't working label May 7, 2024
@eahau
Copy link

eahau commented May 7, 2024

看异常的堆栈,应该是该集合是只读不可写的,所以你可以换成别的可写的集合。

@stc-W
Copy link
Author

stc-W commented May 7, 2024

感觉和fastjson初始化的方法有关系,如果是直接把填好值的数组给到类的构造器就可以,fastjson貌似是先构造数组然后向数组内填值所以遇到不可以改变的集合就会报错,感觉这种情况有时候会碰到,就是有时候我需要的就是一个初始化时就确定好不变的集合

@eahau
Copy link

eahau commented May 7, 2024

感觉和fastjson初始化的方法有关系,如果是直接把填好值的数组给到类的构造器就可以,fastjson貌似是先构造数组然后向数组内填值所以遇到不可以改变的集合就会报错,感觉这种情况有时候会碰到,就是有时候我需要的就是一个初始化时就确定好不变的集合

你的想法是好的。但是我还是建议你先在 getter 方法处返回为不可变集合,先解决眼下的问题。

@wenshao
Copy link
Member

wenshao commented May 9, 2024

https://oss.sonatype.org/content/repositories/snapshots/com/alibaba/fastjson2/fastjson2/2.0.50-SNAPSHOT/
问题已修复,请帮忙用2.0.50-SNAPSHOT版本验证,2.0.50版本预计在5月12日前发布

@wenshao wenshao added this to the 2.0.50 milestone May 9, 2024
@wenshao wenshao added the fixed label May 9, 2024
@stc-W
Copy link
Author

stc-W commented May 9, 2024

https://oss.sonatype.org/content/repositories/snapshots/com/alibaba/fastjson2/fastjson2/2.0.50-SNAPSHOT/ 问题已修复,请帮忙用2.0.50-SNAPSHOT版本验证,2.0.50版本预计在5月12日前发布

经过检验可以顺利反序列化,辛苦wenshao

@wenshao
Copy link
Member

wenshao commented May 12, 2024

https://github.com/alibaba/fastjson2/releases/tag/2.0.50
2.0.50已发布,请用新版本

@wenshao wenshao closed this as completed May 12, 2024
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
bug Something isn't working fixed
Projects
None yet
Development

No branches or pull requests

3 participants