deserialize lazy loading in hibernate and jackson
Is there a way to keep LAZY loading and deserialize the object using the id instead of the POJO object.
I have 2 class that are joined by a many-to-many relationship.
Something like this
public class User {
@Id
@JsonProperty
public long id;
@ManyToMany(
fetch = FetchType.EAGER,
)
@JoinTable(
name = "User_EntityType",
joinColumns = @JoinColumn(name = "user_id"),
inverseJoinColumns = @JoinColumn(name = "type_id")
)
@JsonProperty
public Set<Type> types;
}
public class Type {
@Id
@JsonProperty
public long id;
@ManyToMany(
fetch = FetchType.EAGER,
mappedBy = "types",
targetEntity = User.class
)
@JsonProperty
public Set<User> users;
}
The data type works just fine. I can write and read using hibernate with no issue.
However, I want to be able to return an User object with a REST API, so I'm using Jackson to deserialize it. The issue is when I do that, it deserialize every Type in the User object, which includes other Type objects, and it creates a huge mess.
Is it possible to instead just return the Set of Long type ids instead of Set of Type?
Yes it is possible, if you're using Jackson 2.0, with the Object Identity feature.
If you annotate a class with the @JsonIdentityInfo
annotation then Jackson will only output the object once; subsequent references will use the ID instead. So your set of types will be serialized as IDs, as long as the types have been output once. When deserializing Jackson will turn the IDs back into objects.
In your case I think you would need to annotate your Type class like this:
@JsonIdentityInfo(generator=ObjectIdGenerators.PropertyGenerator.class, property="id")
public class Type {
...
}
See http://wiki.fasterxml.com/JacksonFeatureObjectIdentity for details on how to use this feature.
I was facing this problem as well in my JAX-RS endpoints, which have to serialize and serve Hibernate entities using Jackson's object mappers. The option to use solutions like @JsonIgnore
or @JsonIdentityInfo(generator=ObjectIdGenerators.PropertyGenerator.class,...
weren't an option for me, as the former would mean the relational field gets omitted from the serialized output, and the later method sort of failed to resolve the issue no matter what.
So, my solution was to set the following flag on the mapper prior to doing the actual serialization:
ObjectMapper objMapper = new ObjectMapper();
objMapper.configure(SerializationFeature.FAIL_ON_EMPTY_BEANS, false);
This way, there was no attempt to populate relational objects, instead their ids were left intact, and so I could keep the fetch = FetchType.LAZY
flag on my relational fields.
上一篇: 水印video.js播放器的最明智的方式
下一篇: 反序列化休眠和杰克逊中的延迟加载