<kbd id="afajh"><form id="afajh"></form></kbd>
<strong id="afajh"><dl id="afajh"></dl></strong>
    <del id="afajh"><form id="afajh"></form></del>
        1. <th id="afajh"><progress id="afajh"></progress></th>
          <b id="afajh"><abbr id="afajh"></abbr></b>
          <th id="afajh"><progress id="afajh"></progress></th>

          Spring事務(wù)管理

          共 14369字,需瀏覽 29分鐘

           ·

          2021-01-27 17:11

          點(diǎn)擊上方藍(lán)色字體,選擇“標(biāo)星公眾號(hào)”

          優(yōu)質(zhì)文章,第一時(shí)間送達(dá)

          ? 作者?|? 笑忘書(shū)丶

          來(lái)源 |? urlify.cn/vay6fu

          76套java從入門(mén)到精通實(shí)戰(zhàn)課程分享

          Spring的事務(wù)管理簡(jiǎn)化了傳統(tǒng)的事務(wù)管理流程,提高了開(kāi)發(fā)效率。但是首先先要了解Spring的數(shù)據(jù)庫(kù)編程。

          Spring的數(shù)據(jù)庫(kù)編程

          數(shù)據(jù)庫(kù)編程是互聯(lián)網(wǎng)編程的基礎(chǔ),Spring框架為開(kāi)發(fā)者提供了JDBC模板模式,即jdbcTemplate,它可以簡(jiǎn)化許多代碼,但在實(shí)際應(yīng)用中jdbcTemplate使用并不常見(jiàn),在大多數(shù)時(shí)候都采用Spring結(jié)合MyBatis進(jìn)行開(kāi)發(fā)。在這里,只講述Spring的jdbcTemplate開(kāi)發(fā)。

          SpringJDBC的配置

          本節(jié)Spring數(shù)據(jù)庫(kù)編程主要使用的是SpringJDBC模塊的core和DataSource包,core是JDBC的核心包,包括常用的JdbcTemplate類(lèi),DataSource是訪問(wèn)數(shù)據(jù)源的工具類(lèi)包。如果要使用SpringJDBC操作數(shù)據(jù)庫(kù),需要進(jìn)行配置,配置如下:


          "dataSource"?class="org.springframework.jdbc.datasource.DriverManagerDataSource">
          ????
          ????"driverClassName"?value="com.mysql.jdbc.Driver"/>
          ????
          ????"url"?value="jdbc:mysql://localhost:3306/spring?characterEncoding=utf-8"/>
          ????
          ????"username"?value="root"/>
          ????"password"?value="root"/>


          "jdbcTemplate"?class="org.springframework.jdbc.core.JdbcTemplate">
          ????"dataSource"?ref="dataSource"/>


          在上述示例中,配置JDBC模板需要將dataSource注入到j(luò)dbcTemplate,而在數(shù)據(jù)訪問(wèn)層(Dao)中需要使用jdbcTemplate時(shí)也需要將jdbcTemplate注入到對(duì)應(yīng)的bean中。

          @Repository("testDao")
          public?class?TestDaoImpl?implements?TestDao?{
          ????@Autowired?//按照類(lèi)型注入
          ????private?JdbcTemplate?jdbcTemplate;

          JDBCTemplate的常用方法

          public int update(String sql,Object args[]):該方法可以對(duì)數(shù)據(jù)表進(jìn)行增加、修改、刪除。使用args[]設(shè)置參數(shù),函數(shù)返回的是更新的行數(shù)。示例如下:

          String?insertSQL="insert?into?user?values(NULL,?,?)";
          Onject?param[]?=?{"chencheng","m"};
          jdbcTemplate.update(insertSQL,param);

          public List query(String sql,RowMapper rowmapper,Object args[]):該方法可以對(duì)數(shù)據(jù)表進(jìn)行查詢(xún)操作,rowMapper將結(jié)果集映射到用戶自定義的類(lèi)中(前提是類(lèi)的屬性名與字段名相同)。示例如下:

          jdbcTemplate.query(sql,new?BeanPropertyRowMapper(User.class),param);

          具體的實(shí)現(xiàn)步驟

          1. 創(chuàng)建并編輯配置文件applicationContext.xml


          2. "1.0"?encoding="UTF-8"?>
            "http://www.springframework.org/schema/beans"
            ???????xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
            ???????xmlns:aop="http://www.springframework.org/schema/aop"
            ???????xmlns:context="http://www.springframework.org/schema/context"
            ???????xsi:schemaLocation="http://www.springframework.org/schema/beans
            ????????http://www.springframework.org/schema/beans/spring-beans.xsd
            ????????http://www.springframework.org/schema/aop
            ????????http://www.springframework.org/schema/aop/spring-aop.xsd
            ????????http://www.springframework.org/schema/context
            ????????http://www.springframework.org/schema/context/spring-context.xsd"
            >
            ????
            ????"com.ch5"/>
            ????
            ????"dataSource"?class="org.springframework.jdbc.datasource.DriverManagerDataSource">
            ????????
            ????????"driverClassName"?value="com.mysql.jdbc.Driver"/>
            ????????
            ????????"url"?value="jdbc:mysql://localhost:3306/spring?characterEncoding=utf-8"/>
            ????????
            ????????"username"?value="root"/>
            ????????"password"?value="root"/>
            ????
            ????
            ????"jdbcTemplate"?class="org.springframework.jdbc.core.JdbcTemplate">
            ????????"dataSource"?ref="dataSource"/>
            ????


            2.創(chuàng)建映射數(shù)據(jù)庫(kù)的實(shí)體類(lèi)

          package?com.ch5;
          ?
          public?class?User?{
          ????private?Integer?id;
          ????private?String?name;
          ????private?double?money;
          ?
          ????public?Integer?getId()?{
          ????????return?id;
          ????}
          ?
          ????public?void?setId(Integer?id)?{
          ????????this.id?=?id;
          ????}
          ?
          ????public?String?getName()?{
          ????????return?name;
          ????}
          ?
          ????public?void?setName(String?name)?{
          ????????this.name?=?name;
          ????}
          ?
          ????public?double?getMoney()?{
          ????????return?money;
          ????}
          ?
          ????public?void?setMoney(double?money)?{
          ????????this.money?=?money;
          ????}
          ?
          ????@Override
          ????public?String?toString()?{
          ????????return?"User{"?+
          ????????????????"id="?+?id?+
          ????????????????",?name='"?+?name?+?'\''?+
          ????????????????",?money="?+?money?+
          ????????????????'
          }';
          ????}
          }

          1. 創(chuàng)建數(shù)據(jù)庫(kù)訪問(wèn)層TestDao和TestDaoImpl

          package?com.ch5.dao;
          import?com.ch5.User;
          import?java.util.List;
          public?interface?TestDao?{
          ????public?int?update(String?sql,Object[]?param);
          ????public?List?query(String?sql,Object[]?param);
          }

          package?com.ch5.dao.Impl;
          import?com.ch5.User;
          import?com.ch5.dao.TestDao;
          import?org.springframework.beans.factory.annotation.Autowired;
          import?org.springframework.jdbc.core.BeanPropertyRowMapper;
          import?org.springframework.jdbc.core.JdbcTemplate;
          import?org.springframework.stereotype.Repository;
          import?java.util.List;
          @Repository("testDao")
          public?class?TestDaoImpl?implements?TestDao?{
          ????@Autowired?//按照類(lèi)型注入
          ????private?JdbcTemplate?jdbcTemplate;
          ????@Override
          ????public?int?update(String?sql,?Object[]?param)?{
          ????????return?jdbcTemplate.update(sql,param);
          ????}
          ????@Override
          ????public?List?query(String?sql,?Object[]?param)?{
          ????????return?jdbcTemplate.query(sql,new?BeanPropertyRowMapper(User.class),param);
          ????}
          }

          1. 編寫(xiě)測(cè)試類(lèi)JdbcTemplateTest


          package?com.ch5.Test;
          ?
          import?com.ch5.User;
          import?com.ch5.dao.TestDao;
          import?org.springframework.context.ApplicationContext;
          import?org.springframework.context.support.ClassPathXmlApplicationContext;
          ?
          import?java.util.List;
          ?
          public?class?JdbcTemplateTest?{
          ????public?static?void?main(String[]?args)?{
          ????????ApplicationContext?appCo?=?new?ClassPathXmlApplicationContext("appliationContext.xml");
          ????????TestDao?testDao=(TestDao)appCo.getBean("testDao");
          ????????String?insertSql="insert?into?account?values(null,?,?)";
          ????????Object?param[]?=?{"chencheng",1050.0};
          ????????testDao.update(insertSql,param);
          ????????String?selectSql="select?*?from?account";
          ????????List?list=testDao.query(selectSql,null);
          ????????for?(User?user?:?list)?{
          ????????????System.out.println(user);
          ????????}
          ????}
          }


          編程式事務(wù)管理


          在代碼中顯式的調(diào)用beginTransactioncommitrollback等與事務(wù)處理相關(guān)的方法,這就是編程式事務(wù)管理,當(dāng)只有少數(shù)事務(wù)操作時(shí),編程式事務(wù)管理才比較適合。

          基于XML的AOP實(shí)現(xiàn)事務(wù)控制

          1. 編寫(xiě)事務(wù)管理的類(lèi)

          package?com.itheima.utils;
          /**
          ?*?和事務(wù)管理相關(guān)的工具類(lèi),它包含了,開(kāi)啟事務(wù),提交事務(wù),回滾事務(wù)和釋放連接
          ?*/
          public?class?TransactionManager?{
          ????private?ConnectionUtils?connectionUtils;
          ????public?void?setConnectionUtils(ConnectionUtils?connectionUtils)?{
          ????????this.connectionUtils?=?connectionUtils;
          ????}
          ????/**
          ?????*?開(kāi)啟事務(wù)
          ?????*/
          ????public??void?beginTransaction(){
          ????????try?{
          ????????????connectionUtils.getThreadConnection().setAutoCommit(false);
          ????????}catch?(Exception?e){
          ????????????e.printStackTrace();
          ????????}
          ????}
          ????/**
          ?????*?提交事務(wù)
          ?????*/
          ????public??void?commit(){
          ????????try?{
          ????????????connectionUtils.getThreadConnection().commit();
          ????????}catch?(Exception?e){
          ????????????e.printStackTrace();
          ????????}
          ????}
          ????/**
          ?????*?回滾事務(wù)
          ?????*/
          ????public??void?rollback(){
          ????????try?{
          ????????????connectionUtils.getThreadConnection().rollback();
          ????????}catch?(Exception?e){
          ????????????e.printStackTrace();
          ????????}
          ????}
          ????/**
          ?????*?釋放連接
          ?????*/
          ????public??void?release(){
          ????????try?{
          ????????????connectionUtils.getThreadConnection().close();//還回連接池中
          ????????????connectionUtils.removeConnection();
          ????????}catch?(Exception?e){
          ????????????e.printStackTrace();
          ????????}
          ????}
          }

          1. 配置aop


          "txManager"?class="com.itheima.utils.TransactionManager">
          ????
          ???"connectionUtils"?ref="connectionUtils">


          ????????"pt1"?expression="execution(*?com.itheima.service.impl.*.*(..)"/>
          ????????"txAdvice"?ref="txManager">
          ????????
          ????????????"beginTransaction"?pointcut-ref="pt1"/>
          ????????
          ????????????"commit"?pointcut-ref="pt1"/>
          ????????
          ????????????"rollback"?pointcut-ref="pt1"/>
          ????????
          ????????????"release"?pointcut-ref="pt1"/>
          ????????
          ????


          基于底層API的編程式事務(wù)管理

          基于底層API的編程式事務(wù)管理就是根據(jù)PlatformTransactionManagerTransactionDefinitionTeansactionStatus等幾個(gè)核心接口,通過(guò)編程的方式進(jìn)行事務(wù)管理,下面通過(guò)一個(gè)實(shí)例描述底層API的事務(wù)管理實(shí)現(xiàn):

          1. 給數(shù)據(jù)源配置事務(wù)管理器


          "txManager"?class="org.springframework.jdbc.datasource.DataSourceTransactionManager">
          ????"dataSource"?ref="dataSource"/>



          1. 創(chuàng)建數(shù)據(jù)訪問(wèn)類(lèi)

          package?com.ch5.dao.Impl;
          ?
          import?org.springframework.beans.factory.annotation.Autowired;
          import?org.springframework.jdbc.core.JdbcTemplate;
          import?org.springframework.jdbc.datasource.DataSourceTransactionManager;
          import?org.springframework.stereotype.Repository;
          import?org.springframework.transaction.TransactionDefinition;
          import?org.springframework.transaction.TransactionStatus;
          import?org.springframework.transaction.support.DefaultTransactionDefinition;
          ?
          @Repository("codeTransaction")
          public?class?CodeTransaction?{
          ????@Autowired
          ????private?JdbcTemplate?jdbcTemplate;
          ????@Autowired
          ????private?DataSourceTransactionManager?transactionManager;
          ????public?String?testTransaction(){
          ????????//默認(rèn)事務(wù)定義
          ????????TransactionDefinition?definition=new?DefaultTransactionDefinition();
          ????????//開(kāi)啟事務(wù)
          ????????TransactionStatus?transactionStatus?=?transactionManager.getTransaction(definition);
          ????????String?message="執(zhí)行成功,沒(méi)有回滾";
          ????????try{
          ????????????String?sql?=?"delete?*?from?account";
          ????????????String?insertSql?=?"insert?into?account?values(?,?,?)";
          ????????????Object?param[]?=?{"1","chenheng",2000};
          ????????????jdbcTemplate.update(sql);
          ????????????//id重復(fù),因此發(fā)生錯(cuò)誤。
          ????????????jdbcTemplate.update(insertSql,param);
          ????????????jdbcTemplate.update(insertSql,param);
          ????????????//提交事務(wù)
          ????????????transactionManager.commit(transactionStatus);
          ????????}catch?(Exception?e){
          ????????????//出現(xiàn)異常,回滾
          ????????????transactionManager.rollback(transactionStatus);
          ????????????message="事務(wù)回滾";
          ????????????e.printStackTrace();
          ????????}
          ????????return?message;
          ????}
          }

          1. 定義測(cè)試類(lèi)

          package?com.ch5.Test;
          ?
          import?com.ch5.dao.Impl.CodeTransaction;
          import?org.springframework.context.ApplicationContext;
          import?org.springframework.context.support.ClassPathXmlApplicationContext;
          ?
          public?class?TransactionMangagerTest?{
          ????public?static?void?main(String[]?args)?{
          ????????ApplicationContext?appCo=new?ClassPathXmlApplicationContext("appliationContext.xml");
          ????????CodeTransaction?codeTransaction?=?(CodeTransaction)appCo.getBean("codeTransaction");
          ????????String?result?=?codeTransaction.testTransaction();
          ????????System.out.println(result);
          ????}
          }

          基于TransactionTemplate的編程式事務(wù)管理

          事務(wù)處理的代碼散落在業(yè)務(wù)邏輯代碼中,破壞了原有代碼的條理性,并且每一個(gè)事務(wù)都會(huì)有類(lèi)似的啟動(dòng)事務(wù),提交以及回滾事務(wù)的代碼。

          TransactionTemplateexcute方法有一個(gè)TransactionCallback接口類(lèi)型的參數(shù),該接口定義了一個(gè)DoInTransaction的方法,通常以匿名內(nèi)部類(lèi)的方式實(shí)現(xiàn)TransactionCallback接口,并在其doInTransaction方法中寫(xiě)業(yè)務(wù)邏輯代碼。在這里可以使用默認(rèn)的事務(wù)提交和回滾規(guī)則,在業(yè)務(wù)代碼中不需要顯式調(diào)用任何事務(wù)處理的API,doInTransaction方法有一個(gè)TransactionStatus類(lèi)型的參數(shù),可以在方法的任何位置調(diào)用該參數(shù)的setRollbackOnly方法將事務(wù)標(biāo)識(shí)為回滾,以執(zhí)行事務(wù)回滾。

          根據(jù)默認(rèn)規(guī)則,如果在執(zhí)行回調(diào)方法的過(guò)程中拋出未檢查異常,或者顯式調(diào)用了setRollbackOnly方法,則回滾事務(wù);如果事務(wù)執(zhí)行完成或者拋出了checked類(lèi)型的異常,則提交事務(wù)。

          基于TransactionTemplate的編程式事務(wù)管理的步驟如下:

          1. 為事務(wù)管理添加事務(wù)模板:在基于底層的API開(kāi)發(fā)的applicationContext.xml配置文件上使用springframwork提供的org,springframework,transaction.support.TransactionTemplate類(lèi)為事務(wù)管理器添加事務(wù)模板。完整的配置文件如下:

          "1.0"?encoding="UTF-8"?>
          "http://www.springframework.org/schema/beans"
          ???????xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
          ???????xmlns:aop="http://www.springframework.org/schema/aop"
          ???????xmlns:context="http://www.springframework.org/schema/context"
          ???????xsi:schemaLocation="http://www.springframework.org/schema/beans
          ????????http://www.springframework.org/schema/beans/spring-beans.xsd
          ????????http://www.springframework.org/schema/aop
          ????????http://www.springframework.org/schema/aop/spring-aop.xsd
          ????????http://www.springframework.org/schema/context
          ????????http://www.springframework.org/schema/context/spring-context.xsd"
          >
          ????
          ????"com.ch5"/>
          ????
          ????"dataSource"?class="org.springframework.jdbc.datasource.DriverManagerDataSource">
          ????????
          ????????"driverClassName"?value="com.mysql.jdbc.Driver"/>
          ????????
          ????????"url"?value="jdbc:mysql://localhost:3306/spring?characterEncoding=utf-8"/>
          ????????
          ????????"username"?value="root"/>
          ????????"password"?value="root"/>
          ????
          ????
          ????"txManager"?class="org.springframework.jdbc.datasource.DataSourceTransactionManager">
          ????????"dataSource"?ref="dataSource"/>
          ????
          ????
          ????"transactionTemplate"?class="org.springframework.transaction.support.TransactionTemplate">
          ????????"transactionManager"?ref="txManager"/>
          ????
          ????
          ????"jdbcTemplate"?class="org.springframework.jdbc.core.JdbcTemplate">
          ????????"dataSource"?ref="dataSource"/>
          ????


          1. 創(chuàng)建數(shù)據(jù)訪問(wèn)類(lèi)TransactionTemplateDao

          package?com.ch5;
          import?org.springframework.beans.factory.annotation.Autowired;
          import?org.springframework.jdbc.core.JdbcTemplate;
          import?org.springframework.stereotype.Repository;
          import?org.springframework.transaction.TransactionStatus;
          import?org.springframework.transaction.support.TransactionCallback;
          import?org.springframework.transaction.support.TransactionTemplate;
          @Repository("transactionTemplateDao")
          public?class?TransactionTemplateDao?{
          ????@Autowired
          ????private?JdbcTemplate?jdbcTemplate;
          ????@Autowired
          ????private?TransactionTemplate?transactionTemplate;
          ????String?message?=?"";
          ????public?String?TransactionTemplateTest(){
          ????????//以你命好內(nèi)部類(lèi)的方式實(shí)現(xiàn)TransactionCallback接口。使用默認(rèn)的事務(wù)規(guī)則。
          ????????transactionTemplate.execute(new?TransactionCallback()?{
          ????????????@Override
          ????????????public?Object?doInTransaction(TransactionStatus?status)?{
          ????????????????String?insertSql?=?"insert?into?account?values(?,?,?)";
          ????????????????Object?param[]?=?{9,"chen",5000.0};
          ????????????????try{
          ????????????????????jdbcTemplate.update(insertSql,param);
          ????????????????????jdbcTemplate.update(insertSql,param);
          ????????????????????message="執(zhí)行成功,未回滾";
          ????????????????}catch?(Exception?e){
          ????????????????????message="事務(wù)回滾";
          ????????????????}
          ????????????????return?message;
          ????????????}
          ????????});
          ????????return?message;
          ????}
          }

          1. 創(chuàng)建測(cè)試類(lèi)TransactionTemplateDaoTest

          package?com.ch5.Test;
          ?
          import?com.ch5.TransactionTemplateDao;
          import?com.ch5.dao.Impl.CodeTransaction;
          import?org.springframework.context.ApplicationContext;
          import?org.springframework.context.support.ClassPathXmlApplicationContext;
          ?
          public?class?TransactionTemplateDaoTest?{
          ????public?static?void?main(String[]?args)?{
          ????????ApplicationContext?appCo=new?ClassPathXmlApplicationContext("appliationContext.xml");
          ????????TransactionTemplateDao?transactionTemplateDao?=?appCo.getBean("transactionTemplateDao",?TransactionTemplateDao.class);
          ????????String?result?=?transactionTemplateDao.TransactionTemplateTest();
          ????????System.out.println(result);
          ????}
          }

          聲明式事務(wù)管理

          Spring的聲明式事務(wù)管理是通過(guò)AOP技術(shù)實(shí)現(xiàn)的事務(wù)管理,其本質(zhì)是對(duì)方法前后攔截,然后再目標(biāo)方法開(kāi)始之前創(chuàng)建一個(gè)事務(wù),在執(zhí)行完成后提交或回滾事務(wù)。

          與編程式事務(wù)管理相比較,聲明式事務(wù)唯一不足的地方是最細(xì)粒度只能作用到方法級(jí)別,無(wú)法做到像編程式事務(wù)管理那樣可以作用到代碼塊級(jí)別,但即便有這樣的需要,可以通過(guò)變通方法進(jìn)行解決。例如可以將要進(jìn)行事務(wù)處理的代碼塊單獨(dú)封裝為方法。

          Spring聲明式事務(wù)管理可以通過(guò)兩種方式實(shí)現(xiàn),一是基于XML方式,二是基于@Transactional注解的方式

          基于XML方式的聲明式事務(wù)管理

          基于XML方式的聲明式事務(wù)管理是通過(guò)在配置文件中配置事務(wù)規(guī)則的相關(guān)聲明來(lái)實(shí)現(xiàn)的。Spring提供了tx命名空間來(lái)配置事務(wù)管理,提供了元素來(lái)配置事務(wù)的通知,在配置時(shí)一般要指定id和transaction-manager屬性,其中id是配置文件的唯一標(biāo)識(shí)。transaction-manager指定了事務(wù)管理器。另外還需要配置子元素,該子元素可配置多個(gè)子元素決定執(zhí)行事務(wù)的細(xì)節(jié)。

          元素配置了事務(wù)的增強(qiáng)處理后就可以通過(guò)編寫(xiě)AOP配置讓Spring自動(dòng)對(duì)目標(biāo)對(duì)象生成代理,下面通過(guò)實(shí)例演示XML方式讓Spring實(shí)現(xiàn)聲明式事務(wù)管理。為了體現(xiàn)事務(wù)管理的流程,創(chuàng)建Dao、Service、Controller3層實(shí)現(xiàn)。

          1. 創(chuàng)建Dao接口和實(shí)現(xiàn)類(lèi)

          package?statment.dao;
          ?
          public?interface?TestDao?{
          ????public?int?save(String?sql,Object?param[]);
          ????public?int?delete(String?sql,Object?param[]);
          }


          package?statment.dao.Impl;
          ?
          import?org.springframework.beans.factory.annotation.Autowired;
          import?org.springframework.jdbc.core.JdbcTemplate;
          import?org.springframework.stereotype.Repository;
          import?statment.dao.TestDao;
          @Repository("testDao")
          public?class?TestDaoImpl?implements?TestDao?{
          ????@Autowired
          ????private?JdbcTemplate?jdbcTemplate;
          ????public?int?save(String?sql,?Object[]?param)?{
          ????????return?jdbcTemplate.update(sql,param);
          ????}
          ?
          ????public?int?delete(String?sql,?Object[]?param)?{
          ????????return?jdbcTemplate.update(sql,param);
          ????}
          }

          1. 創(chuàng)建Service接口和實(shí)現(xiàn)類(lèi)

          package?statment.Service;
          ?
          public?interface?TestService?{
          ????public?void?test();
          }

          package?statment.Service.Impl;
          ?
          import?org.springframework.beans.factory.annotation.Autowired;
          import?org.springframework.stereotype.Service;
          import?statment.Service.TestService;
          import?statment.dao.TestDao;
          @Service("testService")
          public?class?TestServiceImpl?implements?TestService?{
          ????@Autowired
          ????private?TestDao?testDao;
          ?
          ????public?void?test()?{
          ????????String?deleteSql="delete?from?account";
          ????????String?saveSql="insert?into?account?values(?,?,?)";
          ????????Object?param[]?=?{1,"shitji",5000};
          ????????testDao.delete(deleteSql,null);
          ????????testDao.save(saveSql,param);
          ????}
          }

          1. 創(chuàng)建Controller類(lèi)

          package?statment.controller;
          ?
          import?org.springframework.beans.factory.annotation.Autowired;
          import?org.springframework.stereotype.Controller;
          import?statment.Service.TestService;
          @Controller
          public?class?StatementController?{
          ????@Autowired
          ????private?TestService?testService;
          ????public?void?test(){
          ????????testService.test();
          ????}
          }

          1. 編寫(xiě)配置文件bean.xml

          "1.0"?encoding="UTF-8"?>
          "http://www.springframework.org/schema/beans"
          ???????xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
          ???????xmlns:aop="http://www.springframework.org/schema/aop"
          ???????xmlns:tx="http://www.springframework.org/schema/tx"
          ???????xmlns:context="http://www.springframework.org/schema/context"
          ???????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"
          >
          ????"statment"/>
          ????"dataSource"?class="org.springframework.jdbc.datasource.DriverManagerDataSource">
          ????????"driverClassName"?value="com.mysql.jdbc.Driver"/>
          ????????"url"?value="jdbc:mysql://localhost:3306/spring"/>
          ????????"username"?value="root"/>
          ????????"password"?value="root"/>
          ????
          ????"jdbcTemplate"?class="org.springframework.jdbc.core.JdbcTemplate">
          ????????"dataSource"?ref="dataSource"/>
          ????
          ????"txManager"?class="org.springframework.jdbc.datasource.DataSourceTransactionManager">
          ????????"dataSource"?ref="dataSource"/>
          ????
          ????"myAdvice"?transaction-manager="txManager">
          ????????
          ????????????"*"/>
          ????????

          ????
          ????
          ????????"txPonintCut"?expression="execution(*?statment.Service.*.*(..))"/>
          ????????"myAdvice"?pointcut-ref="txPonintCut"/>
          ????



          1. 編寫(xiě)測(cè)試類(lèi)

          package?statment.Test;
          ?
          import?org.springframework.context.ApplicationContext;
          import?org.springframework.context.support.ClassPathXmlApplicationContext;
          import?statment.controller.StatementController;
          public?class?XMLTest?{
          ????public?static?void?main(String[]?args)?{
          ????????ApplicationContext?appCo=new?ClassPathXmlApplicationContext("bean.xml");
          ????????StatementController?controller?=?appCo.getBean("statementController",?StatementController.class);
          ????????controller.test();
          ????}
          }

          基于注解的聲明式事務(wù)管理

          package?statment.Service.Impl;
          ?
          import?org.springframework.beans.factory.annotation.Autowired;
          import?org.springframework.stereotype.Service;
          import?org.springframework.transaction.annotation.Transactional;
          import?statment.Service.TestService;
          import?statment.dao.TestDao;
          @Service("testService")
          @Transactional
          public?class?TestServiceImpl?implements?TestService?{
          ????@Autowired
          ????private?TestDao?testDao;
          ?
          ????public?void?test()?{
          ????????String?deleteSql="delete?from?account";
          ????????String?saveSql="insert?into?account?values(?,?,?)";
          ????????Object?param[]?=?{1,"shitji",5000};
          ????????testDao.delete(deleteSql,null);
          ????????testDao.save(saveSql,param);
          ????}
          }

          加入@Transactional,就可以指定這個(gè)類(lèi)需要受到Spring的事務(wù)管理,注意該注解只針對(duì)public修飾的方法添加。

          在事務(wù)處理中捕獲異常

          聲明式事務(wù)處理的流程是:

          1. Spring根據(jù)配置完成事務(wù)定義,設(shè)置事務(wù)屬性。

          2. 執(zhí)行開(kāi)發(fā)者的代碼邏輯。

          3. 如果開(kāi)發(fā)者的代碼產(chǎn)生異常并且滿足事務(wù)回滾的配置條件,則事務(wù)回滾,否則提交事務(wù)。

          4. 事務(wù)資源釋放。

          如果開(kāi)發(fā)者在代碼邏輯中加入try...catch語(yǔ)句,Spring不能在聲明式事務(wù)處理中正常執(zhí)行事務(wù)的回滾。原因是Spring只在發(fā)生未被捕獲的RuntimeException時(shí)才會(huì)回滾事務(wù)。因此需要處理這種問(wèn)題。

          基于XML方式的聲明式事務(wù)管理中捕獲異常

          在基于XML方式的聲明式事務(wù)管理捕獲異常,需要補(bǔ)充兩個(gè)步驟:

          1. 修改聲明事務(wù)的配置


          <tx:method name="*" rollback-for="java.lang.Exception"/>
          1. 在catch語(yǔ)句中添加throw new RuntimeException();

          基于注解方式的聲明式事務(wù)管理中捕獲異常

          1. 修改注解內(nèi)容,添加rollbackFor屬性


          @Transactional(rollbackFor = {Exception.class})
          1. 在catch語(yǔ)句中添加throw new RuntimeException();





          粉絲福利:Java從入門(mén)到入土學(xué)習(xí)路線圖

          ??????

          ??長(zhǎng)按上方微信二維碼?2 秒


          感謝點(diǎn)贊支持下哈?


          瀏覽 31
          點(diǎn)贊
          評(píng)論
          收藏
          分享

          手機(jī)掃一掃分享

          分享
          舉報(bào)
          評(píng)論
          圖片
          表情
          推薦
          點(diǎn)贊
          評(píng)論
          收藏
          分享

          手機(jī)掃一掃分享

          分享
          舉報(bào)
          <kbd id="afajh"><form id="afajh"></form></kbd>
          <strong id="afajh"><dl id="afajh"></dl></strong>
            <del id="afajh"><form id="afajh"></form></del>
                1. <th id="afajh"><progress id="afajh"></progress></th>
                  <b id="afajh"><abbr id="afajh"></abbr></b>
                    <th id="afajh"><progress id="afajh"></progress></th>
                    西西4444www无码大胆 | 亚洲天堂色在线 | 在线 色 综合午夜 | 天天撸视频在线 | 久久夜色国产精品 |