Solucionado (ver solução)
Solucionado
(ver solução)
4
respostas

Erro 500 ao invés de 400 (2)

Eu vi a solução do outro, mas caso eu queria especificar o campo não cadastrado, eu pensei num if, mas gostaria de saber se tem outra solução melhor

 @ExceptionHandler(SQLIntegrityConstraintViolationException.class)
    public ResponseEntity tratarErro400ParaRegistroDuplicado(SQLIntegrityConstraintViolationException ex) {

        return ResponseEntity.badRequest().body(MensagemErroValidacao.registroDuplicado(ex.getLocalizedMessage()));
    }

Record

    private record MensagemErroValidacao(String mensagem){

        public static MensagemErroValidacao registroDuplicado(String campo){
           if (campo.contains("email"))
               return new MensagemErroValidacao("E-mail já cadastrado");
           else if (campo.contains("crm")){
               return new MensagemErroValidacao("CRM já cadastrado");
           }
           else
               return null;
        }
    }
4 respostas
solução!

Uma outra opção seria criar um mapeamento que associa cada campo a uma mensagem de erro correspondente. Isso te permite atualizar as mensagens facilmente no futuro, sem precisar lidar com muitos ifs complicados.

private record MensagemErroValidacao(String mensagem) {

    private static final Map<String, String> MENSAGENS_ERRO = Map.of(
        "email", "E-mail já cadastrado",
        "crm", "CRM já cadastrado"
    );

    public static MensagemErroValidacao registroDuplicado(String campo) {
        String mensagem = MENSAGENS_ERRO.get(campo);
        if (mensagem != null) {
            return new MensagemErroValidacao(mensagem);
        } else {
            return null;
        }
    }
}
# 

Essa solução é mais escalável e fácil de manter do que muitos ifs, mas pode ser um pouco mais complexa de implementar no início.

Entendi, mas meu problema é que o campo vem dentro do erro

could not execute statement; SQL [n/a]; constraint [tb_pacientes.email]]

Ae no if tava usando um contains pra pegar o campo

Você pode adicionar uma condição extra no método registroDuplicado para verificar se o campo recebido como parâmetro é um dos campos suportados pela sua aplicação.

Por exemplo:

private record MensagemErroValidacao(String mensagem) {
    public static MensagemErroValidacao registroDuplicado(String campo) {
        if (campo.contains("email")) {
            return new MensagemErroValidacao("E-mail já cadastrado");
        } else if (campo.contains("crm")) {
            return new MensagemErroValidacao("CRM já cadastrado");
        } else if (campo.contains("nome")) {
            return new MensagemErroValidacao("Nome já cadastrado");
        } else {
            return new MensagemErroValidacao("Campo " + campo + " já cadastrado");
        }
    }
}

a condição extra else if (campo.contains("nome")) foi adicionada para verificar se o campo é o campo "nome" e, em seguida, uma mensagem de erro correspondente é retornada. Se o campo não for nenhum dos campos suportados uma mensagem genérica é retornada com o nome do campo que foi recebido como parâmetro. Assim você pode especificar o campo que não está cadastrado na mensagem de erro.

Alterei o método dessa forma pra funcionar

        public static MensagemErroValidacao registroDuplicado(String erro) {
            String mensagem = null;
            for (String campo : MENSAGENS_ERRO.keySet()) {
                if (erro.contains(campo)) {
                    mensagem = MENSAGENS_ERRO.get(campo);
                    break;
                }
            }
            if (mensagem != null) {
                return new MensagemErroValidacao(mensagem);
            } else {
                return null;
            }
        }