Spring Bean Disorders Method with @Transactional

Just a little, I’m a new developer who recently took on a major project after the senior developer left the company before I could develop a full understanding of how he structured it. I will try to explain my problem as best as possible.

This application creates several MessageListner threads to read objects from JMS queues. After the object is received, the data is processed based on some business logic, and then displayed on the save object, which will be stored in the oracle database using the sleeping EntityManager.

Until a few weeks ago there were no serious problems with this configuration in the last year or so, since I joined the project. But for one of the queues (the problem is allocated for this particular queue), a spring-driven bean that processes the received object hangs according to the method below. My debugging led me to the conclusion that she completed everything within the method, but hangs after completion. After several weeks of trying to resolve this, I am at the end of my rope with this problem. Any help with this would be greatly appreciated.

Since each MessageListner receives its own processor, this suspension method only affects incoming data in a single queue.

@Transactional(propagation = Propagation.REQUIRES_NEW , timeout = 180) public void update(UserRelatedData userData, User user,Company company,...) { ... .... //business logic performed on user object .... ...... entityMgr.persist(user); //business logic performed on userData object ... .... entityMgr.persist(userData); ... .... entityMgr.flush(); } 

I inserted the debug statements just to go through this method, and it completes everything, including entityMgr.flush. ().

+4
source share
4 answers

Such problems can occur when the underlying database has locks from uncommitted changes.

I would suggest that some other code did insert / delete in userData table (s) outside of a transaction or in a transaction that takes a very long time, as this is a batch job or the like. You should analyze all the code referencing these tables and look for the missing @Transactional.

+4
source

REQUIRES_NEW can hang in a test context because the transaction manager used in unit testing does not support nested transactions ... From the Javadoc JpaTransactionManager:

 * <p>This transaction manager supports nested transactions via JDBC 3.0 Savepoints. * The {@link #setNestedTransactionAllowed "nestedTransactionAllowed"} flag defaults * to {@code false} though, since nested transactions will just apply to the JDBC * Connection, not to the JPA EntityManager and its cached entity objects and related * context. You can manually set the flag to {@code true} if you want to use nested * transactions for JDBC access code which participates in JPA transactions (provided * that your JDBC driver supports Savepoints). <i>Note that JPA itself does not support * nested transactions! Hence, do not expect JPA access code to semantically * participate in a nested transaction.</i> 

So it is clear if you do not call (@Java config) or set the equivalent flag in your XML configuration:

 txManager.setNestedTransactionAllowed(true); 

or if your driver does not support Savepoints, it is "normal" to get a problem with REQUIRES_NEW ... (Some may prefer the exception "non-nested transactions are not supported")

+2
source

Unfortunately, I have the same problem with Propagation.REQUIRES_NEW . Resolving the issue resolves the issue. The debugger shows me that the commit method is hanging (called from the implementation of the @Transactional aspect).

The problem appears only in the test context of spring, when the application is deployed to the application server, it works fine.

+1
source

Next to this answer , you can also check the isolation level of your transaction - perhaps this is too restrictive.

Is the update() method used forever, or does it throw an exception after a timeout?

0
source

Source: https://habr.com/ru/post/1381631/


All Articles