React 前端导航

单测报错:Transaction synchronization is not active解决办法

场景

有时候我们需要在事务提交后处理一个Task,这个Task又要依赖事务提交的结果,这时候会使用到TransactionSynchronizationManager。

这里我是简单封装了一个工具类:

import java.util.concurrent.ExecutorService;
import java.util.concurrent.Executors;

import org.springframework.transaction.support.TransactionSynchronizationAdapter;
import org.springframework.transaction.support.TransactionSynchronizationManager;

/****

  • 事物后置处理

*/
public class TransactionSyncManagerUtil {

<span data-slate-leaf="true"><span class="token keyword" data-slate-string="true">private</span></span> <span data-slate-leaf="true"><span class="token keyword" data-slate-string="true">static</span></span> <span data-slate-leaf="true"><span class="token class-name" data-slate-string="true">ExecutorService</span></span><span data-slate-leaf="true"><span data-slate-string="true"> executorService </span></span><span data-slate-leaf="true"><span class="token operator" data-slate-string="true">=</span></span> <span data-slate-leaf="true"><span class="token class-name" data-slate-string="true">Executors</span></span><span data-slate-leaf="true"><span class="token punctuation" data-slate-string="true">.</span></span><span data-slate-leaf="true"><span class="token function" data-slate-string="true">newFixedThreadPool</span></span><span data-slate-leaf="true"><span class="token punctuation" data-slate-string="true">(</span></span><span data-slate-leaf="true"><span class="token number" data-slate-string="true">20</span></span><span data-slate-leaf="true"><span class="token punctuation" data-slate-string="true">)</span></span><span data-slate-leaf="true"><span class="token punctuation" data-slate-string="true">;</span></span>

<span data-slate-leaf="true"><span class="token keyword" data-slate-string="true">public</span></span> <span data-slate-leaf="true"><span class="token keyword" data-slate-string="true">static</span></span> <span data-slate-leaf="true"><span class="token keyword" data-slate-string="true">void</span></span> <span data-slate-leaf="true"><span class="token function" data-slate-string="true">registerSynchronization</span></span><span data-slate-leaf="true"><span class="token punctuation" data-slate-string="true">(</span></span><span data-slate-leaf="true"><span class="token keyword" data-slate-string="true">final</span></span> <span data-slate-leaf="true"><span class="token class-name" data-slate-string="true">Runnable</span></span><span data-slate-leaf="true"><span data-slate-string="true"> task</span></span><span data-slate-leaf="true"><span class="token punctuation" data-slate-string="true">)</span></span> <span data-slate-leaf="true"><span class="token punctuation" data-slate-string="true">{</span></span>

    <span data-slate-leaf="true"><span class="token class-name" data-slate-string="true">TransactionSynchronizationManager</span></span><span data-slate-leaf="true"><span class="token punctuation" data-slate-string="true">.</span></span><span data-slate-leaf="true"><span class="token function" data-slate-string="true">registerSynchronization</span></span><span data-slate-leaf="true"><span class="token punctuation" data-slate-string="true">(</span></span><span data-slate-leaf="true"><span class="token keyword" data-slate-string="true">new</span></span> <span data-slate-leaf="true"><span class="token class-name" data-slate-string="true">TransactionSynchronizationAdapter</span></span><span data-slate-leaf="true"><span class="token punctuation" data-slate-string="true">(</span></span><span data-slate-leaf="true"><span class="token punctuation" data-slate-string="true">)</span></span> <span data-slate-leaf="true"><span class="token punctuation" data-slate-string="true">{</span></span>
        <span data-slate-leaf="true"><span data-slate-string="true">@Override</span></span>
        <span data-slate-leaf="true"><span class="token keyword" data-slate-string="true">public</span></span> <span data-slate-leaf="true"><span class="token keyword" data-slate-string="true">void</span></span> <span data-slate-leaf="true"><span class="token function" data-slate-string="true">afterCommit</span></span><span data-slate-leaf="true"><span class="token punctuation" data-slate-string="true">(</span></span><span data-slate-leaf="true"><span class="token punctuation" data-slate-string="true">)</span></span> <span data-slate-leaf="true"><span class="token punctuation" data-slate-string="true">{</span></span><span data-slate-leaf="true"><span data-slate-string="true">
            executorService</span></span><span data-slate-leaf="true"><span class="token punctuation" data-slate-string="true">.</span></span><span data-slate-leaf="true"><span class="token function" data-slate-string="true">execute</span></span><span data-slate-leaf="true"><span class="token punctuation" data-slate-string="true">(</span></span><span data-slate-leaf="true"><span data-slate-string="true">task</span></span><span data-slate-leaf="true"><span class="token punctuation" data-slate-string="true">)</span></span><span data-slate-leaf="true"><span class="token punctuation" data-slate-string="true">;</span></span>
        <span data-slate-leaf="true"><span class="token punctuation" data-slate-string="true">}</span></span>
    <span data-slate-leaf="true"><span class="token punctuation" data-slate-string="true">}</span></span><span data-slate-leaf="true"><span class="token punctuation" data-slate-string="true">)</span></span><span data-slate-leaf="true"><span class="token punctuation" data-slate-string="true">;</span></span>
<span data-slate-leaf="true"><span class="token punctuation" data-slate-string="true">}</span></span>

}

具体使用示例如下:

@Transactional
public void fun() {
    // 数据库的一系列操作
    // ...
    // 事务提交后任务
    TransactionSyncManagerUtil.registerSynchronization(new Runnable() {
                    @Override
                    public void run() {
                        // 后置处理
                    }
      });
}

问题

然后在对方法编写单测的时候遇到报错如下:

java.lang.IllegalStateException: Transaction synchronization is not active

解决方案

import java.lang.reflect.Field;
import java.lang.reflect.Modifier;
import java.util.ArrayList;
import java.util.HashSet;
import java.util.List;
import java.util.Set;

import org.junit.Before;
import org.junit.Test;
import org.mockito.InjectMocks;
import org.mockito.Mock;
import org.mockito.Mockito;
import org.mockito.MockitoAnnotations;
import org.springframework.core.NamedThreadLocal;
import org.springframework.transaction.support.TransactionSynchronization;
import org.springframework.transaction.support.TransactionSynchronizationManager;

public class XXXServiceTest {

<span data-slate-leaf="true"><span class="token operator" data-slate-string="true">@InjectMocks</span></span>
<span data-slate-leaf="true"><span class="token keyword" data-slate-string="true">private</span></span> <span data-slate-leaf="true"><span class="token class-name" data-slate-string="true">XXXService</span></span><span data-slate-leaf="true"><span class="token class-name" data-slate-string="true"> xxxService</span></span><span data-slate-leaf="true"><span class="token punctuation" data-slate-string="true">;</span></span>

<span data-slate-leaf="true"><span class="token string" data-slate-string="true">@Mock</span></span>
<span data-slate-leaf="true"><span class="token keyword" data-slate-string="true">private</span></span> <span data-slate-leaf="true"><span class="token class-name" data-slate-string="true">TransactionSynchronization</span></span><span data-slate-leaf="true"><span class="token keyword" data-slate-string="true"> transactionSynchronization</span></span><span data-slate-leaf="true"><span class="token punctuation" data-slate-string="true">;</span></span>

<span data-slate-leaf="true"><span class="token keyword" data-slate-string="true">private</span></span> <span data-slate-leaf="true"><span class="token class-name" data-slate-string="true">Set</span></span><span data-slate-leaf="true"><span class="token punctuation" data-slate-string="true">&lt;TransactionSynchronization&gt;</span></span><span data-slate-leaf="true"><span class="token punctuation" data-slate-string="true"> synchronizationSet </span></span><span data-slate-leaf="true"><span class="token operator" data-slate-string="true">=</span></span> <span data-slate-leaf="true"><span class="token keyword" data-slate-string="true">new</span></span> <span data-slate-leaf="true"><span class="token class-name" data-slate-string="true">HashSet</span></span><span data-slate-leaf="true"><span class="token punctuation" data-slate-string="true">&lt;&gt;</span></span><span data-slate-leaf="true"><span class="token punctuation" data-slate-string="true">(</span></span><span data-slate-leaf="true"><span class="token punctuation" data-slate-string="true">)</span></span><span data-slate-leaf="true"><span class="token punctuation" data-slate-string="true">;</span></span>

<span data-slate-leaf="true"><span class="token keyword" data-slate-string="true">private</span></span> <span data-slate-leaf="true"><span class="token class-name" data-slate-string="true">ThreadLocal</span></span><span data-slate-leaf="true"><span class="token punctuation" data-slate-string="true">&lt;Set&lt;TransactionSynchronization&gt;&gt;</span></span><span data-slate-leaf="true"><span class="token keyword" data-slate-string="true"> synchronizations
        </span></span><span data-slate-leaf="true"><span class="token operator" data-slate-string="true">=</span></span> <span data-slate-leaf="true"><span class="token keyword" data-slate-string="true">new</span></span> <span data-slate-leaf="true"><span class="token class-name" data-slate-string="true">NamedThreadLocal</span></span><span data-slate-leaf="true"><span class="token punctuation" data-slate-string="true">&lt;&gt;</span></span><span data-slate-leaf="true"><span class="token punctuation" data-slate-string="true">(</span></span><span data-slate-leaf="true"><span class="token string" data-slate-string="true">"Transaction synchronizations"</span></span><span data-slate-leaf="true"><span class="token punctuation" data-slate-string="true">)</span></span><span data-slate-leaf="true"><span class="token punctuation" data-slate-string="true">;</span></span>
        

@Before
public void setup() throws Exception {
MockitoAnnotations.initMocks(this);

    <span data-slate-leaf="true"><span class="token keyword" data-slate-string="true">this</span></span><span data-slate-leaf="true"><span class="token punctuation" data-slate-string="true">.</span></span><span data-slate-leaf="true"><span class="token keyword" data-slate-string="true">synchronizationSet</span></span><span data-slate-leaf="true"><span class="token punctuation" data-slate-string="true">.</span></span><span data-slate-leaf="true"><span class="token function" data-slate-string="true">add</span></span><span data-slate-leaf="true"><span class="token punctuation" data-slate-string="true">(</span></span><span data-slate-leaf="true"><span class="token function" data-slate-string="true">transactionSynchronization</span></span><span data-slate-leaf="true"><span class="token punctuation" data-slate-string="true">)</span></span><span data-slate-leaf="true"><span class="token punctuation" data-slate-string="true">;</span></span>
    <span data-slate-leaf="true"><span class="token keyword" data-slate-string="true">this</span></span><span data-slate-leaf="true"><span class="token punctuation" data-slate-string="true">.</span></span><span data-slate-leaf="true"><span class="token class-name" data-slate-string="true">synchronizations</span></span><span data-slate-leaf="true"><span class="token punctuation" data-slate-string="true">.</span></span><span data-slate-leaf="true"><span class="token function" data-slate-string="true">set</span></span><span data-slate-leaf="true"><span class="token punctuation" data-slate-string="true">(</span></span><span data-slate-leaf="true"><span class="token keyword" data-slate-string="true">synchronizationSet</span></span><span data-slate-leaf="true"><span class="token punctuation" data-slate-string="true">)</span></span><span data-slate-leaf="true"><span class="token punctuation" data-slate-string="true">;</span></span>
    <span data-slate-leaf="true"><span class="token function" data-slate-string="true">setFinalStatic</span></span><span data-slate-leaf="true"><span class="token punctuation" data-slate-string="true">(</span></span><span data-slate-leaf="true"><span class="token class-name" data-slate-string="true">TransactionSynchronizationManager</span></span><span data-slate-leaf="true"><span class="token punctuation" data-slate-string="true">.</span></span><span data-slate-leaf="true"><span class="token keyword" data-slate-string="true">class</span></span><span data-slate-leaf="true"><span class="token punctuation" data-slate-string="true">.</span></span><span data-slate-leaf="true"><span class="token function" data-slate-string="true">getDeclaredField</span></span><span data-slate-leaf="true"><span class="token punctuation" data-slate-string="true">(</span></span><span data-slate-leaf="true"><span class="token string" data-slate-string="true">"synchronizations"</span></span><span data-slate-leaf="true"><span class="token punctuation" data-slate-string="true">)</span></span><span data-slate-leaf="true"><span class="token punctuation" data-slate-string="true">,</span></span><span data-slate-leaf="true"><span class="token operator" data-slate-string="true"> synchronizations</span></span><span data-slate-leaf="true"><span class="token punctuation" data-slate-string="true">)</span></span><span data-slate-leaf="true"><span class="token punctuation" data-slate-string="true">;</span></span>
<span data-slate-leaf="true"><span class="token punctuation" data-slate-string="true">}</span></span>

<span data-slate-leaf="true"><span class="token keyword" data-slate-string="true">static</span></span> <span data-slate-leaf="true"><span class="token keyword" data-slate-string="true">void</span></span> <span data-slate-leaf="true"><span class="token function" data-slate-string="true">setFinalStatic</span></span><span data-slate-leaf="true"><span class="token punctuation" data-slate-string="true">(</span></span><span data-slate-leaf="true"><span class="token class-name" data-slate-string="true">Field</span></span><span data-slate-leaf="true"><span class="token function" data-slate-string="true"> field</span></span><span data-slate-leaf="true"><span class="token punctuation" data-slate-string="true">,</span></span> <span data-slate-leaf="true"><span class="token class-name" data-slate-string="true">Object</span></span><span data-slate-leaf="true"><span class="token punctuation" data-slate-string="true"> newValue</span></span><span data-slate-leaf="true"><span class="token punctuation" data-slate-string="true">)</span></span> <span data-slate-leaf="true"><span class="token keyword" data-slate-string="true">throws</span></span> <span data-slate-leaf="true"><span class="token class-name" data-slate-string="true">Exception</span></span> <span data-slate-leaf="true"><span class="token punctuation" data-slate-string="true">{</span></span><span data-slate-leaf="true"><span class="token punctuation" data-slate-string="true">
    field</span></span><span data-slate-leaf="true"><span class="token punctuation" data-slate-string="true">.</span></span><span data-slate-leaf="true"><span class="token function" data-slate-string="true">setAccessible</span></span><span data-slate-leaf="true"><span class="token punctuation" data-slate-string="true">(</span></span><span data-slate-leaf="true"><span class="token boolean" data-slate-string="true">true</span></span><span data-slate-leaf="true"><span class="token punctuation" data-slate-string="true">)</span></span><span data-slate-leaf="true"><span class="token punctuation" data-slate-string="true">;</span></span>
    <span data-slate-leaf="true"><span class="token class-name" data-slate-string="true">Field</span></span><span data-slate-leaf="true"><span class="token punctuation" data-slate-string="true"> modifiersField </span></span><span data-slate-leaf="true"><span class="token operator" data-slate-string="true">=</span></span> <span data-slate-leaf="true"><span class="token class-name" data-slate-string="true">Field</span></span><span data-slate-leaf="true"><span class="token punctuation" data-slate-string="true">.</span></span><span data-slate-leaf="true"><span class="token keyword" data-slate-string="true">class</span></span><span data-slate-leaf="true"><span class="token punctuation" data-slate-string="true">.</span></span><span data-slate-leaf="true"><span class="token function" data-slate-string="true">getDeclaredField</span></span><span data-slate-leaf="true"><span class="token punctuation" data-slate-string="true">(</span></span><span data-slate-leaf="true"><span class="token string" data-slate-string="true">"modifiers"</span></span><span data-slate-leaf="true"><span class="token punctuation" data-slate-string="true">)</span></span><span data-slate-leaf="true"><span class="token punctuation" data-slate-string="true">;</span></span><span data-slate-leaf="true"><span class="token punctuation" data-slate-string="true">
    modifiersField</span></span><span data-slate-leaf="true"><span class="token punctuation" data-slate-string="true">.</span></span><span data-slate-leaf="true"><span class="token function" data-slate-string="true">setAccessible</span></span><span data-slate-leaf="true"><span class="token punctuation" data-slate-string="true">(</span></span><span data-slate-leaf="true"><span class="token boolean" data-slate-string="true">true</span></span><span data-slate-leaf="true"><span class="token punctuation" data-slate-string="true">)</span></span><span data-slate-leaf="true"><span class="token punctuation" data-slate-string="true">;</span></span><span data-slate-leaf="true"><span class="token keyword" data-slate-string="true">
    modifiersField</span></span><span data-slate-leaf="true"><span class="token punctuation" data-slate-string="true">.</span></span><span data-slate-leaf="true"><span class="token function" data-slate-string="true">setInt</span></span><span data-slate-leaf="true"><span class="token punctuation" data-slate-string="true">(</span></span><span data-slate-leaf="true"><span class="token punctuation" data-slate-string="true">field</span></span><span data-slate-leaf="true"><span class="token punctuation" data-slate-string="true">,</span></span><span data-slate-leaf="true"><span class="token punctuation" data-slate-string="true"> field</span></span><span data-slate-leaf="true"><span class="token punctuation" data-slate-string="true">.</span></span><span data-slate-leaf="true"><span class="token function" data-slate-string="true">getModifiers</span></span><span data-slate-leaf="true"><span class="token punctuation" data-slate-string="true">(</span></span><span data-slate-leaf="true"><span class="token punctuation" data-slate-string="true">)</span></span> <span data-slate-leaf="true"><span class="token operator" data-slate-string="true">&amp;</span></span> <span data-slate-leaf="true"><span class="token operator" data-slate-string="true">~</span></span><span data-slate-leaf="true"><span class="token class-name" data-slate-string="true">Modifier</span></span><span data-slate-leaf="true"><span class="token punctuation" data-slate-string="true">.</span></span><span data-slate-leaf="true"><span data-slate-string="true">FINAL</span></span><span data-slate-leaf="true"><span class="token punctuation" data-slate-string="true">)</span></span><span data-slate-leaf="true"><span class="token punctuation" data-slate-string="true">;</span></span><span data-slate-leaf="true"><span data-slate-string="true">
    field</span></span><span data-slate-leaf="true"><span class="token punctuation" data-slate-string="true">.</span></span><span data-slate-leaf="true"><span class="token function" data-slate-string="true">set</span></span><span data-slate-leaf="true"><span class="token punctuation" data-slate-string="true">(</span></span><span data-slate-leaf="true"><span class="token keyword" data-slate-string="true">null</span></span><span data-slate-leaf="true"><span class="token punctuation" data-slate-string="true">,</span></span><span data-slate-leaf="true"><span data-slate-string="true"> newValue</span></span><span data-slate-leaf="true"><span class="token punctuation" data-slate-string="true">)</span></span><span data-slate-leaf="true"><span class="token punctuation" data-slate-string="true">;</span></span>
<span data-slate-leaf="true"><span class="token punctuation" data-slate-string="true">}</span></span>

<span data-slate-leaf="true"><span data-slate-string="true">@Test</span></span>
<span data-slate-leaf="true"><span class="token keyword" data-slate-string="true">public</span></span> <span data-slate-leaf="true"><span class="token keyword" data-slate-string="true">void</span></span> <span data-slate-leaf="true"><span class="token function" data-slate-string="true">testFun</span></span><span data-slate-leaf="true"><span class="token punctuation" data-slate-string="true">(</span></span><span data-slate-leaf="true"><span class="token punctuation" data-slate-string="true">)</span></span> <span data-slate-leaf="true"><span class="token punctuation" data-slate-string="true">{</span></span>
    <span data-slate-leaf="true"><span class="token comment" data-slate-string="true">// 单元测试编写</span></span>
<span data-slate-leaf="true"><span class="token punctuation" data-slate-string="true">}</span></span>

}

声明:本网站发布的内容(图片、视频和文字)以原创、转载和分享网络内容为主,如果涉及侵权请尽快告知,我们将会在第一时间删除。文章观点不代表本网站立场,如需处理请联系客服。邮箱:farmerlzj@163.com。 本站原创内容未经允许不得转载,或转载时需注明出处: 内容转载自: React前端网:https://qianduan.shop/blogs/detail/170

#java#单测

相关推荐

彻底下线fastjson的依赖,Jackson替换FastJson注意事项

近几年fastjson爆出的漏洞非常多,因此可能你所在的公司会要求使用jackson替代fastjson。本文主要就作者自己最近完成fastjson替换记录的一个比较分享。

sms-aggregation 聚合短信发送工具

SMS Aggregation 是一款聚合短信发送工具,统一了各个厂商的发送功能和发送方法,省去学习不同短信厂商的差异化的时间,极简单的使用,可以让你在三分钟内完成短信发送功能的编写,并且额外添加了许多常用的工具和方法,让简单的事情回归简单的本质。