Fix regressions in SimpleThreadScope and SimpleTransactionScope
PR gh-25038 introduced regressions in SimpleThreadScope and SimpleTransactionScope in Spring Framework 5.2.7. Specifically, if a thread-scoped or transaction-scoped bean has a dependency on another thread-scoped or transaction-scoped bean, respectively, a ConcurrentModificationException will be thrown on Java 11 or higher. The reason is that Java 11 introduced a check for concurrent modification in java.util.HashMap's computeIfAbsent() implementation, and such a modification can occur when a thread-scoped bean is being created in order to satisfy a dependency of another thread-scoped bean that is currently being created. This commit fixes these regressions by switching from HashMap to ConcurrentHashMap for the instance maps in SimpleThreadScope and SimpleTransactionScope. Closes gh-25618
This commit is contained in:
@@ -1,51 +1,21 @@
|
||||
<?xml version="1.0" encoding="UTF-8"?>
|
||||
<beans xmlns="http://www.springframework.org/schema/beans"
|
||||
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
|
||||
xsi:schemaLocation="http://www.springframework.org/schema/beans
|
||||
https://www.springframework.org/schema/beans/spring-beans-2.5.xsd">
|
||||
<beans xmlns="http://www.springframework.org/schema/beans" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
|
||||
xsi:schemaLocation="http://www.springframework.org/schema/beans https://www.springframework.org/schema/beans/spring-beans.xsd">
|
||||
|
||||
<bean class="org.springframework.beans.factory.config.CustomScopeConfigurer">
|
||||
<property name="scopes">
|
||||
<map>
|
||||
<entry key="thread">
|
||||
<bean class="org.springframework.context.support.SimpleThreadScope"/>
|
||||
<bean class="org.springframework.context.support.SimpleThreadScope" />
|
||||
</entry>
|
||||
</map>
|
||||
</property>
|
||||
</bean>
|
||||
|
||||
<bean id="threadScopedObject" class="org.springframework.beans.testfixture.beans.TestBean" scope="thread"/>
|
||||
|
||||
<!--
|
||||
<bean id="requestScopedDisposableObject" class="org.springframework.beans.testfixture.beans.DerivedTestBean" scope="request"/>
|
||||
|
||||
<bean id="requestScopedFactoryBean" class="org.springframework.beans.testfixture.beans.factory.DummyFactory" scope="request"/>
|
||||
|
||||
<bean id="requestScopedObjectCircle1" class="org.springframework.beans.testfixture.beans.TestBean" scope="request">
|
||||
<property name="spouse" ref="requestScopedObjectCircle2"/>
|
||||
<bean id="threadScopedObject" class="org.springframework.beans.testfixture.beans.TestBean" scope="thread">
|
||||
<property name="spouse" ref="threadScopedObject2" />
|
||||
</bean>
|
||||
|
||||
<bean id="requestScopedObjectCircle2" class="org.springframework.beans.testfixture.beans.TestBean" scope="request">
|
||||
<property name="spouse" ref="requestScopedObjectCircle1"/>
|
||||
</bean>
|
||||
<bean id="threadScopedObject2" class="org.springframework.beans.testfixture.beans.TestBean" scope="thread" />
|
||||
|
||||
<bean id="requestScopedOuterBean" class="org.springframework.beans.testfixture.beans.DerivedTestBean" scope="request">
|
||||
<property name="name" value="outer"/>
|
||||
<property name="spouse">
|
||||
<bean class="org.springframework.beans.testfixture.beans.DerivedTestBean">
|
||||
<property name="name" value="inner"/>
|
||||
</bean>
|
||||
</property>
|
||||
</bean>
|
||||
|
||||
<bean id="singletonOuterBean" class="org.springframework.beans.testfixture.beans.DerivedTestBean" lazy-init="true">
|
||||
<property name="name" value="outer"/>
|
||||
<property name="spouse">
|
||||
<bean class="org.springframework.beans.testfixture.beans.DerivedTestBean" scope="request">
|
||||
<property name="name" value="inner"/>
|
||||
</bean>
|
||||
</property>
|
||||
</bean>
|
||||
|
||||
-->
|
||||
</beans>
|
||||
|
||||
Reference in New Issue
Block a user