handle error during remove record - java

void deleteFilm(#PathVariable(value = "id") Integer id) {
try {
filmService.deleteFilm(id);
}
catch (ConstraintViolationException e) {
throw e;
}
catch (SQLIntegrityConstraintViolationException ex) {
}
}
2018-08-15 18:12:10.075 WARN 8568 --- [io-8080-exec-10] o.h.engine.jdbc.spi.SqlExceptionHelper : SQL Error: 1451, SQLState: 23000
2018-08-15 18:12:10.075 ERROR 8568 --- [io-8080-exec-10] o.h.engine.jdbc.spi.SqlExceptionHelper : Cannot delete or update a parent row: a foreign key constraint fails (`todo`.`seance`, CONSTRAINT `FKchlcmip8ejlfuo4c990k5ry8y` FOREIGN KEY (`film_id`) REFERENCES `film` (`id`))
2018-08-15 18:12:10.077 INFO 8568 --- [io-8080-exec-10] o.h.e.j.b.internal.AbstractBatchImpl : HHH000010: On release of batch it still contained JDBC statements
2018-08-15 18:12:10.080 ERROR 8568 --- [io-8080-exec-10] o.h.i.ExceptionMapperStandardImpl : HHH000346: Error during managed flush [org.hibernate.exception.ConstraintViolationException: could not execute statement]
2018-08-15 18:12:10.154 ERROR 8568 --- [io-8080-exec-10] o.a.c.c.C.[.[.[/].[dispatcherServlet] : Servlet.service() for servlet [dispatcherServlet] in context with path [] threw exception [Request processing failed; nested exception is org.springframework.dao.DataIntegrityViolationException: could not execute statement; SQL [n/a]; constraint [null]; nested exception is org.hibernate.exception.ConstraintViolationException: could not execute statement] with root cause
com.mysql.jdbc.exceptions.jdbc4.MySQLIntegrityConstraintViolationException: Cannot delete or update a parent row: a foreign key constraint fails (`todo`.`seance`, CONSTRAINT `FKchlcmip8ejlfuo4c990k5ry8y` FOREIGN KEY (`film_id`) REFERENCES `film` (`id`))
at sun.reflect.NativeConstructorAccessorImpl.newInstance0(Native Method) ~[na:1.8.0_131]
at sun.reflect.NativeConstructorAccessorImpl.newInstance(NativeConstructorAccessorImpl.java:62) ~[na:1.8.0_131]
at sun.reflect.DelegatingConstructorAccessorImpl.newInstance(DelegatingConstructorAccessorImpl.java:45) ~[na:1.8.0_131]
at java.lang.reflect.Constructor.newInstance(Constructor.java:423) ~[na:1.8.0_131]
ConstraintViolationException don't catch error and using SQLIntegrityConstraintViolationException i have is never throw by corresponding try block
i read that
java.lang.Object
java.lang.Throwable
java.lang.Exception
java.sql.SQLException
java.sql.SQLNonTransientException
java.sql.SQLIntegrityConstraintViolationException
com.mysql.jdbc.exceptions.jdbc4.MySQLIntegrityConstraintViolationException
jdbc4.MySQLIntegrityConstraintViolationException inherits from SQLEXception but this exception is never throw by try block

This is a programming error and has to be corrected by choosing how to handle the foreign key.
The problem is that you're deleting a parent record, leaving orphan entries (film_id in todo.seance, which references the film ID)
You have two options
Do cascade deletion, so that if a film is deleted, corresponding seance records are also deleted (automatically done by the database). MySQL's documentation on forein keys is here (with reference options, which include on delete cascade, among other things)
Change application logic to first delete seance entries for the film_id before deleting the parent film record.
Remember that you need to explicitly throw the exception:
catch (SQLIntegrityConstraintViolationException ex) {
//Assuming deleteFilm() has the correct throws clause
throw ex; //you are not doing this.
}

Related

sql exceptions when trying to insert duplicate records into the database

I have the below method which checks if a user exists and then adds it to the database if it does not exist.
#Transactional(isolation = Isolation.READ_COMMITTED)
public Optional<User> create(User user) {
Optional<User> userOptional = userRepository.findByEmail(user.getEmail());
if (userOptional.isPresent()) {
return Optional.empty();
}
User savedUser = userRepository.save(user);
return Optional.of(savedUser);
}
two threads t1 and t2 are trying to save the same user with the same email(example#example.com). The following occurs:
t1 cant find user
t2 also cant find user
t1 adds user to database
t2 tries to add user to database but fails as record already exists and throws following error:
2019-10-02 18:28:43 WARN UKPC000029 --- [nio-8090-exec-2]
o.h.e.j.s.SqlExceptionHelper : SQL Error: 1062, SQLState: 23000
2019-10-02 18:28:43 ERROR UKPC000029 --- [nio-8090-exec-2]
o.h.e.j.s.SqlExceptionHelper : Duplicate entry 'example#example.com' for key 'UK_tcks72p02h4dp13cbhxne17ad'
2019-10-02 18:28:43 ERROR UKPC000029 --- [nio-8090-exec-2] o.h.i.ExceptionMapperStandardImpl : HHH000346: Error during managed flush [org.hibernate.exception.ConstraintViolationException: could not execute statement]
2019-10-02 18:28:43 DEBUG UKPC000029 --- [nio-8090-exec-2] o.s.o.j.JpaTransactionManager : Initiating transaction rollback after commit exception
org.springframework.dao.DataIntegrityViolationException: could not execute statement; SQL [n/a]; constraint [UK_tcks72p02h4dp13cbhxne17ad]; nested exception is org.hibernate.exception.ConstraintViolationException: could not execute statement
at org.springframework.orm.jpa.vendor.HibernateJpaDialect.convertHibernateAccessException(HibernateJpaDialect.java:296)
at org.springframework.orm.jpa.vendor.HibernateJpaDialect.translateExceptionIfPossible(HibernateJpaDialect.java:253)
at org.springframework.orm.jpa.JpaTransactionManager.doCommit(JpaTransactionManager.java:536)
In order to get around this error I tried to use serializble isolation level
#Transactional(isolation = Isolation.SERIALIZABLE)
However in the same scenario I got the following error:
2019-10-02 18:52:56 WARN UKPC000029 --- [nio-8090-exec-2] o.h.e.j.s.SqlExceptionHelper : SQL Error: 1213, SQLState: 40001
2019-10-02 18:52:56 ERROR UKPC000029 --- [nio-8090-exec-2] o.h.e.j.s.SqlExceptionHelper : Deadlock found when trying to get lock; try restarting transaction
2019-10-02 18:52:56 ERROR UKPC000029 --- [nio-8090-exec-2] o.h.i.ExceptionMapperStandardImpl : HHH000346: Error during managed flush [org.hibernate.exception.LockAcquisitionException: could not execute statement]
2019-10-02 18:52:56 DEBUG UKPC000029 --- [nio-8090-exec-1] o.s.o.j.JpaTransactionManager : Not closing pre-bound JPA EntityManager after transaction
2019-10-02 18:52:56 DEBUG UKPC000029 --- [nio-8090-exec-2] o.s.o.j.JpaTransactionManager : Initiating transaction rollback after commit exception
org.springframework.dao.CannotAcquireLockException: could not execute statement; SQL [n/a]; nested exception is org.hibernate.exception.LockAcquisitionException: could not execute statement
at org.springframework.orm.jpa.vendor.HibernateJpaDialect.convertHibernateAccessException(HibernateJpaDialect.java:287)
at org.springframework.orm.jpa.vendor.HibernateJpaDialect.translateExceptionIfPossible(HibernateJpaDialect.java:253)
at org.springframework.orm.jpa.JpaTransactionManager.doCommit(JpaTransactionManager.java:536)
I was under the impression that both transactions would be done 1 after the other?
The following link
isolation explained
SERIALIZABLE isolation level is the most restrictive of all isolation levels. Transactions are executed with locking at all levels (read, range and write locking) so they appear as if they were executed in a serialized way. This leads to a scenario where none of the issues mentioned above may occur, but in the other way we don't allow transaction concurrency and consequently introduce a performance penalty.
However both threads are still checking for the user email even though the 1st transaction hasnt finished? What is the best way to deal with this problem? Is using java locks acceptable in this case?

hibernate_sequence creates duplicate key 'PRIMARY'

A previously working Spring-Boot application came up with a bug. It last worked 100%. I made zero changes to the code. It seems duplicate primary keys are being entered on the hibernate_sequence table.
Worked for three hours today with my mentor developer. We are both stumped. We've tried using a different database, renaming and launching a back up of the app. Have tried different ways to generate ids on the Entities. We updated Spring-Boot to most current version. Each time we drop/delete the hibernate_sequence table, you can see in the console when it is generated on initial app start up, you get Hibernate: insert into hibernate_sequence values (1) twice. At this point, since the code has not changed and it worked fine last Wednesday, my mentor feels it might be an update somewhere we are not aware of?
Github Repo of working code : https://github.com/chrisyoung0101/DrinkWithWineApp
IMG 1 : database before hibernate_sequence is generated
/ IMG 2 : console on app start up /
IMG 3 : database before hibernate_sequence is generated
Errors after trying to save to Pairing table in MySQL :
2019-05-19 18:33:23.698 WARN 4405 --- [nio-8080-exec-7] o.h.engine.jdbc.spi.SqlExceptionHelper : SQL Error: 1062, SQLState: 23000
2019-05-19 18:33:23.698 ERROR 4405 --- [nio-8080-exec-7] o.h.engine.jdbc.spi.SqlExceptionHelper : Duplicate entry '1' for key 'PRIMARY'
2019-05-19 18:33:23.702 ERROR 4405 --- [nio-8080-exec-7] o.h.i.ExceptionMapperStandardImpl : HHH000346: Error during managed flush [org.hibernate.exception.ConstraintViolationException: could not execute statement]
2019-05-19 18:33:23.717 ERROR 4405 --- [nio-8080-exec-7] o.a.c.c.C.[.[.[/].[dispatcherServlet] : Servlet.service() for servlet [dispatcherServlet] in context with path [] threw exception [Request processing failed; nested exception is org.springframework.dao.DataIntegrityViolationException: could not execute statement; SQL [n/a]; constraint [PRIMARY]; nested exception is org.hibernate.exception.ConstraintViolationException: could not execute statement] with root cause
com.mysql.jdbc.exceptions.jdbc4.MySQLIntegrityConstraintViolationException: Duplicate entry '1' for key 'PRIMARY'

How to Set Offset and limit for My Native SQL query using SpringJPA

I have created query to fetch Offset and Limit values from Local host URL.But I am getting below error.
Hibernate: SELECT * FROM mail_user u WHERE u.mailaddr LIKE ? AND u.userName LIKE ? AND u.sendflag =? AND (u.info01 LIKE ? OR u.info02 LIKE ? OR u.info03 LIKE ? OR u.info04 LIKE ? OR u.info05 LIKE ? ) ORDER BY u.userName ASC LIMIT ?
2018-08-30 12:58:47.905 WARN 9896 --- [nio-8080-exec-1] o.h.engine.jdbc.spi.SqlExceptionHelper : SQL Error: 1064, SQLState: 42000
2018-08-30 12:58:47.905 ERROR 9896 --- [nio-8080-exec-1] o.h.engine.jdbc.spi.SqlExceptionHelper : You have an error in your SQL syntax; check the manual that corresponds to your MySQL server version for the right syntax to use near 'null' at line 1
2018-08-30 12:58:47.909 DEBUG 9896 --- [nio-8080-exec-1] .m.m.a.ExceptionHandlerExceptionResolver : Resolving exception from handler [public java.util.List<usergroup.restapi.models.UserDetails> usergroup.restapi.controller.UserSearchController.getGroupList(java.lang.String,java.lang.String,java.lang.String,java.lang.String,java.lang.String,java.lang.String,java.lang.String,java.lang.String,java.lang.String)]: org.springframework.dao.InvalidDataAccessResourceUsageException: could not extract ResultSet; SQL [n/a]; nested exception is org.hibernate.exception.SQLGrammarException: could not extract ResultSet
2018-08-30 12:58:47.910 DEBUG 9896 --- [nio-8080-exec-1] .w.s.m.a.ResponseStatusExceptionResolver : Resolving exception from handler [public java.util.List<usergroup.restapi.models.UserDetails> usergroup.restapi.controller.UserSearchController.getGroupList(java.lang.String,java.lang.String,java.lang.String,java.lang.String,java.lang.String,java.lang.String,java.lang.String,java.lang.String,java.lang.String)]: org.springframework.dao.InvalidDataAccessResourceUsageException: could not extract ResultSet; SQL [n/a]; nested exception is org.hibernate.exception.SQLGrammarException: could not extract ResultSet
2018-08-30 12:58:47.911 DEBUG 9896 --- [nio-8080-exec-1] .w.s.m.s.DefaultHandlerExceptionResolver : Resolving exception from handler [public java.util.List<usergroup.restapi.models.UserDetails> usergroup.restapi.controller.UserSearchController.getGroupList(java.lang.String,java.lang.String,java.lang.String,java.lang.String,java.lang.String,java.lang.String,java.lang.String,java.lang.String,java.lang.String)]: org.springframework.dao.InvalidDataAccessResourceUsageException: could not extract ResultSet; SQL [n/a]; nested exception is org.hibernate.exception.SQLGrammarException: could not extract ResultSet
2018-08-30 12:58:47.916 DEBUG 9896 --- [nio-8080-exec-1] o.s.web.servlet.DispatcherServlet : Could not complete request
org.springframework.dao.InvalidDataAccessResourceUsageException: could not extract ResultSet; SQL [n/a]; nested exception is org.hibernate.exception.SQLGrammarException: could not extract ResultSet
at org.springframework.orm.jpa.vendor.HibernateJpaDialect.convertHibernateAccessException(HibernateJpaDialect.java:242) ~[spring-orm-5.0.6.RELEASE.jar:5.0.6.RELEASE]
at org.springframework.orm.jpa.vendor.HibernateJpaDialect.translateExceptionIfPossible(HibernateJpaDialect.java:225) ~[spring-orm-5.0.6.RELEASE.jar:5.0.6.RELEASE]
at org.springframework.orm.jpa.AbstractEntityManagerFactoryBean.translateExceptionIfPossible(AbstractEntityManagerFactoryBean.java:527) ~[spring-orm-5.0.6.RELEASE.jar:5.0.6.RELEASE]
at org.springframework.dao.support.ChainedPersistenceExceptionTranslator.translateExceptionIfPossible(ChainedPersistenceExceptionTranslator.java:61) ~[spring-tx-5.0.6.RELEASE.jar:5.0.6.RELEASE]
My Native SQL Query as below:
#Query(
value = "SELECT * FROM mail_user u WHERE u.mailaddr LIKE %:mailaddr% AND u.userName LIKE %:userName% AND u.sendflag =:sendFlag AND "+"(u.info01 LIKE %:info01% OR u.info02 LIKE %:info02% OR u.info03 LIKE %:info03% OR u.info04 LIKE %:info04% OR u.info05 LIKE %:info05% )"+" ORDER BY u.userName ASC LIMIT :limit",nativeQuery = true
) public List<UserDetails> findByEmailAndUserAndFlag(#Param("mailaddr") String mailaddr,#Param("userName") String userName,#Param("sendFlag") String sendFlag,
#Param("info01") String info01,#Param("info02") String info02,#Param("info03") String info03,#Param("info04") String info04,#Param("info05") String info05,
#Param("limit") String limit
);

jdbc4.MySQLSyntaxErrorException: error in your SQL syntax; check the manual MySQL server version for the right syntax to use near ') )' at line 1

I am facing problem when trying to fetch data using crudRepository.
i am using native query to fetch count of records from data base but i am getting the following error.
com.mysql.jdbc.exceptions.jdbc4.MySQLSyntaxErrorException: You have an error in your SQL syntax; check the manual that corresponds to your MySQL server version for the right syntax to use near ') )' at line 1
at sun.reflect.NativeConstructorAccessorImpl.newInstance0(Native Method) ~[na:1.8.0_171]
at sun.reflect.NativeConstructorAccessorImpl.newInstance(Unknown Source) ~[na:1.8.0_171]
my query in repository is:
#Query(value = "select count(1) from user_records upr where RECORD_ID in ( SELECT record_id FROM region_record_relation where region_id in :regionIds) ", nativeQuery = true)
public int findAllRecordsforRegionIds(#Param("regionIds") List<Long> regionIds);
i dont have any idea how to solve this problem. i am using Mysql database.
show-sql setting is turned on. but all i get is:
2018-08-02 20:06:17.210 WARN 3764 --- [nio-8088-exec-2] o.h.engine.jdbc.spi.SqlExceptionHelper : SQL Error: 1064, SQLState: 42000
2018-08-02 20:06:17.210 ERROR 3764 --- [nio-8088-exec-2] o.h.engine.jdbc.spi.SqlExceptionHelper : You have an error in your SQL syntax; check the manual that corresponds to your MySQL server version for the right syntax to use near ') )' at line 1
2018-08-02 20:06:17.231 ERROR 3764 --- [nio-8088-exec-2] o.a.c.c.C.[.[.[/].[dispatcherServlet] : Servlet.service() for servlet [dispatcherServlet] in context with path [] threw exception [Request processing failed; nested exception is org.springframework.orm.jpa.JpaSystemException: org.hibernate.exception.SQLGrammarException: could not extract ResultSet; nested exception is javax.persistence.PersistenceException: org.hibernate.exception.SQLGrammarException: could not extract ResultSet] with root cause
com.mysql.jdbc.exceptions.jdbc4.MySQLSyntaxErrorException: You have an error in your SQL syntax; check the manual that corresponds to your MySQL server version for the right syntax to use near ') )' at line 1
at sun.reflect.NativeConstructorAccessorImpl.newInstance0(Native Method) ~[na:1.8.0_171]
at sun.reflect.NativeConstructorAccessorImpl.newInstance(Unknown Source) ~[na:1.8.0_171]
at sun.reflect.DelegatingConstructorAccessorImpl.newInstance(Unknown Source) ~[na:1.8.0_171]
#Query(value = "select count(1) from user_records upr where RECORD_ID in ( SELECT record_id FROM region_record_relation where region_id in :regionIds)
Should be
#Query(value = "select count(1) from user_records upr where RECORD_ID in ( SELECT record_id FROM region_record_relation where region_id in (:regionIds)))
There are better ways to write this that would be more efficient. But this should solve the error.

MySql throws exception when Update statement does not find a record

I'm using MySql 5.5, queries are executing via Spring Framework(JdbcTemplate) over Jboss 5.1
I'm experiencing an issue which causes an update statement to throw the following:
javax.ejb.EJBTransactionRolledbackException: PreparedStatementCallback; uncategorized SQLException for SQL [ UPDATE events SET last_update=? WHERE account_id=? ]; SQL state [HY000]; error
code [1032]; Can't find record in 'events'; nested exception is java.sql.SQLException: Can't find record in 'events
'
My question is why do I get an exception when the record is not found(it is expected behavior) and how can I prevent that from happening.
Many Thanks
Yaniv
More Details
The table has no foreign keys. it has a total of 15 fields, out of which on is an auto increment id, and 4 others are indexed. The query is `UPDATE events SET last_update=? WHERE account_id=?
Here is also the stack trace of the actual SQLException:
Caused by: java.sql.SQLException: Can't find record in 'events'
at com.mysql.jdbc.SQLError.createSQLException(SQLError.java:1073)
at com.mysql.jdbc.MysqlIO.checkErrorPacket(MysqlIO.java:3609)
at com.mysql.jdbc.MysqlIO.checkErrorPacket(MysqlIO.java:3541)
at com.mysql.jdbc.MysqlIO.sendCommand(MysqlIO.java:2002)
at com.mysql.jdbc.MysqlIO.sqlQueryDirect(MysqlIO.java:2163)
at com.mysql.jdbc.ConnectionImpl.execSQL(ConnectionImpl.java:2624)
at com.mysql.jdbc.PreparedStatement.executeInternal(PreparedStatement.java:2127)
at com.mysql.jdbc.PreparedStatement.executeUpdate(PreparedStatement.java:2427)
at com.mysql.jdbc.PreparedStatement.executeUpdate(PreparedStatement.java:2345)
at com.mysql.jdbc.PreparedStatement.executeUpdate(PreparedStatement.java:2330)
at org.jboss.resource.adapter.jdbc.WrappedPreparedStatement.executeUpdate(WrappedPreparedStatement.java:365)
at org.springframework.jdbc.core.JdbcTemplate$2.doInPreparedStatement(JdbcTemplate.java:818)
at org.springframework.jdbc.core.JdbcTemplate$2.doInPreparedStatement(JdbcTemplate.java:1)
at org.springframework.jdbc.core.JdbcTemplate.execute(JdbcTemplate.java:587)

Categories