前言
本文主要介紹下spring事務中的傳播行為。事務傳播行為是spring框架獨有的事務增強特性,他不屬于的事務實際提供方數據庫行為。這是spring為我們提供的強大的工具箱,使用事務傳播行可以為我們的開發工作提供許多便利。
下面話不多說了,來一起看看詳細的介紹吧
事務傳播行為介紹
spring中的7個事務傳播行為:
|事務行為|說明 |
|:--|:--|
|propagation_required | 支持當前事務,假設當前沒有事務。就新建一個事務 |
| propagation_supports |支持當前事務,假設當前沒有事務,就以非事務方式運行 |
| propagation_mandatory| 支持當前事務,假設當前沒有事務,就拋出異常|
| propagation_requires_new | 新建事務,假設當前存在事務。把當前事務掛起|
|propagation_not_supported | 以非事務方式運行操作。假設當前存在事務,就把當前事務掛起 |
| propagation_never | 以非事務方式運行,假設當前存在事務,則拋出異常 |
| propagation_nested |如果當前存在事務,則在嵌套事務內執行。如果當前沒有事務,則執行與propagation_required類似的操作。 |
舉例說明
案例代碼
servicea
1
2
3
4
5
|
servicea { void methoda() { serviceb.methodb(); } } |
serviceb
1
2
3
4
|
serviceb { void methodb() { } } |
1.propagation_required
假如當前正要運行的事務不在另外一個事務里,那么就起一個新的事務 比方說,serviceb.methodb的事務級別定義propagation_required, 那么因為執行servicea.methoda的時候,servicea.methoda已經起了事務。這時調用serviceb.methodb,serviceb.methodb看到自己已經執行在servicea.methoda的事務內部。就不再起新的事務。而假如servicea.methoda執行的時候發現自己沒有在事務中,他就會為自己分配一個事務。這樣,在servicea.methoda或者在serviceb.methodb內的不論什么地方出現異常。事務都會被回滾。即使serviceb.methodb的事務已經被提交,可是servicea.methoda在接下來fail要回滾,serviceb.methodb也要回滾
2.propagation_supports
假設當前在事務中。即以事務的形式執行。假設當前不在一個事務中,那么就以非事務的形式執行
3propagation_mandatory
必須在一個事務中執行。也就是說,他僅僅能被一個父事務調用。否則,他就要拋出異常
4.propagation_requires_new
這個就比較繞口了。 比方我們設計servicea.methoda的事務級別為propagation_required,serviceb.methodb的事務級別為propagation_requires_new。那么當運行到serviceb.methodb的時候,servicea.methoda所在的事務就會掛起。serviceb.methodb會起一個新的事務。等待serviceb.methodb的事務完畢以后,他才繼續運行。
他與propagation_required 的事務差別在于事務的回滾程度了。由于serviceb.methodb是新起一個事務,那么就是存在兩個不同的事務。假設serviceb.methodb已經提交,那么servicea.methoda失敗回滾。serviceb.methodb是不會回滾的。假設serviceb.methodb失敗回滾,假設他拋出的異常被servicea.methoda捕獲,servicea.methoda事務仍然可能提交。
5.propagation_not_supported
當前不支持事務。比方servicea.methoda的事務級別是propagation_required 。而serviceb.methodb的事務級別是propagation_not_supported ,那么當執行到serviceb.methodb時。servicea.methoda的事務掛起。而他以非事務的狀態執行完,再繼續servicea.methoda的事務。
6.propagation_never
不能在事務中執行。
如果servicea.methoda的事務級別是propagation_required。 而serviceb.methodb的事務級別是propagation_never ,那么serviceb.methodb就要拋出異常了。
7.propagation_nested
如果當前存在事務,則在嵌套事務內執行。如果當前沒有事務,則執行與propagation_required類似的操作。
spring中事務的配置
配置文件的方式
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
|
<tx:advice id= "txadvice" transaction-manager= "txmanager" > <tx:attributes> <!--設置所有匹配的方法,然后設置傳播級別和事務隔離--> <tx:method name= "save*" propagation= "required" /> <tx:method name= "add*" propagation= "required" /> <tx:method name= "create*" propagation= "required" /> <tx:method name= "insert*" propagation= "required" /> <tx:method name= "update*" propagation= "required" /> <tx:method name= "merge*" propagation= "required" /> <tx:method name= "del*" propagation= "required" /> <tx:method name= "remove*" propagation= "required" /> <tx:method name= "put*" propagation= "required" /> <tx:method name= "get*" propagation= "supports" read-only= "true" /> <tx:method name= "count*" propagation= "supports" read-only= "true" /> <tx:method name= "find*" propagation= "supports" read-only= "true" /> <tx:method name= "list*" propagation= "supports" read-only= "true" /> <tx:method name= "*" propagation= "supports" read-only= "true" /> </tx:attributes> </tx:advice> |
注解的方式
1
2
|
<!--開啟注解的方式--> <tx:annotation-driven transaction-manager= "transactiomanager" /> |
@transactional(propagation=propagation.required)
如果有事務, 那么加入事務, 沒有的話新建一個(默認情況下)
@transactional(propagation=propagation.not_supported)
容器不為這個方法開啟事務
@transactional(propagation=propagation.requires_new)
不管是否存在事務,都創建一個新的事務,原來的掛起,新的執行完畢,繼續執行老的事務
@transactional(propagation=propagation.mandatory)
必須在一個已有的事務中執行,否則拋出異常
@transactional(propagation=propagation.never)
必須在一個沒有的事務中執行,否則拋出異常(與propagation.mandatory相反)
@transactional(propagation=propagation.supports)
如果其他bean調用這個方法,在其他bean中聲明事務,那就用事務.如果其他bean沒有聲明事務,那就不用事務.
總結
以上就是這篇文章的全部內容了,希望本文的內容對大家的學習或者工作具有一定的參考學習價值,如果有疑問大家可以留言交流,謝謝大家對服務器之家的支持。
原文鏈接:https://www.cnblogs.com/dengpengbo/p/10425316.html