微服务中Exception(异常)的设计思想
系统对于异常的处理可以使用统一的异常处理流程:
- 自定义异常类型;
- 自定义错误代码和错误信息;
- 对于可预知的异常由程序员在代码中主动抛出,由SpringMVC统一捕获;
- 可预知异常时程序员在代码中手动抛出本系统定义的特定异常类型,由于是程序员抛出的异常,通常信息比较比较齐全,程序员在抛出时会指定错误代码及错误信息,获取异常信息也比较方便;
- 对于不可预知的异常(运行时异常)由SpringMVC统一捕获Exception类型的异常;
- 可预知的异常及不可预知的运行时异常最终会采用统一的信息格式(错误代码+错误信息)来表示,最终也会随请求响应给客户端;
/**
* @Author:朱国庆
* @Date:2019/12/16 00:26
* @Version: 1.0
*/
@ControllerAdvice//控制器增强
@ResponseBody
public class ExceptionCatch {
private static final Logger LOGGER = LoggerFactory.getLogger(ExceptionCatch.class);
/**
* 定义Map,配置异常类型所对应的错误代码
* 使用Exceptions存放异常类型和错误代码的映射,ImmutableMap的特点就是一旦创建不可改变,并且线程安全;
*/
private static ImmutableMap<Class<? extends Throwable>, ResultCode> EXCEPTIONS;
/**
* 定义Map的builder对象,去构建ImmutableMap
*/
protected static ImmutableMap.Builder<Class<? extends Throwable>, ResultCode> builder = ImmutableMap.builder();
static {
//定义异常
builder.put(HttpMessageNotReadableException.class, CommonCode.INVALID_PARAM);
}
/**
* 捕获CustomException
* @param customException
* @return
*/
@ExceptionHandler(CustomException.class)
public ResponseResult customException(CustomException customException) {
LOGGER.error("catch exception:{}", customException);
ResultCode resultCode = customException.getResultCode();
return new ResponseResult(resultCode);
}
@ExceptionHandler(Exception.class)
public ResponseResult exception(Exception exception) {
LOGGER.error("catch exception:{}", exception);
if (EXCEPTIONS == null) {
EXCEPTIONS = builder.build();
//EXCEPTIONS构建成功
}
//从EXCEPTIONS中找异常类型中所对应的错误代码,如果找到了将错误代码响应给用户,如果找不到给用户响应99999
ResultCode resultCode = EXCEPTIONS.get(exception.getClass());
if (resultCode != null) {
return new ResponseResult(resultCode);
} else {
return new ResponseResult(CommonCode.SERVER_ERROR);
}
}
}
因为该异常我们是单独放在·common这个项目中的·在依赖项目中的SpringBoot的启动类中加:@ComponentScan(basePackages="xxxxx")
使其能够被扫描到并注入到Spring容器中去;