Skip to content
AITroveRead. Build. Understand.
Make this comfortable

Spring NESTED versus REQUIRES_NEW: savepoint or independent commit

Last updated: 30 Sept 20264 min read
tutorial
IntermediateBy AITrove Editorial

NESTED keeps one physical transaction with savepoints; REQUIRES_NEW starts an independent physical transaction that can commit while its caller later rolls back.

Download Spring source kit

The persistence outcomes differ

In the new savepoint fixture, the failed child insert disappears and the outer rows commit. The existing propagation fixture checks an independent inner commit surviving an outer rollback. That difference matters when writing audit rows, external work markers or compensating state. A surviving inner row may refer to business data that never committed.

NESTED depends on savepoint support in the actual transaction manager and database driver. REQUIRES_NEW typically needs another database connection while the outer one remains bound; a pool sized only for active outer calls can stall under nested use. Neither mode coordinates a broker. An outbox row should normally share the business transaction when atomicity is required.

Test a state table, not only annotations

Draw the expected rows after inner failure, outer failure and success. Then run those branches against the target database. Proxy self-invocation can bypass annotation-based propagation, so obtain the managed service and invoke across the proxy boundary when testing @Transactional methods.

Checked source

Java
nested.setPropagationBehavior(TransactionDefinition.PROPAGATION_NESTED);
outer.executeWithoutResult(status -> {
    jdbc.update("insert into receipt_step values (?)", "accept");
    try {
        nested.executeWithoutResult(child -> {
            jdbc.update("insert into receipt_step values (?)", "temporary-check");
            throw new IllegalStateException("reject nested step");
        });
    } catch (IllegalStateException rejected) {
        jdbc.update("insert into receipt_step values (?)", "record-rejection");
    }
});

Verification boundary

NestedSavepointContractTest.nestedFailureRollsBackToSavepointWhileOuterWorkCommits and FrameworkBoundaryTest.requiresNewAuditSurvivesOuterRollback runs in the downloadable Spring source kit. The excerpt omits imports and surrounding setup; the kit contains the complete tests.

Costs and limits

Two local H2 fixtures check one nested rollback and an independent propagation case. They do not establish pool capacity, target-database deadlock behavior or cross-service atomicity.

Common Mistakes

  • Do not expect a REQUIRES_NEW commit to roll back with its caller.
  • Do not use NESTED when the underlying manager cannot create savepoints.
  • Do not ignore the extra connection demand of independent inner transactions.

Read next

Spring nested transactions: roll back one step to a JDBC savepoint, Spring transaction propagation: joined rollback and independent commit, Spring transactional outbox: commit a receipt and event row together.

spring
spring-boot
nested-vs-requires-new
Storage details