国产片侵犯亲女视频播放_亚洲精品二区_在线免费国产视频_欧美精品一区二区三区在线_少妇久久久_在线观看av不卡

服務器之家:專注于服務器技術及軟件下載分享
分類導航

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

服務器之家 - 編程語言 - Java教程 - Spring中的事務操作、注解及XML配置詳解

Spring中的事務操作、注解及XML配置詳解

2021-06-26 12:03余同學的開發之路 Java教程

這篇文章主要給大家介紹了關于Spring中事務操作、注解及XML配置的相關資料,文中通過示例代碼介紹的非常詳細,對大家的學習或者工作具有一定的參考學習價值,需要的朋友們下面隨著小編來一起學習學習吧

事務

事務全稱叫數據庫事務,是數據庫并發控制時的基本單位,它是一個操作集合,這些操作要么不執行,要么都執行,不可分割。例如我們的轉賬這個業務,就需要進行數據庫事務的處理。

轉賬中至少會涉及到兩條 sql 語句:

?
1
2
update acoount set balance = balance - money where id = 'a';
update acoount set balance = balance + money where id = 'b'

上面這兩條 sql 就可以要看成是一個事務,必須都執行,或都不執行。如何保證呢,一般這樣表示:

?
1
2
3
4
5
6
7
8
9
10
11
12
# 開啟事務
begin transaction
 
 
update account set balance = balance - money where id = 'a';
update account set balance = balance + money where id = 'b'
# 提交事務
commit transaction
 
exception
 # 回滾事務
 rollback transaction

事務的特性(筆試的時候會有)

atomic(原子性):事務中包含的操作被看做一個邏輯單元,這個邏輯單元中的操作要么全部成功,要么全部失敗。

 

consistency(一致性):只有合法的數據可以被寫入數據庫,否則事務應該將其回滾到最初狀態。在轉賬的時候不會出現一當少錢了,另一方沒有增加的情況。

isolation(隔離性):事務允許多個用戶對同一個數據進行并發訪問,而不破壞數據的正確性和完整性。同時,并行事務的修改必須與其他并行事務的修改相互獨立。

durability(持久性):事務完成之后,它對于系統的影響是永久的,該修改即使出現系統故障也將一直保留,真實的修改了數據庫。

以上 4 個屬性常被簡稱為 acid(酸的)。

事務并發的問題

臟讀:事務二讀取到事務一中已經更新但是還沒有提交的數據,這就是臟讀。

不可重復讀:一個事務兩次讀取同一個行數據結果不同,因為有其它的事務對數據進行了更新。此時的數據即為不可重復讀數據。

幻讀:同一事務執行兩次查詢,結果不一致,因為中間有其它的事務對數據進行更改。

如何解決這些問題呢?數據庫系統為事務設置了 4 種不同的隔離級別。

事務隔離級別

讀未提交(read uncommitted):最低級別,可能會導入臟讀。

讀已提交(read committed):可以避免臟讀,只能查詢到已經提交的數據。且具有良好的性能,但是不能避免不可重復讀和幻讀。

可重復讀(repeatable):解決了不可重復讀,可能會出現幻讀。

串行化(serializable):通過加鎖,使同一時間只能執行一個事務,不出現上述問題,但是可能會導致大量的超時現象和鎖競爭。

另外,mysql 中默認的隔離級別是可重復讀。oracle 中默認的事務隔離級別是讀已提交。

說完事務,想想我們曾經為了處理事務而寫過的那些代碼。最后在說說 spring 中是如何處理的,學完 spring 再也不用擔心事務操作了。

在 jdbc 時代我們需要這樣手動的處理事務。

?
1
2
3
4
5
6
7
8
// 獲取連接 conn
conn.setautocommit(false); 設置提交方式為手工提交
// 業務代碼
// 減錢
// 加錢
conn.commit(); 提交事務
// 出現異常
conn.rollback(); 回滾事務

我們說處理事務那是處理數據庫事務,所以肯定要先有數據庫連接才能說事務的事,而在 java 中我們連接數據庫無非就是 jdbc,或是對 jdbc 進一步的封裝,比方說 hibernate ,mybatis 或是 dbutils 這些框架,所以萬變不離其宗,就是這么回事,就是看誰封裝的好罷了。你們有興趣可以看看它們都是如何封裝的。

spring 中的如何管理事務呢

首先,我們知道 spring 是一個容器,不同的框架在處理事務時用到的對象不同,原生的 jdbc 使用 connection ,而 mybatis 中使用 sqlsession 對象。而 spring 為了整合這些不同的框架,定義了一個 platformtransactionmanager 接口來統一標準,對不同的框架又有不同的實現類。

在 spring 中根據 dao 層技術的不同來選擇不同的事務處理的對象,是 jdbc 時使用 datasourcetransactionmanager,是 hibernate 時使用 hibernatetransitionmanager 對象,核心對象就是 transitionmanager。

在 spring 中管理事務會涉及到這幾個屬性,事務隔離級別、是否只讀、事務的傳播行為,說到事務的傳播行為,指的就是不同的業務方法之間相互調用時,應該如何管理事務。spring 中一共定義了 7 種傳播行為,無腦記住使用 required ,表示支持當前事務,若是不存在事務,就創建一個。例如在 a 調用 b 的時候,會首先使用 a 的事務,若 a 沒有事務,則新創建一個,不管 b 有沒有事務。

下面就是要實際操作一下,需要有具體的業務邏輯,還是那個轉賬的例子。來看看如何使用 spring 來管理事務,有兩種常見的管理方式,我們一種一種的說。

使用 xml 配置

1 首先是導包,spring 涉及的包是真的多,我有一個省事的方法,可能用到的 jar 包一下子導入。

2 導入新的約束文件,不然在 xml 無法使用 tx 標簽。

3 準備目標對象和通知并配置。

目標對象 accountserviceimpl

?
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
public class accountserviceimpl implements accountservice {
 
 private accountdao ad;
 
 @transactional(isolation=isolation.repeatable_read,propagation = propagation.required,readonly=false)
 @override
 public void transfer(integer from, integer to, double money) {
 
 ad.decreasemoney(from, money);
 
 //int i = 1/0;
 
 ad.increasemoney(to, money);
 }
 
 public void setad(accountdao ad) {
 this.ad = ad;
 }
}

在 aop 中通知即為增強的代碼,而在處理事務時,要增強的代碼無非就是開啟事務,提交事務和回滾事務,所以 spring 已經為我們封裝好了處理事務的通知,我們只需要配置一下即可。

?
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
<!-- 導入 properties 配置文件 -->
<context:property-placeholder location="classpath:db.properties"/>
<!-- 配置連接數據庫的核心處理對象-->
<bean name="transactionmanager" class = "org.springframework.jdbc.datasource.datasourcetransactionmanager">
 <property name="datasource" ref= "datasource"></property>
</bean>
<!-- 配置通知-->
<tx:advice id="txadvise" transaction-manager="transactionmanager">
 <tx:attributes>
 <tx:method name="transfer" isolation="default" propagation="required" read-only="false"/>
 </tx:attributes>
</tx:advice>
<!-- 配置 aop ,以達成自動處理事務的要求-->
<aop:config>
 <aop:pointcut expression="execution(* yu.transation.*serviceimpl.*(..))" id="txpointcut"/>
 
 <aop:advisor advice-ref="txadvise" pointcut-ref="txpointcut"/>
</aop:config>
 
 
<bean name="datasource" class="com.mchange.v2.c3p0.combopooleddatasource" >
 <property name="jdbcurl" value="${jdbc.jdbcurl}" ></property>
 <property name="driverclass" value="${jdbc.driverclass}" ></property>
 <property name="user" value="${jdbc.user}" ></property>
 <property name="password" value="${jdbc.password}" ></property>
</bean>
<!-- 配置 dao 層對象-->
<bean name="ad" class="yu.transation.accountdaoimpl">
 <property name="datasource" ref = "datasource"></property>
</bean>
<!-- 配置 service 層對象-->
<bean name = "accountservice" class = "yu.transation.accountserviceimpl">
 <property name="ad" ref = "ad"></property>
</bean>

上面的配置文件中,在配置通知時,我們具體到不同的方法會有不同的配置,在項目應用時,會使用通配符來進行配置。下面介紹一下使用注解來處理事務,看起來會比較簡單。

步驟和上面有重復的部分,需要導包導入約束,接下來就是配置一下使用注解管理事務的開關

使用注解配置

?
1
2
<!-- 打開注解配置 aop 事務 -->
<tx:annotation-driven/>

下面是使用注解為 service 中的方法配置事務處理的屬性,當然,每一個方法都寫會比較麻煩,也可以在類上面使用注解,若是某個方法的處理規則不一致就單獨使用注解配置一下。

?
1
2
3
@transactional(isolation=isolation.repeatable_read,propagation = propagation.required,readonly=false)
@override
public void transfer(integer from, integer to, double money) {...}

回顧一下,以上主要說了事務以及 spring 中處理事務的方式,而這也正是 aop 思想在 spring 中的應用,我們可以看到不管是前面說的 ioc 還是 aop 在這里都有體現。

注解的出現是為了替換配置文件,所以我就以配置文件為主,并說一下與之對應的注解方式。

spring 中的配置主要在核心配置文件 applicationcontext.xml 中,由不同的標簽來表示,所以首先我們就需要導入各種約束,常用的約束有 bean、context、aop、tx 。

bean 標簽是最基本的標簽,主要用來配置各種對象。

?
1
2
3
4
5
6
7
8
9
10
11
12
13
<!--
屬性介紹:
id: 為對象命名,唯一性標識,不能重復,不能使用特殊字符。
name: 和 id 的作用類似,區別在于可是使用特殊字符,可重復,但是不建議重復。
class: 指定對象的全類名。
init-method: 對象初始化之后立即執行的方法。
destroy-method: 對象銷毀之前執行的方法。
scope: 對象的作用范圍,可以設置單例 singleton 和多例 prototype。默認為單例
 -->
<bean name="userservice" class="yu.service.userserviceimpl" >
 <property name="" value="" ></property>
 <property name="" ref="" ></property>
</bean>

對應的注解有以下幾個,但是想要使用注解之前要首先配置一下……

?
1
2
<!-- 打開注解配置,掃描包及其子包 -->
<context:component-scan base-package="yu"></context:component-scan>

使用注解的時候,我們可以使用 @component 來表示將這個對象交由 spring 管理,@scope 來指定對象的作用域。之后便可以使用 @resource 來獲取對象。

在注冊對象的時候我們可以使用 @component ,但是若是每一個對象都是用這個注解,不能很好的分辨出對象屬于哪一層,所以 spring 又提供了 @controller @service @repository 來分別表示控制器層,service 層和 dao 層的對象,功能和 @component 是一模一樣的。

同樣的在為對象賦值的時候,我們可以使用注解 @autowired 來自動獲取容器中的對象,可是若是有重名的情況就需要另外一個注解 @qualifier 來具體指定叫什么名字,這樣就有點麻煩了,我們一般都是直接使用 @resource 來指定對象。

?
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
@component("user")
@scope("prototype")
public class user{
 private string name;
 
 @value(value = "18") // 屬性注入,項目中不用。
 private integer age;
 
 //@autowired 自動裝配 car 類型變量,同一類型
 //@qualifier("car") 指定具體的是哪一個。
 @resource(name = "car") // 指名道姓指定是哪個對象
 private car car;
 
 ...
 
 @postconstruct
 public void init(){
 system.out.println("init 方法");
 }
 @predestroy
 public void destroy(){
 system.out.println("destory 方法");
 }
}

aop 相關的配置和注解

在 spring 中我們可以自定義通知和切面,下面只是展示了如何配置,但是在具體的業務中應該不會出現 5 種通知齊上陣的現象。

?
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
<aop:config>
 <!-- 配置切點-->
 <aop:pointcut expression="execution(* yu.service.*serviceimpl.*(..))" id="pc"/>
 
 <aop:aspect ref="myadvice" >
  <!-- 指定名為before方法作為前置通知 -->
  <aop:before method="before" pointcut-ref="pc" />
  <!-- 后置 -->
  <aop:after-returning method="afterreturning" pointcut-ref="pc" />
  <!-- 環繞通知 -->
  <aop:around method="around" pointcut-ref="pc" />
  <!-- 異常攔截通知 -->
  <aop:after-throwing method="afterexception" pointcut-ref="pc"/>
  <!-- 后置 -->
  <aop:after method="after" pointcut-ref="pc"/>
 </aop:aspect>
</aop:config>

同樣的,我們也可以使用注解來達到自定義配置的方式。同樣的套路,想用注解配置實現 aop,需要打開注解配置 aop 的開關。

?
1
<aop:aspectj-autoproxy></aop:aspectj-autoproxy>

之后就是在通知類中進行配置即可。

?
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
@aspect
//通知類
public class myadvice {
 
 // 快速配置切點表達式,方法直接調用即可
 @pointcut("execution(* yu.service.*serviceimpl.*(..))")
 public void pc(){}
 
 //前置通知
 @before("myadvice.pc()")
 public void before(){
  system.out.println("這是前置通知!!");
 }
 //后置通知
 @afterreturning("myadvice.pc()")
 public void afterreturning(){
  system.out.println("這是后置通知(如果出現異常不會調用)!!");
 }

context 主要是和全局有關的配置

?
1
2
3
4
5
6
7
8
9
10
11
12
13
14
<!-- 打開注解配置對象,掃描包及其子包 -->
<context:component-scan base-package="yu"></context:component-scan>
 
 
 
<!-- 導入 properties 配置文件 -->
<context:property-placeholder location="classpath:db.properties"/>
 
<bean name="datasource" class="com.mchange.v2.c3p0.combopooleddatasource" >
 <property name="jdbcurl" value="${jdbc.jdbcurl}" ></property>
 <property name="driverclass" value="${jdbc.driverclass}" ></property>
 <property name="user" value="${jdbc.user}" ></property>
 <property name="password" value="${jdbc.password}" ></property>
</bean>

tx 配置事務管理中的通知

tx 用來配置通知對象,而這個對象是由 spring 為我們寫好了,而事務管理依賴于數據庫連接對象,所以你能看到 transactionmanager 對象依賴于 datasource 對象。

?
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
<bean name="transactionmanager" class = "org.springframework.jdbc.datasource.datasourcetransactionmanager">
 <property name="datasource" ref= "datasource"></property>
</bean>
 
<tx:advice id="txadvise" transaction-manager="transactionmanager">
 <tx:attributes>
  <tx:method name="transfer" isolation="default" propagation="required" read-only="false"/>
 </tx:attributes>
</tx:advice>
 
<aop:config>
 <aop:pointcut expression="execution(* yu.transation.*serviceimpl.*(..))" id="txpointcut"/>
 
 <aop:advisor advice-ref="txadvise" pointcut-ref="txpointcut"/>
</aop:config>

使用注解配置時還是需要打開注解配置的開關

?
1
2
<!-- 打開注解配置 aop 事務 -->
<tx:annotation-driven/>

在具體的業務方法上或是類上使用注解 @transactional 來配置事務處理的方式。

?
1
2
3
@transactional(isolation=isolation.repeatable_read,propagation = propagation.required,readonly=false)
@override
public void transfer(integer from, integer to, double money) {...}

最后有一個完美的意外,那就是 import 標簽。用于導入其它的配置模塊到主配置文件中。

?
1
2
<!-- 導入其它的 spring 配置模塊 -->
<import resource="yu/transation/applicationcontext.xml"/>

總結

以上就是這篇文章的全部內容了,希望本文的內容對大家的學習或者工作具有一定的參考學習價值,如果有疑問大家可以留言交流,謝謝大家對服務器之家的支持。

原文鏈接:https://www.cnblogs.com/YJK923/p/10187081.html

延伸 · 閱讀

精彩推薦
Weibo Article 1 Weibo Article 2 Weibo Article 3 Weibo Article 4 Weibo Article 5 Weibo Article 6 Weibo Article 7 Weibo Article 8 Weibo Article 9 Weibo Article 10 Weibo Article 11 Weibo Article 12 Weibo Article 13 Weibo Article 14 Weibo Article 15 Weibo Article 16 Weibo Article 17 Weibo Article 18 Weibo Article 19 Weibo Article 20 Weibo Article 21 Weibo Article 22 Weibo Article 23 Weibo Article 24 Weibo Article 25 Weibo Article 26 Weibo Article 27 Weibo Article 28 Weibo Article 29 Weibo Article 30 Weibo Article 31 Weibo Article 32 Weibo Article 33 Weibo Article 34 Weibo Article 35 Weibo Article 36 Weibo Article 37 Weibo Article 38 Weibo Article 39 Weibo Article 40
主站蜘蛛池模板: 韩国精品一区 | 色在线观看视频 | 91大片在线观看 | 久久av网| 亚洲一区免费在线观看 | 亚洲一区二区免费看 | 色噜噜狠狠狠综合曰曰曰88av | 在线观看日韩av | 国产一区二区三区久久久 | 国产精品极品美女在线观看免费 | 免费观看国产精品 | 九色在线 | 一级黄色毛片 | 日日干夜夜操 | 国产一区二区久久 | 久久精品一区二区国产 | 久久777| 日韩一区在线观看视频 | 免费一区| 韩国三级午夜理伦三级三 | 日韩av片无码一区二区不卡电影 | 欧美一区 | 成人在线一区二区 | 欧美成人免费在线视频 | 国产在线一区二区 | 日韩欧美a级v片免费播放 | 午夜爽视频 | 成人福利视频网 | 国产精品免费av | 亚洲美女在线视频 | 亚洲日韩中文字幕一区 | 久久99精品久久久久久琪琪 | 一级片在线观看 | 1000部精品久久久久久久久 | 亚洲国产欧美日韩 | av大全在线 | 国产精品69毛片高清亚洲 | 久久人人爽爽爽人久久久 | 亚洲一区中文字幕在线观看 | 五月天一区二区 | 在线亚洲精品 |