jinini利用拦截器实现
1.创建异常实体,继承RuntimeException
public class MyCustomException extends RuntimeException {
private ResponseStatusEnum responseStatusEnum;
public MyCustomException(ResponseStatusEnum responseStatusEnum) {
super("异常状态码为:" + responseStatusEnum.status() + ";" + "具体异常信息为:" + responseStatusEnum.msg());
this.responseStatusEnum = responseStatusEnum;
}
public ResponseStatusEnum getResponseStatusEnum() {
return responseStatusEnum;
}
public void setResponseStatusEnum(ResponseStatusEnum responseStatusEnum) {
this.responseStatusEnum = responseStatusEnum;
}
}
2.创建自定义异常捕捉器
@ControllerAdvice:切面 @ExceptionHandler(MyCustomException.class):只捕捉这个异常 GraceJSONResult:已定义返回类
@ControllerAdvice
public class GraceExceptionHandler {
@ExceptionHandler(MyCustomException.class)
@ResponseBody
public GraceJSONResult returnMyException(MyCustomException e) {
e.printStackTrace();
return GraceJSONResult.exception(e.getResponseStatusEnum());
}
}
3.创建拦截器
1.实现HandlerInterceptor接口,重写preHandle、postHandle、afterCompletion;
2.preHandle:拦截请求,访问controller之前
3.postHandle:在请求访问到controller之后,渲染视图之前
4.afterCompletion:在请求访问到controller之后,渲染视图之后
只要上面三个方法中返回false则会被拦截,返回true则通过
public class PassportInterceptor implements HandlerInterceptor {
@Autowired
protected RedisOperator redisOperator;
public static final String MOBILE_SMSCODE = "mobile:smscode:";
/**
* 拦截请求,访问controller之前
*
* @param request
* @param response
* @param handler
* @return
* @throws Exception
*/
@Override
public boolean preHandle(HttpServletRequest request, HttpServletResponse response, Object handler) throws Exception {
String userIP = IPUtil.getRequestIp(request);
if (redisOperator.keyIsExist(MOBILE_SMSCODE + userIP)) {
GraceException.display(ResponseStatusEnum.SMS_NEED_WAIT_ERROR);
return false;
}
return true;
}
/**
* 在请求反问道controller之后,渲染视图之前
*
* @param request
* @param response
* @param handler
* @param modelAndView
* @throws Exception
*/
@Override
public void postHandle(HttpServletRequest request, HttpServletResponse response, Object handler, ModelAndView modelAndView) throws Exception {
HandlerInterceptor.super.postHandle(request, response, handler, modelAndView);
}
/**
* 在请求反问道controller之后,渲染视图之后
*
* @param request
* @param response
* @param handler
* @param ex
* @throws Exception
*/
@Override
public void afterCompletion(HttpServletRequest request, HttpServletResponse response, Object handler, Exception ex) throws Exception {
HandlerInterceptor.super.afterCompletion(request, response, handler, ex);
}
}
4.当拦截器拦截到时,使用GraceException优雅得抛出异常,被上面的自定义异常捕捉器捕获,实现自定义异常拦截处理
@Override
public boolean preHandle(HttpServletRequest request, HttpServletResponse response, Object handler) throws Exception {
String userIP = IPUtil.getRequestIp(request);
if (redisOperator.keyIsExist(MOBILE_SMSCODE + userIP)) {
GraceException.display(ResponseStatusEnum.SMS_NEED_WAIT_ERROR);
return false;
}
return true;
}
把拦截器配置放进bean容器并设置拦截路径:
拦截到异常抛出
public class GraceException {
public static void display(ResponseStatusEnum responseStatusEnum) {
throw new MyCustomException(responseStatusEnum);
}
}
5. 重点:
在springBoot启动类中需要添加@ComponentScan()或@ComponentScans(),负责扫描拦截对应的包前缀下面的异常抛出,否则无法拦截
@SpringBootApplication
@MapperScan(basePackages = "com.fox.user.mapper")
@ComponentScan("com.fox") // 负责扫这个包前缀
public class Application {
public static void main(String[] args) {
SpringApplication.run(Application.class, args);
}
}