Java n 层应用程序中处理异常的适当方法

问题描述 投票:0回答:1

我的应用程序有三层:控制器、服务和 DAO。我的控制器和服务层位于 Spring,而 DAO 层位于 Hibernate 6。我的问题是在 CRUD 操作时处理异常的最合适方法是什么。 例如,如果我只是在 DAO 中记录一般异常,我只能在日志中获得详细信息,而在前端我无法插入记录。

try{
} catch(Exception e){
logger("Error in DAO {}", e.getMessage(), e)
}

我有三个问题

  1. 我应该捕获一般异常吗?如果是的话应该去哪里抓?
  2. 如果我在 DAO 层捕获
    HibernateException
    ,我仍然无法让用户确切知道是什么导致了异常,如果我捕获
    ConstraintViolationException
    ,我该如何处理语法异常或数据库服务器出现故障等情况下发生的异常?
  3. 异常应该翻译到哪里?我应该只是将异常从 DAO 记录并抛出到服务层并在服务层中转换它们,还是应该将异常转换为 DAO 层中的适当错误消息?
java hibernate exception try-catch exceptionhandler
1个回答
0
投票

处理n层架构,坚持第一个SOLID原则,即单一职责原则。

例如,在 DAO 层中,捕获特定异常,如

HibernateException
ConstraintViolationException
等...避免在 DAO 层中捕获通用异常,因为它可能掩盖其他潜在问题。

在您的服务层中,捕获更常见的异常并相应地处理或翻译它们。服务层可以捕获 DAO 层抛出的异常并将其转换为应用程序特定的异常或消息。

这是一个简化的示例,可以帮助您理解这个想法:

道:

public void insertRecord(Entity entity) {
    try {
        session.save(entity);
    } catch (ConstraintViolationException e) {
        logger.error("Constraint violation in DAO: {}", e.getMessage(), e);
        throw new CustomConstraintViolationException("Constraint violation occurred while inserting record.");
    } catch (HibernateException e) {
        logger.error("Hibernate exception in DAO: {}", e.getMessage(), e);
        throw new CustomDatabaseException("Database error occurred while inserting record.");
    } catch (Exception e) {
        logger.error("Unexpected exception in DAO: {}", e.getMessage(), e);
        throw new CustomGenericException("An unexpected error occurred.");
    }
}

服务

public void addRecord(Entity entity) {
    try {
        dao.insertRecord(entity);
    } catch (CustomConstraintViolationException e) {
        logger.error("Service layer caught constraint violation: {}", e.getMessage(), e);
        throw new ServiceException("Cannot insert record due to constraint violation.");
    } catch (CustomDatabaseException e) {
        logger.error("Service layer caught database exception: {}", e.getMessage(), e);
        throw new ServiceException("Database error occurred while processing the request.");
    } catch (CustomGenericException e) {
        logger.error("Service layer caught unexpected exception: {}", e.getMessage(), e);
        throw new ServiceException("An unexpected error occurred.");
    }
}

控制器

@PostMapping("/add")
public ResponseEntity<String> addRecord(@RequestBody Entity entity) {
    try {
        service.addRecord(entity);
        return ResponseEntity.ok("Record added successfully.");
    } catch (ServiceException e) {
        logger.error("Controller caught service exception: {}", e.getMessage(), e);
        return ResponseEntity.status(HttpStatus.BAD_REQUEST).body(e.getMessage());
    } catch (Exception e) {
        logger.error("Controller caught unexpected exception: {}", e.getMessage(), e);
        return ResponseEntity.status(HttpStatus.INTERNAL_SERVER_ERROR).body("An unexpected error occurred.");
    }
}
© www.soinside.com 2019 - 2024. All rights reserved.