问题
I have problem with jackson serialization of object by its interface.
I have class
class Point implements PointView {
private String id;
private String name;
public Point() {
}
public Point(String id, String name) {
this.id = id;
this.name = name;
}
@Override
public String getId() {
return id;
}
public String getName() {
return name;
}
}
which implements
interface PointView {
String getId();
}
and have class
class Map implements MapView {
private String id;
private String name;
private Point point;
public Map() {
}
public Map(String id, String name, Point point) {
this.id = id;
this.name = name;
this.point = point;
}
@Override
public String getId() {
return id;
}
public String getName() {
return name;
}
@JsonSerialize(as = PointView.class)
public Point getPoint() {
return point;
}
}
which implements
interface MapView {
String getId();
Point getPoint();
}
And have class
class Container {
private Map map;
public Container() {
}
public Container(Map map) {
this.map = map;
}
@JsonSerialize(as = MapView.class)
public Map getMap() {
return map;
}
}
I want serialize Container with Jackson and get result
{"map":{"id":"mapId","point":{"id":"pointId"}}}
But in fact I get result
{"map":{"id":"mapId","point":{"id":"pointId","name":"pointName"}}}
that have property "name" in nested object "point" although I specified serializition type of Point in Map (@JsonSerialize(as = PointView.class)
). Interface PointView dont have method getName, but in result exists field "name" of Point.
If I remove annotation (@JsonSerialize(as = MapView.class)
) from method getMap in class Container I get result
{"map":{"id":"mapId","name":"mapName","point":{"id":"pointId"}}}
Now point dont have property "name", but map have.
How can I get result
{"map":{"id":"mapId","point":{"id":"pointId"}}}
?
回答1:
To get the desired result also the same method in interface must be annotated by @JsonSerialize
interface MapView {
String getId();
@JsonSerialize(as = PointView.class)
Point getPoint();
}
回答2:
You can annotate the method like this:
@JsonIgnore
public String getName() {
return name;
}
Or if you want specific serialization in this use case, but normal serialization in others, you can use a @JsonView
(see doc).
The reason it's serializing out the name
is that the instance has the accessor getName()
, even though interface does not.
回答3:
Yes, you can use
@JsonSerialize(as=MyInterface.class)
public class ConcreteClass implements MyInterface { .... }
either on implementation class (as above), or on property that has value.
来源:https://stackoverflow.com/questions/33151974/jackson-serialization-of-nested-objects