springAop:面向切面的編程
應用場景:權限控制掀序、事物管理璧疗、日志打印等等肴甸,就是在不同的方法中重復用到相同的代碼或者重復的操作是可以用Aop來解決相嵌。
在Spring的AOP編程中屎暇,
???????? 如果加入容器的目標對象有實現(xiàn)接口承桥,用JDK代理;
???????? 如果目標對象沒有實現(xiàn)接口恭垦,用Cglib代理快毛;
手動實現(xiàn)AOP編程
AOP 面向切面的編程,
???????? AOP可以實現(xiàn)“業(yè)務代碼”與“關注點代碼”分離
// 保存一個用戶
public void add(User user) {
?????????????????? Session? session = null;
?????????????????? Transaction? trans = null;
?????????????????? try? {
??????????????????????????? session? = HibernateSessionFactoryUtils.getSession();??//【關注點代碼】
??????????????????????????? trans? = session.beginTransaction();??? //【關注點代碼】
??????????????????????????? ?
??????????????????????????? session.save(user);??? ?//核心業(yè)務代碼
??????????????????????????? ?
??????????????????????????? trans.commit();????//…【關注點代碼】
?????????????????? }? catch (Exception e) {????
??????????????????????????? e.printStackTrace();
??????????????????????????? if(trans? != null){
???????????????????????????????????? trans.rollback();??//..【關注點代碼】
??????????????????????????? }
?????????????????? }? finally{
??????????????????????????? HibernateSessionFactoryUtils.closeSession(session);??////..【關注點代碼】
?????????????????? }
??
? }
分析總結(jié):
???????? 關注點代碼番挺,就是指重復執(zhí)行的代碼唠帝。
???????? 業(yè)務代碼與關注點代碼分離,好處玄柏?
???????? ?? --à 關注點代碼寫一次即可襟衰;
?????????????????? -à開發(fā)者只需要關注核心業(yè)務;
?????????????????? -à運行時期粪摘,執(zhí)行核心業(yè)務代碼時候動態(tài)植入關注點代碼瀑晒;【代理】
如何分離?
???????? 過程式/對象式/代理模式分離
AOP編程
概述:
AOP: Aspect Oriented Programming 面向切面編程徘意√υ茫 面向切面編程(也叫面向方面):Aspect Oriented Programming(AOP),是目前軟件開發(fā)中的一個熱點。利用AOP可以對業(yè)務邏輯的各個部分進行隔離椎咧,從而使得業(yè)務邏輯各部分之間的耦合度降低玖详,提高程序的可重用性,同時提高了開發(fā)的效率勤讽◇ AOP是OOP的延續(xù),是(Aspect Oriented Programming)的縮寫脚牍,意思是面向切面(方面)編程向臀。 主要的功能是:日志記錄诸狭,性能統(tǒng)計券膀,安全控制,事務處理作谚,異常處理等等三娩。 主要的意圖是:將日志記錄妹懒,性能統(tǒng)計雀监,安全控制,事務處理,異常處理等代碼從業(yè)務邏輯代碼中劃分出來会前,通過對這些行為的分離好乐,我們希望可以將它們獨立到非指導業(yè)務邏輯的方法中,進而改 ?變這些行為的時候不影響業(yè)務邏輯的代碼瓦宜。
[if !supportLineBreakNewLine]
[endif]
可以通過預編譯方式和運行期動態(tài)代理實現(xiàn)在不修改源代碼的情況下給程序動態(tài)統(tǒng)一添加功能的一種技術蔚万。AOP實際是GoF設計模式的延續(xù),設計模式孜孜不倦追求的是調(diào)用者和被調(diào)用者之間的解耦临庇,AOP可以說也是這種目標的一種實現(xiàn)反璃。
假設把應用程序想成一個立體結(jié)構(gòu)的話,OOP的利刃是縱向切入系統(tǒng)假夺,把系統(tǒng)劃分為很多個模塊(如:用戶模塊淮蜈,文章模塊等等),而AOP的利刃是橫向切入系統(tǒng)已卷,提取各個模塊可能都要重復操作的部分(如:權限檢查梧田,日志記錄等等)。由此可見侧蘸,AOP是OOP的一個有效補充裁眯。
注意:AOP不是一種技術,實際上是編程思想讳癌。凡是符合AOP思想的技術穿稳,都可以看成是AOP的實現(xiàn)。
Aop晌坤,? aspect objectprogramming? 面向切面編程
???????? 功能:讓關注點代碼與業(yè)務代碼分離司草!
關注點,
???????? 重復代碼就叫做關注點;
切面泡仗,
???????? ?關注點形成的類,就叫切面(類)猜憎!
???????? ?面向切面編程娩怎,就是指對很多功能都有的重復的代碼抽取,再在運行的時候網(wǎng)業(yè)務方法上動態(tài)植入“切面類代碼”胰柑。
切入點截亦,
???????? 執(zhí)行目標對象方法,動態(tài)植入切面代碼柬讨。
???????? 可以通過切入點表達式崩瓤,指定攔截哪些類的哪些方法;給指定的類在運行的時候植入切面類代碼踩官。
注解方式實現(xiàn)AOP編程
? 開啟事物注解權限
4) 使用注解
@Aspect????????????????????????????????????????????????????????????? 指定一個類為切面類?????????????
@Pointcut("execution(*com.itmayiedu.service.UserService.add(..))")? 指定切入點表達式
@Before("pointCut_()")?????????????????????????????????? 前置通知: 目標方法之前執(zhí)行
@After("pointCut_()")????????????????????????????????????? 后置通知:目標方法之后執(zhí)行(始終執(zhí)行)
@AfterReturning("pointCut_()")????????? ??? 返回后通知:執(zhí)行方法結(jié)束前執(zhí)行(異常不執(zhí)行)
@AfterThrowing("pointCut_()")??????????????????? 異常通知:? 出現(xiàn)異常時候執(zhí)行
@Around("pointCut_()")????????????????????????????????? 環(huán)繞通知:環(huán)繞目標方法執(zhí)行
@Component
@Aspect
public class Aop {
??? @Before("execution(*
? com.itmayiedu.service.UserService.add(..))")
??? public void begin() {
??????? System.out.println("前置通知");
??? }
?
??? @After("execution(*
? com.itmayiedu.service.UserService.add(..))")
??? public void commit() {
??????? System.out.println("后置通知");
??? }
?
??? @AfterReturning("execution(*
? com.itmayiedu.service.UserService.add(..))")
??? public void afterReturning() {
??????? System.out.println("運行通知");
??? }
?
??? @AfterThrowing("execution(*
? com.itmayiedu.service.UserService.add(..))")
??? public void afterThrowing() {
??????? System.out.println("異常通知");
??? }
?
??? @Around("execution(*
? com.itmayiedu.service.UserService.add(..))")
??? public voidaround(ProceedingJoinPointproceedingJoinPoint) throws Throwable {
?????? System.out.println("我是環(huán)繞通知-前");
?????? proceedingJoinPoint.proceed();
?????? System.out.println("我是環(huán)繞通知-后");
??? }
?
}
XML方式實現(xiàn)AOP編程
Xml實現(xiàn)aop編程:
???????? 1)引入jar文件? 【aop 相關jar却桶, 4個】
???????? 2)引入aop名稱空間
???????? 3)aop 配置
?????????????????? *配置切面類(重復執(zhí)行代碼形成的類)
?????????????????? *aop配置
??????????????????????????? 攔截哪些方法 / 攔截到方法后應用通知代碼
"1.0"encoding="UTF-8"?>
"http://www.springframework.org/schema/beans"
? xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
? xmlns:p="http://www.springframework.org/schema/p"
? xmlns:context="http://www.springframework.org/schema/context"
? xmlns:aop="http://www.springframework.org/schema/aop"
? xsi:schemaLocation="
???????
? http://www.springframework.org/schema/beans
???????
? http://www.springframework.org/schema/beans/spring-beans.xsd
???????
? http://www.springframework.org/schema/context
???????
? http://www.springframework.org/schema/context/spring-context.xsd
?? ?????http://www.springframework.org/schema/aop
???????
? http://www.springframework.org/schema/aop/spring-aop.xsd">
??? "userDao"class="com.itmayiedu.UserDao">
??? "orderDao"class="com.itmayiedu.OrderDao">
??? "aop"class="com.itmayiedu.Aop">
???
??????? "execution(* com.itmayiedu.*.*(..))"id="pt"/>
??????? "aop">
??? ??????? "around"pointcut-ref="pt"/>
??????????? "begin"pointcut-ref="pt"/>
??????????? "after" pointcut-ref="pt"/>
??????????? "afterReturning" pointcut-ref="pt"/>
??????????? "afterThrowing"pointcut-ref="pt"/>
事物的概述
⑴原子性(Atomicity)
原子性是指事務包含的所有操作要么全部成功,要么全部失敗回滾,因此事務的操作如果成功就必須要完全應用到數(shù)據(jù)庫颖系,如果操作失敗則不能對數(shù)據(jù)庫有任何影響嗅剖。
⑵ 一致性(Consistency)
一致性是指事務必須使數(shù)據(jù)庫從一個一致性狀態(tài)變換到另一個一致性狀態(tài),也就是說一個事務執(zhí)行之前和執(zhí)行之后都必須處于一致性狀態(tài)嘁扼。
拿轉(zhuǎn)賬來說信粮,假設用戶A和用戶B兩者的錢加起來一共是5000,那么不管A和B之間如何轉(zhuǎn)賬趁啸,轉(zhuǎn)幾次賬强缘,事務結(jié)束后兩個用戶的錢相加起來應該還得是5000,這就是事務的一致性不傅。
⑶ 隔離性(Isolation)
隔離性是當多個用戶并發(fā)訪問數(shù)據(jù)庫時旅掂,比如操作同一張表時,數(shù)據(jù)庫為每一個用戶開啟的事務蛤签,不能被其他事務的操作所干擾辞友,多個并發(fā)事務之間要相互隔離。
即要達到這么一種效果:對于任意兩個并發(fā)的事務T1和T2震肮,在事務T1看來称龙,T2要么在T1開始之前就已經(jīng)結(jié)束,要么在T1結(jié)束之后才開始戳晌,這樣每個事務都感覺不到有其他事務在并發(fā)地執(zhí)行鲫尊。
關于事務的隔離性數(shù)據(jù)庫提供了多種隔離級別,稍后會介紹到沦偎。
⑷ 持久性(Durability)
持久性是指一個事務一旦被提交了疫向,那么對數(shù)據(jù)庫中的數(shù)據(jù)的改變就是永久性的,即便是在數(shù)據(jù)庫系統(tǒng)遇到故障的情況下也不會丟失提交事務的操作豪嚎。
例如我們在使用JDBC操作數(shù)據(jù)庫時搔驼,在提交事務方法后,提示用戶事務操作完成侈询,當我們程序執(zhí)行完成直到看到提示后舌涨,就可以認定事務以及正確提交,即使這時候數(shù)據(jù)庫出現(xiàn)了問題扔字,也必須要將我們的事務完全執(zhí)行完成囊嘉,否則就會造成我們看到提示事務處理完畢,但是數(shù)據(jù)庫因為故障而沒有執(zhí)行事務的重大錯誤革为。
程序中事務控制
環(huán)境準備
用戶訪問—》C--》 Service---》Dao
一個業(yè)務的成功:調(diào)用的service是執(zhí)行成功的扭粱,意味著service中調(diào)用的所有的dao是執(zhí)行成功的。?事務應該在Service層統(tǒng)一控制震檩。
?
1)沒有應用事務的代碼:
2)模擬:
在service中調(diào)用2次dao琢蛤,希望其中一個dao執(zhí)行失敗,整個操作要回滾。
開發(fā)步驟:
???????? 1.后臺環(huán)境準備
數(shù)據(jù)庫虐块、表/entity/dao/service
???????? 2.dao的實現(xiàn)用JdbcTemplate
???????? 3.對象創(chuàng)建都有Spring容器完成
程序中事務控制
事務控制概述
編程式事務控制
???????? 自己手動控制事務俩滥,就叫做編程式事務控制。
???????? Jdbc代碼:
?????????????????? Conn.setAutoCommite(false);? //設置手動控制事務
???????? Hibernate代碼:
?????????????????? Session.beginTransaction();??? //開啟一個事務
???????? 【細粒度的事務控制: 可以對指定的方法贺奠、指定的方法的某幾行添加事務控制】
???????? (比較靈活霜旧,但開發(fā)起來比較繁瑣: 每次都要開啟、提交儡率、回滾.)
?
聲明式事務控制
???????? Spring提供了對事務的管理, 這個就叫聲明式事務管理挂据。
???????? Spring提供了對事務控制的實現(xiàn)。用戶如果想用Spring的聲明式事務管理儿普,只需要在配置文件中配置即可崎逃; 不想使用時直接移除配置。這個實現(xiàn)了對事務控制的最大程度的解耦眉孩。
???????? Spring聲明式事務管理个绍,核心實現(xiàn)就是基于Aop。
???????? 【粗粒度的事務控制: 只能給整個方法應用事務浪汪,不可以對方法的某幾行應用事務巴柿。】
???????? (因為aop攔截的是方法死遭。)
???????? Spring聲明式事務管理器類:
?????????????????? Jdbc技術:DataSourceTransactionManager
?????????????????? Hibernate技術:HibernateTransactionManager
編程事物管理
手動管理事物
1. UserDao.java
@Repository
public class UserDao {
????? @Autowired
????? private JdbcTemplate jdbcTemplate;
????? public void add(String name, Integer age) {
?????????? Stringsql = "INSERT INTO users(NAME, age) VALUES(?,?);";
?????????? int update = jdbcTemplate.update(sql, name, age);
?????????? System.out.println("updateResult:" + update);
????? }
}
2. UserService
@Service
public class UserService
? {
???? @Autowired
???? private UserDao userDao;
???? public void add() {
???????? userDao.add("lisi", 18);
???????? int i=1/0;//可能會發(fā)生異常
???????? userDao.add("yushengjun", 19);
???? }
}
3. App 測試類
public class UserTest {
???? public static void main(String[] args) {
???????? ClassPathXmlApplicationContextapplicationContext = new ClassPathXmlApplicationContext("bean.xml");
???????? UserServiceuserService = (UserService) applicationContext.getBean("userService");
???????? userService.add();
???? }
}
4.手動事物管理類
@Component
public class TransactionUtils {
????? // 事物管理器
????? @Autowired
????? private DataSourceTransactionManager dataSourceTransactionManager;
????? public TransactionStatus begin() {
?????????? TransactionStatustransaction = dataSourceTransactionManager.getTransaction(new DefaultTransactionDefinition());
?????????? return transaction;
????? }
????? public void commit(TransactionStatus transaction) {
?????????? dataSourceTransactionManager.commit(transaction);
????? }
????? public void rollback(TransactionStatus transaction) {
?????????? dataSourceTransactionManager.rollback(transaction);
????? }
}
5. bean.xml? (Spring務管理配置)
xmlversion="1.0"encoding="UTF-8"?>
<beansxmlns="http://www.springframework.org/schema/beans"
???? xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"xmlns:p="http://www.springframework.org/schema/p"
???? xmlns:context="http://www.springframework.org/schema/context"
???? xmlns:aop="http://www.springframework.org/schema/aop"xmlns:tx="http://www.springframework.org/schema/tx"
???? xsi:schemaLocation="http://www.springframework.org/schema/beans
???? ?http://www.springframework.org/schema/beans/spring-beans.xsd
????? ?http://www.springframework.org/schema/context
????????
? http://www.springframework.org/schema/context/spring-context.xsd
????????
? http://www.springframework.org/schema/aop
????????
? http://www.springframework.org/schema/aop/spring-aop.xsd
????????
? http://www.springframework.org/schema/tx
????? ?http://www.springframework.org/schema/tx/spring-tx.xsd">
???? 開啟注解 -->
???? <context:component-scanbase-package="com.itmayiedu">
???? 數(shù)據(jù)源對象: C3P0連接池 -->
???? <beanid="dataSource"class="com.mchange.v2.c3p0.ComboPooledDataSource">
???????? <propertyname="driverClass"value="com.mysql.jdbc.Driver">
???????? <propertyname="jdbcUrl"value="jdbc:mysql://localhost:3306/test">
???????? <propertyname="user"value="root">
???????? <propertyname="password"value="root">
???? bean>
?
???? 工具類實例 -->
???? <beanid="jdbcTemplate"class="org.springframework.jdbc.core.JdbcTemplate">
???????? <propertyname="dataSource"ref="dataSource">
???? bean>
?
??
? 配置事物 -->
??
? <bean? id="DataSourceTransactionManager"class="org.springframework.jdbc.datasource.DataSourceTransactionManager">
???
? <propertyname="dataSource"ref="dataSource">
??
? bean>
beans>?? ????
?
聲明式事務管理
?XML方式實現(xiàn)
1. UserDao.java
@Repository
public class UserDao {
????? @Autowired
????? private JdbcTemplate jdbcTemplate;
????? public void add(String name, Integer age) {
?????????? Stringsql = "INSERT INTO users(NAME, age) VALUES(?,?);";
?????????? int update = jdbcTemplate.update(sql, name, age);
?????????? System.out.println("updateResult:" + update);
????? }
}
2. UserService
@Service
public class UserService
? {
???? @Autowired
???? private UserDao userDao;
???? public void add() {
???????? userDao.add("lisi", 18);
???????? int i=1/0;//可能會發(fā)生異常
???????? userDao.add("yushengjun", 19);
???? }
}
3. App 測試類
public class UserTest {
???? public static void main(String[] args) {
???????? ClassPathXmlApplicationContextapplicationContext = new ClassPathXmlApplicationContext("bean.xml");
???????? UserServiceuserService = (UserService) applicationContext.getBean("userService");
???????? userService.add();
???? }
}
4.手動事物管理類
@Component
public class TransactionUtils {
????? // 事物管理器
????? @Autowired
????? private DataSourceTransactionManager dataSourceTransactionManager;
????? public TransactionStatus begin() {
?????????? TransactionStatustransaction = dataSourceTransactionManager.getTransaction(new DefaultTransactionDefinition());
?????????? return transaction;
????? }
????? public void commit(TransactionStatus transaction) {
?????????? dataSourceTransactionManager.commit(transaction);
????? }
????? public void rollback(TransactionStatus transaction) {
?????????? dataSourceTransactionManager.rollback(transaction);
????? }
}
5. bean.xml? (Spring務管理配置)
????? 開啟注解 -->
????? <context:component-scanbase-package="com.itmayiedu">
????? 數(shù)據(jù)源對象: C3P0連接池 -->
????? <beanid="dataSource"class="com.mchange.v2.c3p0.ComboPooledDataSource">
?????????? <propertyname="driverClass"value="com.mysql.jdbc.Driver">
?????????? <propertyname="jdbcUrl"value="jdbc:mysql://localhost:3306/test">
?????????? <propertyname="user"value="root">
?????????? <propertyname="password"value="root">
????? bean>
????? 工具類實例 -->
????? <beanid="jdbcTemplate"class="org.springframework.jdbc.core.JdbcTemplate">
?????????? <propertyname="dataSource"ref="dataSource">
????? bean>
????? 配置事物 -->
????? <beanid="dataSourceTransactionManager"
?????????? class="org.springframework.jdbc.datasource.DataSourceTransactionManager">
?????????? <propertyname="dataSource"ref="dataSource">
????? bean>
?? ?? 配置事物增強-->
????? <tx:adviceid="txAdvice"transaction-manager="dataSourceTransactionManager">
?????????? <tx:attributes>
???????????????? <tx:methodname="get*"read-only="true"/>
???????????????? <tx:methodname="find*"read-only="true"/>
???????????????? <tx:methodname="*"read-only="false"/>
?????????? tx:attributes>
????? tx:advice>
????? 配置: 攔截哪些方法(切入點表表達式) + 應用上面的事務增強配置 -->
????? <aop:config>
?????????? <aop:pointcutexpression="execution(* com.itmayiedu.service.*.*(..))"
???????????????? id="pt"/>
?????????? <aop:advisoradvice-ref="txAdvice"pointcut-ref="pt"/>
????? aop:config>
使用事物注意事項
?事物是程序運行如果沒有錯誤,會自動提交事物,如果程序運行發(fā)生異常,則會自動回滾广恢。
?如果使用了try捕獲異常時.一定要在catch里面手動回滾。
?事物手動回滾代碼
TransactionAspectSupport.currentTransactionStatus().setRollbackOnly();
注解方式實現(xiàn)
使用注解實現(xiàn)Spring的聲明式事務管理呀潭,更加簡單钉迷!
步驟:
???????? 1)必須引入Aop相關的jar文件
???????? 2) bean.xml中指定注解方式實現(xiàn)聲明式事務管理以及應用的事務管理器類
???????? 3)在需要添加事務控制的地方,寫上: @Transactional
@Transactional注解:
???????? 1)應用事務的注解
???????? 2)定義到方法上:當前方法應用spring的聲明式事務
???????? 3)定義到類上:?? 當前類的所有的方法都應用Spring聲明式事務管理;
???????? 4)定義到父類上:當執(zhí)行父類的方法時候應用事務钠署。
Bean.xm
xmlversion="1.0"encoding="UTF-8"?>
<beansxmlns="http://www.springframework.org/schema/beans"
???? xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"xmlns:p="http://www.springframework.org/schema/p"
???? xmlns:context="http://www.springframework.org/schema/context"
???? xmlns:aop="http://www.springframework.org/schema/aop"xmlns:tx="http://www.springframework.org/schema/tx"
???? xsi:schemaLocation="http://www.springframework.org/schema/beans
???? ?http://www.springframework.org/schema/beans/spring-beans.xsd
????? ?http://www.springframework.org/schema/context
????????
? http://www.springframework.org/schema/context/spring-context.xsd
????????
? http://www.springframework.org/schema/aop
????????
? http://www.springframework.org/schema/aop/spring-aop.xsd
????????
? http://www.springframework.org/schema/tx
????? ?http://www.springframework.org/schema/tx/spring-tx.xsd">
???? 開啟注解 -->
???? <context:component-scanbase-package="com.itmayiedu">
???? 數(shù)據(jù)源對象: C3P0連接池 -->
???? <beanid="dataSource"class="com.mchange.v2.c3p0.ComboPooledDataSource">
???????? <propertyname="driverClass"value="com.mysql.jdbc.Driver">
???????? <propertyname="jdbcUrl"value="jdbc:mysql://localhost:3306/test">
???????? <propertyname="user"value="root">
???????? <propertyname="password"value="root">
???? bean>
?
???? 工具類實例 -->
???? <beanid="jdbcTemplate"class="org.springframework.jdbc.core.JdbcTemplate">
???????? <propertyname="dataSource"ref="dataSource">
???? bean>
?
???? 配置事物 -->
???? <beanid="dataSourceTransactionManager"
???????? class="org.springframework.jdbc.datasource.DataSourceTransactionManager">
???????? <propertyname="dataSource"ref="dataSource">
???? bean>
???? 開啟注解事物 -->
???
? <tx:annotation-driventransaction-manager="dataSourceTransactionManager"/>
beans> ????
UserService
@Transactional
??? public void add() {
??????? try {
??????????? userDao.add("lisi", 18);
??????????? int i = 1 / 0;
??????????? userDao.add("yushengjun", 19);
??????? }catch (Exception e) {
??????????? TransactionAspectSupport.currentTransactionStatus().setRollbackOnly();
??????? }
???????
??? }
傳播七種行為
Spring中事務的定義:
Propagation(key屬性確定代理應該給哪個方法增加事務行為糠聪。這樣的屬性最重要的部份是傳播行為。)有以下選項可供使用:
PROPAGATION_REQUIRED--支持當前事務谐鼎,如果當前沒有事務枷颊,就新建一個事務。這是最常見的選擇该面。
PROPAGATION_SUPPORTS--支持當前事務,如果當前沒有事務信卡,就以非事務方式執(zhí)行隔缀。
PROPAGATION_MANDATORY--支持當前事務,如果當前沒有事務傍菇,就拋出異常猾瘸。
PROPAGATION_REQUIRES_NEW--新建事務,如果當前存在事務,把當前事務掛起牵触。
PROPAGATION_NOT_SUPPORTED--以非事務方式執(zhí)行操作淮悼,如果當前存在事務,就把當前事務掛起揽思。
PROPAGATION_NEVER--以非事務方式執(zhí)行袜腥,如果當前存在事務,則拋出異常钉汗。
@Transactional(
????????????? readOnly? =false,? // 讀寫事務
????????????? timeout? = -1,?????? // 事務的超時時間不限制
????????????? noRollbackFor? = ArithmeticException.class,? // 遇到數(shù)學異常不回滾
????????????? isolation? = Isolation.DEFAULT,????????????? // 事務的隔離級別羹令,數(shù)據(jù)庫的默認
????????????? propagation= Propagation.REQUIRED??????????? // 事務的傳播行為
???? )
事務傳播行為:
???????? Propagation.REQUIRED
?????????????????? 指定當前的方法必須在事務的環(huán)境下執(zhí)行;
?????????????????? 如果當前運行的方法损痰,已經(jīng)存在事務福侈,就會加入當前的事務;
???????? Propagation.REQUIRED_NEW
?????????????????? 指定當前的方法必須在事務的環(huán)境下執(zhí)行卢未;
?????????????????? 如果當前運行的方法肪凛,已經(jīng)存在事務:? 事務會掛起;會始終開啟一個新的事務辽社,執(zhí)行完后伟墙;? 剛才掛起的事務才繼續(xù)運行。
舉例:
Class Log{
?????????????????? Propagation.REQUIRED
?????????????????? insertLog();?
}
???????? Propagation.REQUIRED
???????? Void?saveDept(){
?????????????????? insertLog();? ??//加入當前事務
?????????????????? ..異常, 會回滾
?????????????????? saveDept();
???????? }
???????? ClassLog{
?????????????????? Propagation.REQUIRED_NEW
?????????????????? insertLog();?
}
???????? Propagation.REQUIRED
???????? Void?saveDept(){
?????????????????? insertLog();? ??//始終開啟事務
?????????????????? ..異常, 日志不會回滾
?????????????????? saveDept();
???????? }
測試步驟:
???????? 1)日志表Log_
???????? 2)LogService.java
??????????????????????????? insertLog();