Spring Boot中关联表的JsonFilter属性过滤问题
解决Spring Boot中JsonFilter动态过滤关联表数组属性的问题
要实现主表和关联表数组的动态字段过滤,核心是给主实体和关联实体分别配置Jackson的@JsonFilter,并在序列化时同时指定两个过滤器的字段规则,具体操作如下:
1. 给实体类添加JsonFilter注解
给主表实体和关联表实体各自标注不同的过滤器名称,方便后续分别配置规则:
@Entity @JsonFilter("MainEntityFilter") public class MainEntity { private String var1; private String var2; private LocalDateTime var4; @OneToMany(mappedBy = "mainEntity") private List<AssociatedEntity> arr1; // 省略getter、setter } @Entity @JsonFilter("AssociatedEntityFilter") public class AssociatedEntity { private String v5; private String v6; private String v7; @ManyToOne private MainEntity mainEntity; // 省略getter、setter }
2. 动态配置过滤器并序列化
在接口中接收前端传入的主表字段列表和关联表字段列表,通过SimpleFilterProvider给两个过滤器分别设置要保留的字段,再用自定义的ObjectMapper完成序列化(不要修改全局ObjectMapper,避免影响其他接口):
@RestController public class MainController { @Autowired private ObjectMapper objectMapper; @Autowired private MainEntityRepository mainRepo; @GetMapping("/main-entities") public String getFilteredEntities(@RequestParam List<String> mainFields, @RequestParam List<String> assocFields) throws JsonProcessingException { // 查询数据,注意关联表如果是懒加载,要提前加载(比如用@EntityGraph或fetch join) List<MainEntity> entities = mainRepo.findAll(); // 配置两个过滤器的字段保留规则 SimpleFilterProvider filterProvider = new SimpleFilterProvider() .addFilter("MainEntityFilter", SimpleBeanPropertyFilter.filterOutAllExcept(mainFields)) .addFilter("AssociatedEntityFilter", SimpleBeanPropertyFilter.filterOutAllExcept(assocFields)); // 创建ObjectMapper副本,避免修改全局配置 ObjectMapper customMapper = objectMapper.copy(); customMapper.setFilterProvider(filterProvider); return customMapper.writeValueAsString(entities); } }
关键注意事项
- 关联表如果是懒加载模式,必须确保查询时已经加载关联数据,否则序列化时会触发懒加载异常,可通过
@EntityGraph(attributePaths = "arr1")或自定义JPQL的fetch join实现。 - 不要直接修改Spring Boot自动配置的全局
ObjectMapper,创建副本单独配置过滤器,防止其他接口的序列化规则被干扰。
这样请求接口时,传入mainFields=var1,var4和assocFields=v5,v6,就能得到你想要的仅包含指定字段的JSON结果。
内容的提问来源于stack exchange,提问作者Ankit Kulkarni
相关产品推荐
相关产品推荐

