全局响应体处理器(ResponseBodyAdvice)

David 2022-09-28 23:50:20
Categories: Tags:
  • 封装响应体依旧需要在控制层频繁使用 Result.success()Result.fail() 手动封装响应体返回,这造成了代码的大量耦合,并且也污染了业务处理的代码逻辑

 

  • SpringMVC 4.1 后提供了 ResponseBodyAdvice 接口用于拦截 Controller 方法的返回值,它允许在执行 @ResponseBody 后处理返回数据,可以用来封装统一数据格式返回

方法

说明

supports

判断是否要执行beforeBodyWrite方法,true为执行,false不执行

beforeBodyWrite

body 获取之前对响应体处理的执行方法

 

  • 我们只需要自定义 ResponseBodyAdvice 接口的实现类,增加响应体的统一封装逻辑

示例

@RestControllerAdvice(basePackages="com.example.controller")

public class GlobalResponseBodyAdvice implements ResponseBodyAdvice<Object> {

 

    @Resource

    private ObjectMapper objectMapper;

 

    @Override

    public boolean supports(MethodParameter returnType, Class<? extends HttpMessageConverter<?>> converterType) {

        return true;

    }

 

    @SneakyThrows

    @Override

    public Object beforeBodyWrite(Object o, MethodParameter returnType, MediaType selectedContentType, Class<? extends 

HttpMessageConverter<?>> selectedConverterType, ServerHttpRequest request, ServerHttpResponse response) {

//单字符串处理

        if (o instanceof String) {

            return objectMapper.writeValueAsString(Result.success(o));

        }

//兼容手动封装

        if (o instanceof Result || o instanceof ErrorResult) {

            return o;

        }

        return Result.success(o);

    }

}

 

  • 这时我们只需要回到最原本的业务逻辑,直接返回数据即可

示例

@RestController

@RequestMapping("/user")

public class UserController {

    @GetMapping("/{id}")

    public User getUserById(@PathVariable Integer id) {

        User user = userService.getById(id);

        return user;

    }

}

 

接口数据返回如下: