{"data":{"id":"1","name":"jack"},"code":200,"message":"success"}
为SpringBoot写一个简单的Response返回数据处理
对于每次的数据返回处理,是不是很厌烦,每次都要封装对象,形成统一的返回格式
return ResultVO.success(i);
这次通过aop思想统一处理
@ControllerAdvice ,这个注解,这是一个增强的 Controller。使用这个 Controller ,可以实现三个方面的功能:
- 全局异常处理
- 全局数据绑定
- 全局数据预处理
灵活使用这三个功能,可以帮助我们简化很多工作,需要注意的是,这是 SpringMVC 提供的功能,在 Spring Boot 中可以直接使用,下面分别来看。
一、首先定义我们的注解,以便标识哪个类,哪个方法需要用到自动封装处理
import java.lang.annotation.*;
/*
* 返回数据封装
* 第一步注解
* */
@Retention(RetentionPolicy.RUNTIME)
@Target({ElementType.TYPE,ElementType.METHOD})
@Documented
public @interface ResponseResult {
}
二、设置用于测试的返回数据实体类以及用户实体
@Data
public class Result {
private Object data;
private Integer code;
private String message;
public Result(Object data, Integer code, String message) {
this.data = data;
this.code = code;
this.message = message;
}
public static Result success(Object data) {
return new Result(data,200,"success");
}
public static Result success(Object data, Integer code, String message) {
return new Result(data,code,message);
}
public static Result fail(Object data, Integer code, String message) {
return new Result(data,code,message);
}
}
@Data
public class BaseMan {
String id;
String name;
}
三、设置一个controller,方便用于实际测试
@RestController
@RequestMapping("/base")
@ResponseResult
public class BaseController {
@GetMapping("")
public BaseMan getBaseMans(){
BaseMan baseMan=new BaseMan();
baseMan.setId("1");
baseMan.setName("jack");
return baseMan;
}
}
四、设置一个handler处理器,处理这些封装事务
@Slf4j
@ControllerAdvice(annotations = {ResponseResult.class})
public class GlobalResponseHandler implements ResponseBodyAdvice<Object> {
@Override
public boolean supports(MethodParameter methodParameter, Class<? extends HttpMessageConverter<?>> aClass) {
//避免重复处理已经做过封装处理的返回值
final String returnTypeName= methodParameter.getParameterType().getName();
boolean flag=!"com.example.demo.entity.Result".equals(returnTypeName)
&&!"org.springframework.http.ResponseEntity".equals(returnTypeName);
log.info("supports:"+flag);
return flag;
}
@Override
public Object beforeBodyWrite(Object o,
MethodParameter methodParameter,
MediaType mediaType,
Class<? extends HttpMessageConverter<?>> aClass,
ServerHttpRequest serverHttpRequest,
ServerHttpResponse serverHttpResponse) {
log.info("before");
final String returnTypeName = methodParameter.getParameterType().getName();
if("void".equals(returnTypeName)){
return Result.success(null);
}
if(!mediaType.includes(MediaType.APPLICATION_JSON)){
return o; //返回值不是json类型
}
if("com.example.demo.entity.Result".equals(returnTypeName)){
return o;
}
/*
* 这里我们只处理了正常成功的包装,如果方法体报异常怎么办?处理异常也比较简单,只要判断body是否为异常类。
* o instanceof Exception
* */
return Result.success(o);
}
}
测试请求
没有设置handler处理返回的结果
{"id":"1","name":"jack"}
处理后的结果
{"data":{"id":"1","name":"jack"},"code":200,"message":"success"}
这个设置处理流程是不够详细的,里面可能还会涉及到 异常抛出时的处理 流程。所以这只是最基本的处理思路,如果有用到,还需要更详细去设计处理流程,尽量考虑到方方面面的情况。
嘻嘻