Skip to content

TransactionSynchronizationManager uses static ThreadLocals for synchronizations - bad design [SPR-11980] #16596

Closed
@spring-projects-issues

Description

@spring-projects-issues

Pavel Kostelnik opened SPR-11980 and commented

There is a design flaw in Transaction handling of spring-jdbc.
We have the following setup:

  1. scheduled java programs running in sandbox using spring-jdbc and transporting data
  2. the flow of the program is
    Spring core JMS pom.xml #1 wrapping utility thread do some utility logging and other logic
    Improve annotation processing thread-safety #2 call processing method of java program
    Fixes https://jira.springsource.org/browse/SPR-7721 #3 this method uses spring-jdbc with transactions (we need to control them directly from code using DataSourceTransactionManager).
    SPR-7752 - EntityManager proxy now exposes provider specific interface. #4 The transactionManager instance is bound to datasource to a different DS
    SPR-7679 - Qualified TransactionManager now also found if declared in parent context #5 process data
    quick changelog typo fix #6 return to original utilityThread.

Now if transactions were enabled in phase #3, #4, #5 then they still remain active even when using JDBC template with a COMPLETELY different datasource.

It is a really bad design to have static ThreadLoacal variable hold synchronizations... (see below code from TransactionSynchronizationManager):
private static final ThreadLocal<Set<TransactionSynchronization>> synchronizations =
new NamedThreadLocal<Set<TransactionSynchronization>>("Transaction synchronizations");

What is even weirder is that when creating a transaction manager you create it like this:
transactionManager = new DataSourceTransactionManager();
transactionManager.setDataSource(myInProcessDS);

Now any reasonable person would assume that this binds that manager only to that one DS. But since the variable is static and threadLocal it affects the whole thread.

This is very silly and I suggest that Transaction manager keeps the variable bound to DataSource + Thread and not to Thread only. Plus I am not sure if it really has to remain static.


Affects: 3.1.1

1 votes, 4 watchers

Metadata

Metadata

Assignees

No one assigned

    Labels

    in: dataIssues in data modules (jdbc, orm, oxm, tx)status: bulk-closedAn outdated, unresolved issue that's closed in bulk as part of a cleaning process

    Type

    No type

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions