使用Jackson对序列化的最终类进行反序列化

时间:2015-11-04 12:55:36

标签: java json jackson

我为用户提供以下价值持有人类:

package entities;

import com.fasterxml.jackson.annotation.JsonTypeInfo;
import com.fasterxml.jackson.databind.annotation.JsonDeserialize;
import com.fasterxml.jackson.databind.annotation.JsonSerialize;
import org.immutables.value.Value;

import javax.annotation.Nullable;

@Value.Immutable
@JsonSerialize(as = ImmutableUser.class)
@JsonDeserialize(as = ImmutableUser.class)
@JsonTypeInfo(use = JsonTypeInfo.Id.CLASS)
public interface User {

    String getUsername();
    String getEmail();
    @Nullable String getPassword();
    @Nullable String getEncodedPassword();
}

在编译期间生成此值持有者的不可变最终实现:

@SuppressWarnings("all")
@ParametersAreNonnullByDefault
@Generated({"Immutables.generator", "User"})
@Immutable
public final class ImmutableUser implements User {

Immutable的序列化实例

{"@class":"entities.ImmutableUser$Json","username":"testuser","email":"123@gmail.com","password":null,"encodedPassword":null}

问题是此JSON的反序列化失败,并出现以下错误:

java.lang.IllegalArgumentException: Class entities.ImmutableUser$Json is not assignable to entities.User
    at com.fasterxml.jackson.databind.JavaType._assertSubclass(JavaType.java:466)
    at com.fasterxml.jackson.databind.JavaType.narrowBy(JavaType.java:149)
    at com.fasterxml.jackson.databind.type.TypeFactory.constructSpecializedType(TypeFactory.java:315)
    at com.fasterxml.jackson.databind.jsontype.impl.ClassNameIdResolver._typeFromId(ClassNameIdResolver.java:64)
    ... 38 more

为什么序列化实例的JSON中的@class属性值为"entities.ImmutableUser$Json"而不是"entities.ImmutableUser"?是因为班级是final吗? 有没有其他方法可以序列化这些类并避免在反序列化过程中出现问题?

2 个答案:

答案 0 :(得分:1)

  

发现问题是由生成的类引起的。结果   这些类应该使用特定的类封送:   immutables.github.io/site1.x/json.html

答案 1 :(得分:0)

http://immutables.github.io/site1.x/json.html指的是较旧版本的文档,如果您使用 Immutables v2.0及更高版本,则无关紧要。在您的情况下,您面临已经修复的问题(类似于https://github.com/immutables/immutables/issues/175)。尝试升级到 Immutables v2.1以解决它。

简而言之,Jackson在序列化过程中使用了注释@JsonValue来替换对象。不幸的是,我们发现它与@JsonTypeInfo@JsonSubTypes等其他功能不相符。请参阅https://github.com/FasterXML/jackson-databind/issues/937

Immutables 的2.1版不再使用@JsonValue,因此它现在应该可以使用了。如果没有,请将其作为错误报告给https://github.com/immutables/immutables/issues