今天在码代码时,发现一个错误,有时正常有时不正常,完全没有一个程序该有的节操。在一翻调教下正常了。现留下解决方法备用。
以下原理纯属个人臆测,完全没有依据,误导完全不负责任~ 另请明白的大神评论里解释,脆谢~
目标描述:
我需要一次并行运行多个线程,使用CyclicBarrier 线程阻塞,等待全部执行完毕。每一个执行的线程调用外部接口并收到接口响应,且都有单独的日志信息的DB插入。日志信息记录接口执行前时间和外部接口返回结果时间。
原代码逻辑:
CyclicBarrier 实现跳过,在每一个线程中,我先插入DB一条日志,通过mybatis 插入返回日志对象。然后调用接口,接口返回后去DB 修改此日志对象,添加结果与结果返回时间。
错误现象:
一般第一次运行时,可以同时运行多线程并返回正常结果,但再点就有时候只调用了一次接口,有的时候一次外部接口调用都没有。点多少次都一样,时好使时不好使。
臆测原因:
mybatis 的插入返回是基于java 反射机制。几乎同时运行的线程程序是一样的,对于相同对象名造成反射瞎掉。还有一个可能的因素就是DB运行的影响,但我觉得不应该。再次声明:原理纯属个人臆测,完全没有依据,误导完全不负责任~
解决:
1 去掉mybatis 表映射文件 表名.xml 中 插入的 插入返回。
<insert id="insert" parameterType="com.xxx.xxx.pojo.xxx" keyProperty="xxId" useGeneratedKeys="true">
...
...
...
</insert>
对 ,说 白了 就是 删除 keyProperty="xxId" useGeneratedKeys="true"
2 线程开始后先弄个日志对象记录下执行时间,但并不插入DB。
3 调用接口后在日志对象里记录下返回时间,插入DB
总结:其实就一句话,不要觉得mybatis操作DB方便就随便用,能少连接DB就少连接!