我有一个Spring Boot应用程序,它具有以下近似结构:
- 项目
- Api
- ApiImpl
- 应用程序
Api
是一个interface
,它看起来像这样:
public interface Api {
public String methodOne(...) throws ExceptionOne, ExceptionTwo, ExceptionThree;
...
public int methodN(...) throws ExceptionOne, ExceptionThree, ExceptionFour;
}
ApiImpls
是请求控制器(实际上还有第二层,但这对于本例来说应该足够了(。在那里,我现在做的事情如下:
@Controller
public class ApiImpl {
public String methodOne(...) {
try {
// do stuff that can yield an exception
}
catch(ExceptionOne e) {
// set proper response code and return values
}
catch(ExceptionTwo e) {
// set proper response code and return values
}
catch(ExceptionThree e) {
// set proper response code and return values
}
}
}
基本上,这种行为会产生大量的重复(也可以将我的异常命名为D、R和Y…(,但在其他方面非常适合处理内部应用程序逻辑。
我的问题是:如何实现一个在Java中处理此问题的自定义异常调度器?理想情况下,我希望这里有这样的答案,但不幸的是,据我所知,在Java中不可能像C++代码中那样简单地throw
处理当前异常。为了简洁起见,我想完成的事情如下:
@Controller
public class ApiImpl {
public String methodOne(...) {
try {
// do stuff that can yield an exception
}
catch(ExceptionOne e) {
handle()
}
}
private void handle() { // maybe Throwable or Exception subclass as parameter
// handle the correct exception type, set correct response code, etc.
}
}
有没有什么好的方法可以做到这一点,从而最大限度地减少代码重复?
以下是我试图让它发挥作用的初步尝试:
public class Thrower {
public Thrower(int e) throws ExceptionOne, ExceptionTwo, ExceptionThree {
if(e == 0) {
throw new ExceptionOne();
}
if(e == 1) {
throw new ExceptionTwo();
}
if(e == 2) {
throw new ExceptionThree();
}
}
}
class ExceptionOne extends Exception {}
class ExceptionTwo extends Exception {}
class ExceptionThree extends Exception {}
public class ExceptionHandler {
private void handle(Exception ex) throws Exception {
try {
throw ex;
}
catch(ExceptionOne e) {
e.printStackTrace();
System.out.println("Exception one");
}
catch(ExceptionTwo e) {
e.printStackTrace();
System.out.println("Exception two");
}
catch(ExceptionThree e) {
e.printStackTrace();
System.out.println("Exception three");
}
}
public void causesException(int which) throws Throwable {
try {
Thrower t = new Thrower(which);
}
catch(Exception e) {
handle(e);
}
}
public static void main(String[] args) throws Throwable {
ExceptionHandler eh = new ExceptionHandler();
eh.causesException(0);
eh.causesException(1);
eh.causesException(2);
}
}
这可以按预期工作,并且我可以根据需要处理不同的异常类型(此处使用构造函数显示,但原理相同(。然而,这感觉非常笨重。
如果您正在寻找全局处理所有控制器层异常(在Spring MVC体系结构中(,您可以通过使用@ExceptionHandler
方法(这是Spring的ControllerAdvice
(在一个位置为所有控制器执行此操作(下面的选项1(。
选项(1(:在单独的类中配置异常
@ControllerAdvice
class MyProjectExceptionHandler {
@ExceptionHandler(value = ExceptionOne.class)
public R exceptionOne(ExceptionOne exe) {
//set proper response code and return values
}
@ExceptionHandler(value = ExceptionTwo.class)
public R exceptionTwo(ExceptionTwo exe) {
//set proper response code and return values
}
}
选项(2(:在控制器类本身中配置异常
如果您正在Controller
类本身中寻找处理异常的方法,那么您可以按如下方式执行:
@Controller
public class ApiImpl {
public String methodOne(...) {
}
@ExceptionHandler(ExceptionOne.class)
public R exceptionTwo(ExceptionOne exe) {
//set proper response code and return values
}
//other exceptions
}
您可以在这里查看更多关于的信息