假设我有一个集合 /cars,它支持通常的操作,并且我还支持 /cars/{id}。
当我获得 /cars 的 GET 时,仅返回有限的集合元素“视图”的最佳实践是什么?也就是说,列出可能的 id、name 就足够了,客户需要更多信息,他可以通过 /cars/{id} 查询更详细的信息。
这可能是 Jackon@JsonView
注释的一个很好的候选者。我通常在一个通用包中定义一些标记接口(可以在一个应用程序中重复使用):
public interface View {
public interface Partial { }
public interface Full extends Partial { }
}
然后你可以像这样在汽车类中使用它们:
public class Car {
private int id;
private String name;
//Supresses serialization of this property when another view is active
@JsonView(View.Full.class)
private String description;
......
}
最后激活资源中的适当视图:
@Path("/")
@JsonView(View.Partial.class)
public Collection<Car> getAll();
@Path("/{id}")
@JsonView(View.Full.class)
public Car getById(@PathParam("id") int id);
需要注意的是,@JsonView(View.Partial.class)
从getAll()
方法中省略将导致所有属性都被序列化(在这种情况下,人们可能希望description
不会被序列化)。这是因为 Jackson 禁用视图处理并忽略所有视图注释,除非有明确的视图指定用于渲染。我为此写了一个解决方法(这样当没有指定视图时,只有属于默认视图的属性被序列化)。我只能让它用于序列化而不是反序列化,如果你有兴趣我可以尝试挖掘它。
假设您在后端使用一些 ORM 库,定义两个不同的类:一个映射该实体的所有详细信息,另一个仅映射与概览相关的少数属性。然后只需在您的两种方法中将它们返回到不同的类型。
我认为这是一种非常标准的模式,至少我在我一直从事的项目中遇到了这种技术。