Reputation: 2016
Is it possible with Jackson to deserialize json with Builder pattern as well as with default setter and getter approach?
My object is created with Builder that covers only required (final) fields, but I have non-final fields with some values as well that need to be deserialized with setters.
Here is the sample that throws an exception in an attempt to deserialize it with:
new ObjectMapper().readValue(json, Foo.class);
json - json representation serialized with default Jackson serializer, like:
objectMapper.writeValueAsString(foo);
class
@Getter
@Setter
@ToString
@JsonInclude(JsonInclude.Include.NON_NULL)
@JsonDeserialize(builder = Foo.Builder.class)
public class Foo {
private final String key;
private final Long user;
private final String action;
private final String material;
private final String currency;
private Foo(String key, Long user, String action, String material, String currency) {
this.key = key;
this.user = user;
this.action = action;
this.material = material;
this.currency = currency;
}
public static class Builder {
private String key;
private Long user;
private String action;
private String material;
private String currency;
@JsonProperty("key")
public Foo.Builder withKey(String key) {
this.key = key;
return this;
}
@JsonProperty("user")
public Foo.Builder withUser(Long user) {
this.user = user;
return this;
}
@JsonProperty("action")
public Foo.Builder withAction(String action) {
this.action = action;
return this;
}
/// other 'with' setters....
}
@JsonProperty("state")
private int state;
@JsonProperty("stat")
private String stat;
@JsonProperty("step")
private String step;
}
The exception it throws like :
com.fasterxml.jackson.databind.exc.UnrecognizedPropertyException: Unrecognized field "state" (class com.Foo$Builder), not marked as ignorable (5 known properties: "key", "user", "action", "material", "currency",])
If not possible what workaround is the cheapest?
Upvotes: 1
Views: 1153
Reputation: 9786
Two things that are suspicious:
Foo
class. In that case you should correct the specification
(SessionData.Builder.class
is not correct in that case).In both cases you should make sure the final method to get the Foo
instance is called build()
otherwise you should annotate the builder with a @JsonPOJOBuilder(buildMethodName = "nameOfMethod", withPrefix = "set")
.
Upvotes: 2