在 Quarkus 服务层中使用 Mutiny 处理多个异常

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

我正在使用 Mutiny 进行反应式编程开发 Quarkus 应用程序,并且在服务层中遇到异常处理问题。我有一个保留用户的方法,并且我想根据发生的错误类型抛出特定的异常。然而,我遇到了以下挑战:

  • 如果我不使用.transform(),而是使用recoverWithItem()或
    receiveWithUni() 用于处理异常,它会抛出多个
    发生 ConstraintViolationException 时出现异常。
  • 如果我使用
    .transform(),它进入两个变换块而不是
    仅处理相关异常。

以下是相关代码片段:

public Uni<AuthResponse> persistUser(User user) {
        return Panache.withTransaction(user::persist)
                .onItem().transform(success -> {
                    log.info("Successfully created user, email: {}", user.getEmail());
                    return new AuthResponse(user);
                })
                .onFailure(ConstraintViolationException.class)
                .transform(ex -> handleUserCreationError(user.getEmail()))
                .onFailure()
                .transform(ex -> handleGeneralPersistenceError(ex, user.getEmail()));
    }

    private Throwable handleUserCreationError(String email) {
        log.error("User already exists, email: {}", email);
        return new AccountAlreadyExistsException(ExceptionMessages.ACCOUNT_ALREADY_EXISTS + email);
    }

    private Throwable handleGeneralPersistenceError(Throwable ex, String email) {
        log.error("Error occurred while creating user: {}, exception: {}",email, ex.getMessage());
        return new PersistenceException("Failed to create user", ex);
    }

问题: 多个异常:如果不使用.transform(),发生ConstraintViolationException时会抛出多个异常。 两个变换均已触发:当我使用 .transform() 时,两个变换块都会被触发,这不是所需的行为。

期望的行为: 我想确保当ConstraintViolationException发生时,只调用handleUserCreationError,而不会继续调用handleGeneralPersistenceError。此外,我想根据错误类型抛出适当的异常,而不会导致多个异常。

我怎样才能实现这个目标? 任何有关如何在这种情况下正确处理异常的帮助或见解将不胜感激!

reactive-programming quarkus quarkus-panache
1个回答
0
投票

handleGeneralPersistenceError
正在被调用,因为这是一个不与任何特定类型绑定的异常处理程序,因此这是预料之中的,因为前一个
onFailure(Class).transform(...)
将一个异常映射到另一个异常,并且它在管道中转发到
 onFailure().transform(...)

我建议你简单地将逻辑压缩为形式的单个转换:

onFailure().transform(err -> {
  if (err instanceof X) {
     // ...
  } else if (err instanceof Y) { 
     // ...
  }
})
© www.soinside.com 2019 - 2024. All rights reserved.