Search in sources :

Example 1 with UnexpectedRollbackException

use of cn.taketoday.transaction.UnexpectedRollbackException in project today-infrastructure by TAKETODAY.

the class JdbcTransactionManagerTests method doTestParticipatingTransactionWithRollbackOnly.

private void doTestParticipatingTransactionWithRollbackOnly(boolean failEarly) throws Exception {
    given(con.isReadOnly()).willReturn(false);
    if (failEarly) {
        tm.setFailEarlyOnGlobalRollbackOnly(true);
    }
    boolean condition2 = !TransactionSynchronizationManager.hasResource(ds);
    assertThat(condition2).as("Hasn't thread connection").isTrue();
    boolean condition1 = !TransactionSynchronizationManager.isSynchronizationActive();
    assertThat(condition1).as("Synchronization not active").isTrue();
    TransactionStatus ts = tm.getTransaction(new DefaultTransactionDefinition());
    TestTransactionSynchronization synch = new TestTransactionSynchronization(ds, TransactionSynchronization.STATUS_ROLLED_BACK);
    TransactionSynchronizationManager.registerSynchronization(synch);
    boolean outerTransactionBoundaryReached = false;
    try {
        assertThat(ts.isNewTransaction()).as("Is new transaction").isTrue();
        final TransactionTemplate tt = new TransactionTemplate(tm);
        tt.execute(new TransactionCallbackWithoutResult() {

            @Override
            protected void doInTransactionWithoutResult(TransactionStatus status) throws RuntimeException {
                boolean condition1 = !status.isNewTransaction();
                assertThat(condition1).as("Is existing transaction").isTrue();
                assertThat(status.isRollbackOnly()).as("Is not rollback-only").isFalse();
                tt.execute(new TransactionCallbackWithoutResult() {

                    @Override
                    protected void doInTransactionWithoutResult(TransactionStatus status) throws RuntimeException {
                        assertThat(TransactionSynchronizationManager.hasResource(ds)).as("Has thread connection").isTrue();
                        assertThat(TransactionSynchronizationManager.isSynchronizationActive()).as("Synchronization active").isTrue();
                        boolean condition = !status.isNewTransaction();
                        assertThat(condition).as("Is existing transaction").isTrue();
                        status.setRollbackOnly();
                    }
                });
                boolean condition = !status.isNewTransaction();
                assertThat(condition).as("Is existing transaction").isTrue();
                assertThat(status.isRollbackOnly()).as("Is rollback-only").isTrue();
            }
        });
        outerTransactionBoundaryReached = true;
        tm.commit(ts);
        fail("Should have thrown UnexpectedRollbackException");
    } catch (UnexpectedRollbackException ex) {
        // expected
        if (!outerTransactionBoundaryReached) {
            tm.rollback(ts);
        }
        if (failEarly) {
            assertThat(outerTransactionBoundaryReached).isFalse();
        } else {
            assertThat(outerTransactionBoundaryReached).isTrue();
        }
    }
    boolean condition = !TransactionSynchronizationManager.hasResource(ds);
    assertThat(condition).as("Hasn't thread connection").isTrue();
    assertThat(synch.beforeCommitCalled).isFalse();
    assertThat(synch.beforeCompletionCalled).isTrue();
    assertThat(synch.afterCommitCalled).isFalse();
    assertThat(synch.afterCompletionCalled).isTrue();
    verify(con).rollback();
    verify(con).close();
}
Also used : DefaultTransactionDefinition(cn.taketoday.transaction.support.DefaultTransactionDefinition) TransactionTemplate(cn.taketoday.transaction.support.TransactionTemplate) TransactionStatus(cn.taketoday.transaction.TransactionStatus) UnexpectedRollbackException(cn.taketoday.transaction.UnexpectedRollbackException) TransactionCallbackWithoutResult(cn.taketoday.transaction.support.TransactionCallbackWithoutResult)

Example 2 with UnexpectedRollbackException

use of cn.taketoday.transaction.UnexpectedRollbackException in project today-infrastructure by TAKETODAY.

the class AbstractReactiveTransactionAspectTests method cannotCommitTransaction.

/**
 * Simulate failure of the underlying transaction infrastructure to commit.
 * Check that the target method was invoked, but that the transaction
 * infrastructure exception was thrown to the client
 */
@Test
public void cannotCommitTransaction() throws Exception {
    TransactionAttribute txatt = new DefaultTransactionAttribute();
    Method m = setNameMethod;
    MapTransactionAttributeSource tas = new MapTransactionAttributeSource();
    tas.register(m, txatt);
    // Method m2 = getNameMethod;
    // No attributes for m2
    ReactiveTransactionManager rtm = mock(ReactiveTransactionManager.class);
    ReactiveTransaction status = mock(ReactiveTransaction.class);
    given(rtm.getReactiveTransaction(txatt)).willReturn(Mono.just(status));
    UnexpectedRollbackException ex = new UnexpectedRollbackException("foobar", null);
    given(rtm.commit(status)).willReturn(Mono.error(ex));
    given(rtm.rollback(status)).willReturn(Mono.empty());
    DefaultTestBean tb = new DefaultTestBean();
    TestBean itb = (TestBean) advised(tb, rtm, tas);
    String name = "new name";
    Mono.from(itb.setName(name)).as(StepVerifier::create).consumeErrorWith(throwable -> {
        assertThat(throwable.getClass()).isEqualTo(RuntimeException.class);
        assertThat(throwable.getCause()).isEqualTo(ex);
    }).verify();
    // Should have invoked target and changed name
    itb.getName().as(StepVerifier::create).expectNext(name).verifyComplete();
}
Also used : BeforeEach(org.junit.jupiter.api.BeforeEach) ReactiveTransaction(cn.taketoday.transaction.ReactiveTransaction) StepVerifier(reactor.test.StepVerifier) Publisher(org.reactivestreams.Publisher) Assertions.assertThat(org.assertj.core.api.Assertions.assertThat) ReactiveTransactionManager(cn.taketoday.transaction.ReactiveTransactionManager) Mono(reactor.core.publisher.Mono) Mockito.times(org.mockito.Mockito.times) TransactionContext(cn.taketoday.transaction.reactive.TransactionContext) Fail.fail(org.assertj.core.api.Fail.fail) Mockito.verify(org.mockito.Mockito.verify) Mockito.verifyNoInteractions(org.mockito.Mockito.verifyNoInteractions) Test(org.junit.jupiter.api.Test) CannotCreateTransactionException(cn.taketoday.transaction.CannotCreateTransactionException) BDDMockito.given(org.mockito.BDDMockito.given) TransactionSystemException(cn.taketoday.transaction.TransactionSystemException) UnexpectedRollbackException(cn.taketoday.transaction.UnexpectedRollbackException) Method(java.lang.reflect.Method) Mockito.mock(org.mockito.Mockito.mock) Method(java.lang.reflect.Method) ReactiveTransaction(cn.taketoday.transaction.ReactiveTransaction) ReactiveTransactionManager(cn.taketoday.transaction.ReactiveTransactionManager) UnexpectedRollbackException(cn.taketoday.transaction.UnexpectedRollbackException) StepVerifier(reactor.test.StepVerifier) Test(org.junit.jupiter.api.Test)

Example 3 with UnexpectedRollbackException

use of cn.taketoday.transaction.UnexpectedRollbackException in project today-framework by TAKETODAY.

the class JtaTransactionManager method doCommit.

@Override
protected void doCommit(DefaultTransactionStatus status) {
    JtaTransactionObject txObject = (JtaTransactionObject) status.getTransaction();
    try {
        int jtaStatus = txObject.getUserTransaction().getStatus();
        if (jtaStatus == Status.STATUS_NO_TRANSACTION) {
            // In any case, the transaction is already fully cleaned up.
            throw new UnexpectedRollbackException("JTA transaction already completed - probably rolled back");
        }
        if (jtaStatus == Status.STATUS_ROLLEDBACK) {
            // IllegalStateException expected on JBoss; call still necessary.
            try {
                txObject.getUserTransaction().rollback();
            } catch (IllegalStateException ex) {
                if (logger.isDebugEnabled()) {
                    logger.debug("Rollback failure with transaction already marked as rolled back: {}", ex.toString());
                }
            }
            throw new UnexpectedRollbackException("JTA transaction already rolled back (probably due to a timeout)");
        }
        txObject.getUserTransaction().commit();
    } catch (RollbackException ex) {
        throw new UnexpectedRollbackException("JTA transaction unexpectedly rolled back (maybe due to a timeout)", ex);
    } catch (HeuristicMixedException ex) {
        throw new HeuristicCompletionException(HeuristicCompletionException.STATE_MIXED, ex);
    } catch (HeuristicRollbackException ex) {
        throw new HeuristicCompletionException(HeuristicCompletionException.STATE_ROLLED_BACK, ex);
    } catch (IllegalStateException ex) {
        throw new TransactionSystemException("Unexpected internal transaction state", ex);
    } catch (SystemException ex) {
        throw new TransactionSystemException("JTA failure on commit", ex);
    }
}
Also used : HeuristicRollbackException(jakarta.transaction.HeuristicRollbackException) TransactionSystemException(cn.taketoday.transaction.TransactionSystemException) SystemException(jakarta.transaction.SystemException) HeuristicMixedException(jakarta.transaction.HeuristicMixedException) UnexpectedRollbackException(cn.taketoday.transaction.UnexpectedRollbackException) TransactionSystemException(cn.taketoday.transaction.TransactionSystemException) HeuristicRollbackException(jakarta.transaction.HeuristicRollbackException) RollbackException(jakarta.transaction.RollbackException) UnexpectedRollbackException(cn.taketoday.transaction.UnexpectedRollbackException) HeuristicCompletionException(cn.taketoday.transaction.HeuristicCompletionException)

Example 4 with UnexpectedRollbackException

use of cn.taketoday.transaction.UnexpectedRollbackException in project today-framework by TAKETODAY.

the class JdbcTransactionManagerTests method doTestParticipatingTransactionWithRollbackOnly.

private void doTestParticipatingTransactionWithRollbackOnly(boolean failEarly) throws Exception {
    given(con.isReadOnly()).willReturn(false);
    if (failEarly) {
        tm.setFailEarlyOnGlobalRollbackOnly(true);
    }
    boolean condition2 = !TransactionSynchronizationManager.hasResource(ds);
    assertThat(condition2).as("Hasn't thread connection").isTrue();
    boolean condition1 = !TransactionSynchronizationManager.isSynchronizationActive();
    assertThat(condition1).as("Synchronization not active").isTrue();
    TransactionStatus ts = tm.getTransaction(new DefaultTransactionDefinition());
    TestTransactionSynchronization synch = new TestTransactionSynchronization(ds, TransactionSynchronization.STATUS_ROLLED_BACK);
    TransactionSynchronizationManager.registerSynchronization(synch);
    boolean outerTransactionBoundaryReached = false;
    try {
        assertThat(ts.isNewTransaction()).as("Is new transaction").isTrue();
        final TransactionTemplate tt = new TransactionTemplate(tm);
        tt.execute(new TransactionCallbackWithoutResult() {

            @Override
            protected void doInTransactionWithoutResult(TransactionStatus status) throws RuntimeException {
                boolean condition1 = !status.isNewTransaction();
                assertThat(condition1).as("Is existing transaction").isTrue();
                assertThat(status.isRollbackOnly()).as("Is not rollback-only").isFalse();
                tt.execute(new TransactionCallbackWithoutResult() {

                    @Override
                    protected void doInTransactionWithoutResult(TransactionStatus status) throws RuntimeException {
                        assertThat(TransactionSynchronizationManager.hasResource(ds)).as("Has thread connection").isTrue();
                        assertThat(TransactionSynchronizationManager.isSynchronizationActive()).as("Synchronization active").isTrue();
                        boolean condition = !status.isNewTransaction();
                        assertThat(condition).as("Is existing transaction").isTrue();
                        status.setRollbackOnly();
                    }
                });
                boolean condition = !status.isNewTransaction();
                assertThat(condition).as("Is existing transaction").isTrue();
                assertThat(status.isRollbackOnly()).as("Is rollback-only").isTrue();
            }
        });
        outerTransactionBoundaryReached = true;
        tm.commit(ts);
        fail("Should have thrown UnexpectedRollbackException");
    } catch (UnexpectedRollbackException ex) {
        // expected
        if (!outerTransactionBoundaryReached) {
            tm.rollback(ts);
        }
        if (failEarly) {
            assertThat(outerTransactionBoundaryReached).isFalse();
        } else {
            assertThat(outerTransactionBoundaryReached).isTrue();
        }
    }
    boolean condition = !TransactionSynchronizationManager.hasResource(ds);
    assertThat(condition).as("Hasn't thread connection").isTrue();
    assertThat(synch.beforeCommitCalled).isFalse();
    assertThat(synch.beforeCompletionCalled).isTrue();
    assertThat(synch.afterCommitCalled).isFalse();
    assertThat(synch.afterCompletionCalled).isTrue();
    verify(con).rollback();
    verify(con).close();
}
Also used : DefaultTransactionDefinition(cn.taketoday.transaction.support.DefaultTransactionDefinition) TransactionTemplate(cn.taketoday.transaction.support.TransactionTemplate) TransactionStatus(cn.taketoday.transaction.TransactionStatus) UnexpectedRollbackException(cn.taketoday.transaction.UnexpectedRollbackException) TransactionCallbackWithoutResult(cn.taketoday.transaction.support.TransactionCallbackWithoutResult)

Example 5 with UnexpectedRollbackException

use of cn.taketoday.transaction.UnexpectedRollbackException in project today-framework by TAKETODAY.

the class AbstractReactiveTransactionAspectTests method cannotCommitTransaction.

/**
 * Simulate failure of the underlying transaction infrastructure to commit.
 * Check that the target method was invoked, but that the transaction
 * infrastructure exception was thrown to the client
 */
@Test
public void cannotCommitTransaction() throws Exception {
    TransactionAttribute txatt = new DefaultTransactionAttribute();
    Method m = setNameMethod;
    MapTransactionAttributeSource tas = new MapTransactionAttributeSource();
    tas.register(m, txatt);
    // Method m2 = getNameMethod;
    // No attributes for m2
    ReactiveTransactionManager rtm = mock(ReactiveTransactionManager.class);
    ReactiveTransaction status = mock(ReactiveTransaction.class);
    given(rtm.getReactiveTransaction(txatt)).willReturn(Mono.just(status));
    UnexpectedRollbackException ex = new UnexpectedRollbackException("foobar", null);
    given(rtm.commit(status)).willReturn(Mono.error(ex));
    given(rtm.rollback(status)).willReturn(Mono.empty());
    DefaultTestBean tb = new DefaultTestBean();
    TestBean itb = (TestBean) advised(tb, rtm, tas);
    String name = "new name";
    Mono.from(itb.setName(name)).as(StepVerifier::create).consumeErrorWith(throwable -> {
        assertThat(throwable.getClass()).isEqualTo(RuntimeException.class);
        assertThat(throwable.getCause()).isEqualTo(ex);
    }).verify();
    // Should have invoked target and changed name
    itb.getName().as(StepVerifier::create).expectNext(name).verifyComplete();
}
Also used : BeforeEach(org.junit.jupiter.api.BeforeEach) ReactiveTransaction(cn.taketoday.transaction.ReactiveTransaction) StepVerifier(reactor.test.StepVerifier) Publisher(org.reactivestreams.Publisher) Assertions.assertThat(org.assertj.core.api.Assertions.assertThat) ReactiveTransactionManager(cn.taketoday.transaction.ReactiveTransactionManager) Mono(reactor.core.publisher.Mono) Mockito.times(org.mockito.Mockito.times) TransactionContext(cn.taketoday.transaction.reactive.TransactionContext) Fail.fail(org.assertj.core.api.Fail.fail) Mockito.verify(org.mockito.Mockito.verify) Mockito.verifyNoInteractions(org.mockito.Mockito.verifyNoInteractions) Test(org.junit.jupiter.api.Test) CannotCreateTransactionException(cn.taketoday.transaction.CannotCreateTransactionException) BDDMockito.given(org.mockito.BDDMockito.given) TransactionSystemException(cn.taketoday.transaction.TransactionSystemException) UnexpectedRollbackException(cn.taketoday.transaction.UnexpectedRollbackException) Method(java.lang.reflect.Method) Mockito.mock(org.mockito.Mockito.mock) Method(java.lang.reflect.Method) ReactiveTransaction(cn.taketoday.transaction.ReactiveTransaction) ReactiveTransactionManager(cn.taketoday.transaction.ReactiveTransactionManager) UnexpectedRollbackException(cn.taketoday.transaction.UnexpectedRollbackException) StepVerifier(reactor.test.StepVerifier) Test(org.junit.jupiter.api.Test)

Aggregations

UnexpectedRollbackException (cn.taketoday.transaction.UnexpectedRollbackException)10 TransactionStatus (cn.taketoday.transaction.TransactionStatus)6 TransactionSystemException (cn.taketoday.transaction.TransactionSystemException)4 DefaultTransactionDefinition (cn.taketoday.transaction.support.DefaultTransactionDefinition)4 TransactionCallbackWithoutResult (cn.taketoday.transaction.support.TransactionCallbackWithoutResult)4 TransactionTemplate (cn.taketoday.transaction.support.TransactionTemplate)4 Method (java.lang.reflect.Method)4 Test (org.junit.jupiter.api.Test)4 ITestBean (cn.taketoday.beans.testfixture.beans.ITestBean)2 TestBean (cn.taketoday.beans.testfixture.beans.TestBean)2 CannotCreateTransactionException (cn.taketoday.transaction.CannotCreateTransactionException)2 HeuristicCompletionException (cn.taketoday.transaction.HeuristicCompletionException)2 PlatformTransactionManager (cn.taketoday.transaction.PlatformTransactionManager)2 ReactiveTransaction (cn.taketoday.transaction.ReactiveTransaction)2 ReactiveTransactionManager (cn.taketoday.transaction.ReactiveTransactionManager)2 TransactionContext (cn.taketoday.transaction.reactive.TransactionContext)2 HeuristicMixedException (jakarta.transaction.HeuristicMixedException)2 HeuristicRollbackException (jakarta.transaction.HeuristicRollbackException)2 RollbackException (jakarta.transaction.RollbackException)2 SystemException (jakarta.transaction.SystemException)2