一区二区三区在线-一区二区三区亚洲视频-一区二区三区亚洲-一区二区三区午夜-一区二区三区四区在线视频-一区二区三区四区在线免费观看

服務(wù)器之家:專注于服務(wù)器技術(shù)及軟件下載分享
分類導(dǎo)航

PHP教程|ASP.NET教程|Java教程|ASP教程|編程技術(shù)|正則表達(dá)式|C/C++|IOS|C#|Swift|Android|VB|R語言|JavaScript|易語言|vb.net|

服務(wù)器之家 - 編程語言 - Java教程 - spring @Transactional 無效的解決方案

spring @Transactional 無效的解決方案

2021-07-26 10:40dezun Java教程

這篇文章主要介紹了spring @Transactional 無效的解決方案,文中通過示例代碼介紹的非常詳細(xì),對(duì)大家的學(xué)習(xí)或者工作具有一定的參考學(xué)習(xí)價(jià)值,需要的朋友們下面隨著小編來一起學(xué)習(xí)學(xué)習(xí)吧

關(guān)于@transactional注解 一般都認(rèn)為要注意以下三點(diǎn)

1 .在需要事務(wù)管理的地方加@transactional 注解。@transactional 注解可以被應(yīng)用于接口定義和接口方法、類定義和類的 public 方法上 。

2 . @transactional 注解只能應(yīng)用到 public 可見度的方法上 。 如果你在 protected、private 或者 package-visible 的方法上使用 @transactional 注解,它也不會(huì)報(bào)錯(cuò), 但是這個(gè)被注解的方法將不會(huì)展示已配置的事務(wù)設(shè)置。

3 . 注意僅僅 @transactional 注解的出現(xiàn)不足于開啟事務(wù)行為,它僅僅 是一種元數(shù)據(jù)。必須在配置文件中使用配置元素,才真正開啟了事務(wù)行為。

最近在項(xiàng)目中發(fā)現(xiàn)注解無效,經(jīng)過跟蹤源代碼發(fā)現(xiàn)了問題,于是在網(wǎng)上找到相同出現(xiàn)此問題的人,以下為原文,講解的很詳細(xì):

只要避開spring目前的aop實(shí)現(xiàn)上的限制,要么都聲明要事務(wù),要么分開成兩個(gè)類,要么直接在方法里使用編程式事務(wù)

[問題]

spring的聲明式事務(wù),我想就不用多介紹了吧,一句話“自從用了spring aop啊,事務(wù)管理真輕松啊,真輕松;事務(wù)管理代碼沒有了,腦不酸了,手不痛了,一口氣全配上了事務(wù);輕量級(jí),測試起來也簡單,嘿!”。不管從哪個(gè)角度看,輕量級(jí)聲明式事務(wù)都是一件解放生產(chǎn)力的大好事。所以,我們“一直用它”。

不過,最近的一個(gè)項(xiàng)目里,卻碰到了一個(gè)事務(wù)管理上的問題:有一個(gè)服務(wù)類,其一個(gè)聲明了事務(wù)的方法,里面做了三次插入sql操作,但是在后面出錯(cuò)回滾時(shí),卻發(fā)現(xiàn)前面插入成功了,也是說,這個(gè)聲明了事務(wù)的方法,實(shí)際上并沒有真正啟動(dòng)事務(wù)!怎么回事呢?難道spring的聲明式事務(wù)失效了?

[探幽]

其實(shí)以前也會(huì)碰到有人說,spring的事務(wù)配置不起作用,但是根據(jù)第一反應(yīng)和以往經(jīng)驗(yàn),我總會(huì)告訴他,肯定是你的配置有問題啦;所以這一次,我想也不會(huì)例外,大概是把事務(wù)注解配在了接口上而不是實(shí)現(xiàn)方法上,或者,如果是用xml聲明方式的話,很可能是切入點(diǎn)的表達(dá)式?jīng)]有配對(duì)。

 不過,在檢查了他們的配置后,卻發(fā)現(xiàn)沒有配置問題,該起事務(wù)的實(shí)現(xiàn)方法上,用了@transactional事務(wù)注解聲明,xml里也配了注解驅(qū)動(dòng)<tx:annotation-driven .../>,配置很正確啊,怎么會(huì)不起作用?

我很納悶,于是往下問:

問1:其他方法有這種情況么?

答1:沒有。

問2:這個(gè)方法有什么特別的么(以下簡稱方法b)?

答2:就是調(diào)后臺(tái)插了三條記錄啊,沒啥特別的。

問3:這個(gè)方法是從web層直接調(diào)用的吧?

答3:不是,是這個(gè)service類(以下簡稱servicea)的另外一個(gè)方法調(diào)過來的(以下簡稱方法a)。

問4:哦,那個(gè)調(diào)用它的方法配了事務(wù)么(問題可能在這了)?

 答4:沒有。

問5:那web層的action(用的是struts2),調(diào)用的是沒有聲明事務(wù)的方法a,方法a再調(diào)用聲明了事務(wù)的方法b?

答5:對(duì)的。

問6:你直接在方法a上加上事務(wù)聲明看看

答6:好。。。

看來可能找到問題所在了,于是把@transactional也加在方法a上,啟動(dòng)項(xiàng)目測試,結(jié)果是:事務(wù)正常生效,方法a和方法b都在一個(gè)事務(wù)里了。

好了,現(xiàn)在總結(jié)一下現(xiàn)象:

1、servicea類為web層的action服務(wù)

2、action調(diào)用了servicea的方法a,而方法a沒有聲明事務(wù)(原因是方法a本身比較耗時(shí)而又不需要事務(wù))

3、servicea的方法a調(diào)用了自己所在class的方法b,而方法b聲明了事務(wù),但是方法b的事務(wù)聲明在這種情況失效了。

4、如果在方法a上也聲明事務(wù),則在action調(diào)用方法a時(shí),事務(wù)生效,而方法b則自動(dòng)參與了這個(gè)事務(wù)。

我讓他先把a(bǔ)也加上事務(wù)聲明,決定回來自己再測一下。

這個(gè)問題,表面上是事務(wù)聲明失效的問題,實(shí)質(zhì)上很可能是spring的aop機(jī)制實(shí)現(xiàn)角度的問題。

我想到很久以前研究spring的aop實(shí)現(xiàn)時(shí)發(fā)現(xiàn)的一個(gè)現(xiàn)象:對(duì)于以cglib方式增強(qiáng)的aop目標(biāo)類,會(huì)創(chuàng)建兩個(gè)對(duì)象,一個(gè)事bean實(shí)例本身,一個(gè)是cglib增強(qiáng)代理對(duì)象,而不僅僅是只有后者。我曾經(jīng)疑惑過這一點(diǎn),但當(dāng)時(shí)沒有再仔細(xì)探究下去。

 我們知道,spring的aop實(shí)現(xiàn)方式有兩種:1、java代理方式;2、cglib動(dòng)態(tài)增強(qiáng)方式,這兩種方式在spring中是可以無縫自由切換的。

java代理方式的優(yōu)點(diǎn)是不依賴第三方j(luò)ar包,缺點(diǎn)是不能代理類,只能代理接口。

spring通過aopproxy接口,抽象了這兩種實(shí)現(xiàn),實(shí)現(xiàn)了一致的aop方式:

spring @Transactional 無效的解決方案

現(xiàn)在看來,這種抽象同樣帶了一個(gè)缺陷,那就是抹殺了cglib能夠直接創(chuàng)建普通類的增強(qiáng)子類的能力,spring相當(dāng)于把cglib動(dòng)態(tài)生成的子類,當(dāng)普通的代理類了,這也是為什么會(huì)創(chuàng)建兩個(gè)對(duì)象的原因。下圖顯示了spring的aop代理類的實(shí)際調(diào)用過程:

spring @Transactional 無效的解決方案

因此,從上面的分析可以看出,methodb沒有被aopproxy通知到, 導(dǎo)致最終結(jié)果是:

被spring的aop增強(qiáng)的類,在同一個(gè)類的內(nèi)部方法調(diào)用時(shí),其被調(diào)用方法上的增強(qiáng)通知將不起作用。

而這種結(jié)果,會(huì)造成什么影響呢: 1:內(nèi)部調(diào)用時(shí),被調(diào)用方法的事務(wù)聲明將不起作用 2:換句話說,你在某個(gè)方法上聲明它需要事務(wù)的時(shí)候,如果這個(gè)類還有其他開發(fā)者,你將不能保證這個(gè)方法真的會(huì)在事務(wù)環(huán)境中 3:再換句話說,spring的事務(wù)傳播策略在內(nèi)部方法調(diào)用時(shí)將不起作用。

不管你希望某個(gè)方法需要單獨(dú)事務(wù),是requiresnew,還是要嵌套事務(wù),要nested,等等,統(tǒng)統(tǒng)不起作用。
4:不僅僅是事務(wù)通知,所有你自己利用spring實(shí)現(xiàn)的aop通知,都會(huì)受到同樣限制。。。。

[解難]

問題的原因已經(jīng)找到,其實(shí),我理想中的aop實(shí)現(xiàn),應(yīng)該是下面這樣:

spring @Transactional 無效的解決方案

只要一個(gè)cglib增強(qiáng)對(duì)象就好,對(duì)于java代理方式,我的選擇是毫不猶豫的拋棄。

至于前面的事務(wù)問題,只要避開spring目前的aop實(shí)現(xiàn)上的限制,要么都聲明要事務(wù),要么分開成兩個(gè)類,要么直接在方法里使用編程式事務(wù),那么一切ok。

以上就是本文的全部內(nèi)容,希望對(duì)大家的學(xué)習(xí)有所幫助,也希望大家多多支持服務(wù)器之家。

原文鏈接:https://blog.csdn.net/gudejundd/article/details/54380141

延伸 · 閱讀

精彩推薦
主站蜘蛛池模板: 精品欧美一区二区在线观看欧美熟 | 视频在线视频免费观看 | 欧美日韩国产另类一区二区三区 | 欧美成人精品福利在线视频 | 含羞草传媒每天免费一次破解 | 亚洲成人综合在线 | 草草在线视频 | 性xxxx欧美高清 | 亚洲丰满女人ass硕大 | 国产精品www视频免费看 | 国产精品久久久久久网站 | 亚洲香蕉伊在人在线观看9 亚洲系列国产系列 | 免费理伦片在线观看全网站 | 乌克兰粉嫩摘花第一次 | 精品亚洲欧美中文字幕在线看 | 国产三级精品久久三级国专区 | 无人区乱码1区2区3区网站 | 精品欧美一区二区三区四区 | 国产动作大片 | 免费欧美一级 | 午夜小视频网站 | 丝袜爆操 | 日韩去日本高清在线 | 超强台风免费观看完整版视频 | 97视频免费人人观看人人 | 精品国产免费观看一区高清 | 国产剧情一区二区三区 | 星空无限传媒xk8027穆娜 | 国产99在线观看 | tiny4k欧美极品在线 | 99欧美精品 | 欧美同性video | 乳色吐息讲的是什么 | 亚洲 欧美 在线观看 | 日韩精品视频免费 | 色综合色狠狠天天综合色hd | 欧美成人三级伦在线观看 | 图片专区小说专区卡通动漫 | 好奇害死猫在线观看 | 国产成人综合一区精品 | 欧美专区亚洲 |