响应中的 Spring rest api 过滤器字段

Posted

技术标签:

【中文标题】响应中的 Spring rest api 过滤器字段【英文标题】:Spring rest api filter fields in the response 【发布时间】:2016-05-11 12:42:14 【问题描述】:

我正在使用 spring rest api 4.x。我们需要根据请求参数过滤响应中的字段。

我的用户对象:

private class UserResource 
   private String userLastName;
   private String userFirstName;
   private String email;
   private String streetAddress;


E.g. URL:  curl -i http://hostname:port/api/v1/users?fields=firstName,lastName. 

在这种情况下,我只需要返回请求参数“字段”中的字段。 JSON 输出应仅包含 firstName、lastName。

有几种方法可以根据对象过滤 Jackson 中的字段。在我的情况下,我需要通过将字段列表传递给 Jackson 序列化程序来动态过滤。

请分享一些想法。

【问题讨论】:

【参考方案1】:

谢谢阿里。这是一个很大的帮助。让我今天实现它。我会发布结果

@JsonFilter("blah.my.UserEntity")
public class UserEntity implements Serializable 
//fields goes here


@RequestMapping(value = "/users", method = RequestMethod.GET, produces = MediaType.APPLICATION_JSON_VALUE)
public MappingJacksonValue getUsers(@RequestParam MultiValueMap<String, String> params) 
//Build pageable here
Page<UserEntity> users = userService.findAll(pageable);

    MappingJacksonValue mappingJacksonValue = new MappingJacksonValue(users);
    FilterProvider filters = new SimpleFilterProvider()
                .addFilter("blah.my.UserEntity", SimpleBeanPropertyFilter
                        .filterOutAllExcept("userFirstName"));
    mappingJacksonValue.setFilters(filters);
    return mappingJacksonValue;

【讨论】:

这对我很有帮助【参考方案2】:

根据https://jira.spring.io/browse/SPR-12586 通过杰克逊JsonFilter 似乎在 Spring 4.2 中支持此功能(尽管 jira 目前正在返回错误)。

【讨论】:

嗨,本,感谢您的回复。这很有帮助。 这是我的解决方案。 MappingJacksonValue mappingJacksonValue = new MappingJacksonValue(MyObject);在您的控制器中,只需返回 mappingJacksonValue。确保 MyObject 有 @JsonFilter("myObject") 注释。【参考方案3】:

使用ResponseBodyAdvice 以便在响应写入 HTTP 响应之前更改它。在beforeBodyWrite(...) 方法中,您可以访问当前的ServerHttpRequest,您可以读取fields 的值。您的身体建议如下所示:

@ControllerAdvice
public class MyResponseBodyAdvisor implements ResponseBodyAdvice<UserResource> 
    @Override
    public boolean supports(MethodParameter returnType, Class<? extends HttpMessageConverter<?>> converterType) 
        return returnType.getParameterType().equals(UserResource.class);
    

    @Override
    public UserResource beforeBodyWrite(UserResource body, MethodParameter returnType, MediaType selectedContentType, Class<? extends HttpMessageConverter<?>> selectedConverterType, ServerHttpRequest request, ServerHttpResponse response) 
        String fields = ((ServletServerHttpRequest) request).getServletRequest().getParameter("fields");
        // body.set...(null) for each field not in fields

        return body;
    

【讨论】:

嗨,阿里,在您的解决方案中,我们将字段设为空。但我根本不想显示该字段。我按照 SPR-12586 中的描述实现了。谢谢。 使用 @JsonInclude 注释您的 dto 以从响应中删除 empty 字段

以上是关于响应中的 Spring rest api 过滤器字段的主要内容,如果未能解决你的问题,请参考以下文章

在 Spring Data rest json Response 中动态过滤实体字段

如何在 Spring(Boot)中装饰 REST 响应?

如何保护 Grails 中的所有 REST 请求和响应

从 REST API 过滤 JSON 对象的疑问

未调用 Spring Boot Rest API 过滤器

Spring Restful API - 有时,响应时间太长