How to handle JPA unique constraint violations?

巧了我就是萌 提交于 2019-11-27 02:33:33

问题


When a unique constraint is violated, a javax.persistence.RollbackException is thrown. But there could be multiple reasons to throw a RollbackException. How can I find out that a unique constraint was violated?

try {
    repository.save(article);
}
catch(javax.persistence.RollbackException e) {
    // how to find out the reason for the rollback exception?
}

回答1:


How can I find out that a unique constraint was violated?

Exception are chained, you have to call getCause() recursively to get the provider specific exception (and maybe go down to the SQLException) to translate it into something your application can handle nicely for your user. The following will print the chain of exception:

for (t = e.getCause(); t != null; t = t.getCause()) {
    logger.debug("Exception:" + t);
}

For the exception handling and the "translation", you could do something like what Spring does (see the various JpaDialect classes, e.g. HibernateJpaDialect to get an idea).

All this is not nice, this code won't be portable and finding what attribute(s) caused the violation won't be easy. This somehow confirms that there is no elegant and portable way to handle constraint violations in JPA.




回答2:


Use e.getCause() to examine what caused the rollback.




回答3:


compiler returns the exception SQLIntegrityConstraintViolationException, while trying to violate unique constraint.

Use the following catch block concept, to handle proper exceptions.

catch(SQLIntegrityConstraintViolationException e) 
{
  // Error message for integrity constraint violation
}
catch(Exception e)
{
 // Other error messages
}



回答4:


You can use the following :

If you are using spring framework then you can use :

org.springframework.dao.DataIntegrityViolationException

If standard JPA following can be used

org.hibernate.exception.ConstraintViolationException

At sql level following can be used :

java.sql.SQLIntegrityConstraintViolationException




回答5:


This might very late for you but here's how I solved it for PostGres.

catch (DataIntegrityViolationException e) {

            for (Throwable t = e.getCause(); t != null; t = t.getCause()) {

                if (PSQLException.class.equals(t.getClass())) {
                    PSQLException postgresException = (PSQLException) t;

                    // In Postgres SQLState 23505=unique_violation
                    if ("23505".equals(postgresException.getSQLState())) {
                        throw new CustomDataAlreadyExistsException("YourErrorCode", e);
                    }
                }
            }
            throw new SomeOtherException("YourErrorCode2", e);

        }



回答6:


i think printing the stack trace will help you to know this. e.printStackTrace();




回答7:


You can do like this :

StringWriter writer=new StringWriter(); //remains the message from stack trace.
e.printStackTrace(new PrintWriter(writer));
String message=writer.toString(); // gets the message of full stack trace.

And then view the information of exception.



来源:https://stackoverflow.com/questions/3502279/how-to-handle-jpa-unique-constraint-violations

易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!