JDBC Spring-mvc 中的异常处理

JDBC exception handling in Spring-mvc

我正在实施一个 REST api 网络服务,它从 MySql 数据库中获取数据。上面写着 here 我们不需要显式处理数据库异常。我在 Service 层中有 catch 块。我有以下问题。

1- 如何从 catch 块向相应的模型视图发送适当的错误消息?

2- Service 是捕获异常的正确层吗?

我有以下代码

控制器

    @RequestMapping(value = "/saveUser", method = RequestMethod.POST)
    public ModelAndView saveUser(@ModelAttribute User user, BindingResult result) 
    {
       ModelAndView mv = new ModelAndView();

       validator.validate(user, result);
       if(result.hasErrors()) {
           mv.setViewName("addUser");
       }
       else {
           service.saveUser(user);
           mv.setViewName("redirect:/users/listAllUsers");
       }
       return mv;
    }

服务

public void saveUser(User user) {
    try {
        userDao.saveUser(user);
    } catch(DuplicateKeyException e) {
        //Here i want to send "User already exist"
    } catch(DataAccessException e) {
        //Here i want to send "Databae unreachable"
    }
}

UserDAO

public void saveUser(User user) {
        String sql = "INSERT INTO User (fname, lname, address, phone)"
                    + " VALUES (?, ?, ?, ?)";
            jdbcTemplate.update(sql, user.getFname(), user.getLname(),
                    user.getAddress(), user.getPhone()); 
    }
}

您想将特定于 Web 的行为与服务层和数据层隔离开来,我认为最好的方法是抛出一个新的、经过检查的、特定于域的 Exception匹配您希望在 Controller 中以不同方式处理的每种情况的含义。

例如,DuplicateUserExceptionSystemUnavailableException。然后控制器捕获这些并将正确的案例添加到模型中。

@dbreaux 的回答是correct.You 应该自定义一个例外。

public class UserException extends RuntimeException {
      // You can add some custom variables
      // such as error codes, error types, etc.
}

那么,你应该定义一个ControllerAdvice来处理这个异常:

import org.springframework.web.bind.annotation.ControllerAdvice;
import org.springframework.web.bind.annotation.ExceptionHandler;

@ControllerAdvice
public class UserControllerAdvice{

    @ExceptionHandler(value = UserException.class)
    public ModelAndView handleUserException(UserException ex){

        // Generate corresponding results(ModelAndView) based on exception.
        // example: Put the error message to model. 
        return new ModelAndView("prompt_page",ex.getMessage());
    }
}

最后,您可以在您的服务中抛出 UserException

public void saveUser(User user) {
    try {
        userDao.saveUser(user);
    } catch(DuplicateKeyException e) {
        throw new UserException("User already exist");
    } catch(DataAccessException e) {
        throw new UserException("Databae unreachable");
    }
}