事务 订阅
事务(Transaction),一般是指要做的或所做的事情。在计算机术语中是指访问并可能更新数据库中各种数据项的一个程序执行单元(unit)。事务通常由高级数据库操纵语言或编程语言(如SQL,C++或Java)书写的用户程序的执行所引起,并用形如begin transaction和end transaction语句(或函数调用)来界定。事务由事务开始(begin transaction)和事务结束(end transaction)之间执行的全体操作组成。 展开全文
事务(Transaction),一般是指要做的或所做的事情。在计算机术语中是指访问并可能更新数据库中各种数据项的一个程序执行单元(unit)。事务通常由高级数据库操纵语言或编程语言(如SQL,C++或Java)书写的用户程序的执行所引起,并用形如begin transaction和end transaction语句(或函数调用)来界定。事务由事务开始(begin transaction)和事务结束(end transaction)之间执行的全体操作组成。
信息
特    性
事务是恢复和并发控制的基本单位
外文名
Transaction
中文名
事务
解    释
指要做的或所做的事情
事务计算机中的事务
例如:在关系数据库中,一个事务可以是一条SQL语句,一组SQL语句或整个程序。事务是恢复和并发控制的基本单位。事务应该具有4个属性:原子性、一致性、隔离性、持久性。这四个属性通常称为ACID特性。原子性(atomicity)。一个事务是一个不可分割的工作单位,事务中包括的操作要么都做,要么都不做。一致性(consistency)。事务必须是使数据库从一个一致性状态变到另一个一致性状态。一致性与原子性是密切相关的。隔离性(isolation)。一个事务的执行不能被其他事务干扰。即一个事务内部的操作及使用的数据对并发的其他事务是隔离的,并发执行的各个事务之间不能互相干扰。持久性(durability)。持久性也称永久性(permanence),指一个事务一旦提交,它对数据库中数据的改变就应该是永久性的。接下来的其他操作或故障不应该对其有任何影响。
收起全文
精华内容
参与话题
问答
  • 事务

    千次阅读 2019-03-23 17:13:47
    Java事务的类型有三种:JDBC事务、JTA(Java Transaction API)事务、容器事务 1、JDBC事务 JDBC 事务是用 Connection 对象控制的。JDBC Connection 接口( java.sql.Connection )提供了两种事务模式:自动提交和手工...

    事务的三种类型

    Java事务的类型有三种:JDBC事务、JTA(Java Transaction API)事务、容器事务

    1、JDBC事务

    JDBC 事务是用 Connection 对象控制的。JDBC Connection 接口( java.sql.Connection )提供了两种事务模式:自动提交和手工提交。 java.sql.Connection 提供了以下控制事务的方法:

    public void setAutoCommit(boolean)
    public boolean getAutoCommit()
    public void commit()
    public void rollback()
    

    使用 JDBC 事务界定时,您可以将多个 SQL 语句结合到一个事务中。JDBC 事务的一个缺点是事务的范围局限于一个数据库连接。一个 JDBC 事务不能跨越多个数据库。

    2.JTA(Java Transaction API)事务

    JTA是一种高层的,与实现无关的,与协议无关的API,应用程序和应用服务器可以使用JTA来访问事务。

    JTA允许应用程序执行分布式事务处理–在两个或多个网络计算机资源上访问并且更新数据,这些数据可以分布在多个数据库上。JDBC驱动程序的JTA支持极大地增强了数据访问能力。

    如果计划用 JTA 界定事务,那么就需要有一个实现 javax.sql.XADataSource 、 javax.sql.XAConnection 和 javax.sql.XAResource 接口的 JDBC 驱动程序。一个实现了这些接口的驱动程序将可以参与 JTA 事务。一个 XADataSource 对象就是一个 XAConnection 对象的工厂。 XAConnection s 是参与 JTA 事务的 JDBC 连接。

    您将需要用应用服务器的管理工具设置 XADataSource 。从应用服务器和 JDBC 驱动程序的文档中可以了解到相关的指导。

    J2EE 应用程序用 JNDI 查询数据源。一旦应用程序找到了数据源对象,它就调用 javax.sql.DataSource.getConnection() 以获得到数据库的连接。

    XA 连接与非 XA 连接不同。一定要记住 XA 连接参与了 JTA 事务。这意味着 XA 连接不支持 JDBC 的自动提交功能。同时,应用程序一定不要对 XA 连接调用 java.sql.Connection.commit() 或者 java.sql.Connection.rollback() 。相反,应用程序应该使用 UserTransaction.begin()、 UserTransaction.commit() 和 serTransaction.rollback() 。

    3、容器事务

    容器事务主要是J2EE应用服务器提供的,容器事务大多是基于JTA完成,这是一个基于JNDI的,相当复杂的API实现。相对编码实现JTA事务管理,我们可以通过EJB容器提供的容器事务管理机制(CMT)完成同一个功能,这项功能由J2EE应用服务器提供。这使得我们可以简单的指定将哪个方法加入事务,一旦指定,容器将负责事务管理任务。这是我们土建的解决方式,因为通过这种方式我们可以将事务代码排除在逻辑编码之外,同时将所有困难交给 J2EE容器去解决。使用EJB CMT的另外一个好处就是程序员无需关心JTA API的编码,不过,理论上我们必须使用EJB。

    三种事务差异:

    1、JDBC事务控制的局限性在一个数据库连接内,但是其使用简单。
    2、JTA事务的功能强大,事务可以跨越多个数据库或多个DAO,使用也比较复杂。
    3、容器事务,主要指的是J2EE应用服务器提供的事务管理,局限于EJB应用使用。

    总结:

    事务控制是构建J2EE应用不可缺少的一部分,合理选择应用何种事务对整个应用系统来说至关重要。一般说来,在单个JDBC 连接连接的情况下可以选择JDBC事务,在跨多个连接或者数据库情况下,需要选择使用JTA事务,如果用到了EJB,则可以考虑使用EJB容器事务。

    参考:https://www.cnblogs.com/baizhanshi/p/5159332.html

    举例:Spring容器事务:

    Spring事务管理的实现有许多细节,如果对整个接口框架有个大体了解会非常有利于我们理解事务,下面通过讲解Spring的事务接口来了解Spring实现事务的具体策略。

    Spring事务管理涉及的接口及其联系:
    在这里插入图片描述
    Spring并不直接管理事务,而是提供了多种事务管理器,他们将事务管理的职责委托给Hibernate或者JTA等持久化机制所提供的相关平台框架的事务来实现。 Spring事务管理器的接口是org.springframework.transaction.PlatformTransactionManager,通过这个接口,Spring为各个平台如JDBC、Hibernate等都提供了对应的事务管理器,但是具体的实现就是各个平台自己的事情了

    Public interface PlatformTransactionManager{  
           // 由TransactionDefinition得到TransactionStatus对象
           TransactionStatus getTransaction(TransactionDefinition definition) throws TransactionException;
        // 提交
           Void commit(TransactionStatus status) throws TransactionException;  
           // 回滚
           Void rollback(TransactionStatus status) throws TransactionException;  
    }
    

    1)、Spring JDBC事务

    如果应用程序中直接使用JDBC来进行持久化,DataSourceTransactionManager会为你处理事务边界。为了使用 DataSourceTransactionManager,你需要使用如下的XML将其装配到应用程序的上下文定义中

    <bean id="transactionManager" class="org.springframework.jdbc.datasource.DataSourceTransactionManager">
         <property name="dataSource" ref="dataSource" />
    </bean>
    

    实际上,DataSourceTransactionManager是通过调用java.sql.Connection来管理事务。通过调用连接的commit()方法来提交事务,同样,事务失败则通过调用rollback()方法进行回滚

    2)、Hibernate事务

    如果应用程序的持久化是通过Hibernate实现的,那么你需要使用HibernateTransactionManager。对于Hibernate3,需要在Spring上下文定义中添加如下的<bean>声明

    <bean id="transactionManager" class="org.springframework.orm.hibernate3.HibernateTransactionManager">
         <property name="sessionFactory" ref="sessionFactory" />
    </bean>
    

    sessionFactory属性需要装配一个Hibernate的session工厂,HibernateTransactionManager的实现细节是它将事务管理的职责委托给org.hibernate.Transaction对象,而后者是从Hibernate Session中获取到的。当事务成功完成时,HibernateTransactionManager将会调用Transaction对象的commit()方法,反之,将会调用rollback()方法。

    3)、Java持久化API事务(JPA)
    Hibernate多年来一直是事实上的Java持久化标准,但是现在Java持久化API作为真正的Java持久化标准进入大家的视野。如果你计划使用JPA的话,那你需要使用Spring的JpaTransactionManager来处理事务。你需要在Spring中这样配置JpaTransactionManager:

    <bean id="transactionManager" class="org.springframework.orm.jpa.JpaTransactionManager">
         <property name="sessionFactory" ref="sessionFactory" />
    </bean>
    

    JpaTransactionManager只需要装配一个JPA实体管理工厂(javax.persistence.EntityManagerFactory接口的任意实现)。JpaTransactionManager将与由工厂所产生的JPA EntityManager合作来构建事务

    事务管理器接口PlatformTransactionManager通过getTransaction(TransactionDefinition definition)方法来得到事务,这个方法里面的参数是TransactionDefinition类,这个类就定义了一些基本的事务属性。

    事务属性可以理解成事务的一些基本配置,描述了事务策略如何应用到方法上。

    事务属性包含了5个方面:

    传播行为、隔离规则、回滚规则、事务超时、是否只读

    public interface TransactionDefinition {
        int getPropagationBehavior(); // 返回事务的传播行为
        int getIsolationLevel(); // 返回事务的隔离级别,事务管理器根据它来控制另外一个事务可以看到本事务内的哪些数据
        int getTimeout();  // 返回事务必须在多少秒内完成
        boolean isReadOnly(); // 事务是否只读,事务管理器能够根据这个返回值进行优化,确保事务是只读的
    }
    

    参考 https://blog.csdn.net/weixin_37934748/article/details/82774230

    与事务相关的理论

    1.事务(Transaction)的四个属性(ACID)

    原子性(Atomic) 对数据的修改要么全部执行,要么全部不执行。
    一致性(Consistent) 在事务执行前后,数据状态保持一致性。
    隔离性(Isolated) 一个事务的处理不能影响另一个事务的处理。
    持续性(Durable) 事务处理结束,其效果在数据库中持久化

    2.事务并发处理可能引起的问题

    脏读(dirty read):一个事务读取了另一个事务尚未提交的数据,
    不可重复读(non-repeatable read) :一个事务的操作导致另一个事务前后两次读取到不同的数据
    幻读(phantom read) :一个事务的操作导致另一个事务前后两次查询的结果数据量不同。

    3.事务并发处理可能引起的问题

    脏读(dirty read):一个事务读取了另一个事务尚未提交的数据,
    不可重复读(non-repeatable read) :一个事务的操作导致另一个事务前后两次读取到不同的数据
    幻读(phantom read) :一个事务的操作导致另一个事务前后两次查询的结果数据量不同。

    4. 事务隔离级别(Transaction Isolation Levels)

    JDBC提供了5种不同的事务隔离级别,在Connection中进行了定义。
    JDBC定义了五种事务隔离级别

    ISOLATION_DEFAULT 这是一个PlatfromTransactionManager默认的隔离级别,使用数据库默认的事务隔离级别.
    ISOLATION_READ_UNCOMMITTED 允许脏读、不可重复读和幻读
    ISOLATION_READ_COMMITTED 禁止脏读,但允许不可重复读和幻读
    ISOLATION_REPEATABLE_READ 禁止脏读和不可重复读,但允许幻读
    ISOLATION_SERIALIZABLE 禁止脏读、不可重复读和幻读

    5.事务的传播行为

    7种传播行为

    PROPAGATION_REQUIRED 如果当前没有事务,就新建一个事务,如果已经存在一个事务中,加入到这个事务中。这是最常见的选择。
    PROPAGATION_SUPPORTS 支持当前事务,如果当前没有事务,就以非事务方式执行
    PROPAGATION_MANDATORY 支持当前事务,如果当前没有事务,就抛出异常。
    PROPAGATION_REQUIRES_NEW 新建事务,如果当前存在事务,把当前事务挂起
    PROPAGATION_NOT_SUPPORTED 以非事务方式执行操作,如果当前存在事务,就把当前事务挂起
    PROPAGATION_NEVER 以非事务方式执行,如果当前存在事务,则抛出异常

    虽然有7种,但是常用的就第一种REQUIRED和第四种REQUIRES_NEW

    6.保存点(SavePoint)

    JDBC定义了SavePoint接口,提供在一个更细粒度的事务控制机制。当设置了一个保存点后,可以rollback到该保存点处的状态,而不是rollback整个事务。

    Connection接口的setSavepoint和releaseSavepoint方法可以设置和释放保存点。
    JDBC规范虽然定义了事务的以上支持行为,但是各个JDBC驱动,数据库厂商对事务的支持程度可能各不相同。如果在程序中任意设置,可能得不到想要的效果。为此,JDBC提供了DatabaseMetaData接口,提供了一系列JDBC特性支持情况的获取方法。比如,通过DatabaseMetaData.supportsTransactionIsolationLevel方法可以判断对事务隔离级别的支持情况,通过DatabaseMetaData.supportsSavepoints方法可以判断对保存点的支持情况。
    参考 https://blog.csdn.net/weixin_40263776/article/details/79521595

    事务的属性可同时通过注解方式或配置文件配置

    注解方式:

    @Transactional只能被应用到public方法上(aop方式实现的),对于其它非public的方法,如果标记@Transactional也不会报错,但方法没有事务功能.
    默认情况下,一个有事务方法, 遇到RuntimeException 时会回滚 . 遇到 受检查的异常 是不会回滚 的. 要想所有异常都回滚,要加上 @Transactional( rollbackFor={Exception.class,其它异常})

    @Transactional(
        readOnly = false, //读写事务
        timeout = -1 ,     //事务的超时时间,-1为无限制
        noRollbackFor = ArithmeticException.class, //遇到指定的异常不回滚
        isolation = Isolation.DEFAULT, //事务的隔离级别,此处使用后端数据库的默认隔离级别
        propagation = Propagation.REQUIRED //事务的传播行为
    )
    

    配置文件( aop拦截器方式):

    <tx:advice id="advice" transaction-manager="txManager">
              <tx:attributes>
                <!-- tx:method的属性:
                    * name 是必须的,表示与事务属性关联的方法名(业务方法名),对切入点进行细化。通配符 
                         (*)可以用来指定一批关联到相同的事务属性的方法。
                          如:'get*'、'handle*'、'on*Event'等等.
                    * propagation:不是必须的,默认值是REQUIRED表示事务传播行为,
                      包括REQUIRED,SUPPORTS,MANDATORY,REQUIRES_NEW,NOT_SUPPORTED,NEVER,NESTED
                    * isolation:不是必须的 默认值DEFAULT ,表示事务隔离级别(数据库的隔离级别)
                    * timeout:不是必须的 默认值-1(永不超时),表示事务超时的时间(以秒为单位)
                    * read-only:不是必须的 默认值false不是只读的表示事务是否只读?
                    * rollback-for: 不是必须的表示将被触发进行回滚的 Exception(s);以逗号分开。
                       如:'com.foo.MyBusinessException,ServletException'
                    * no-rollback-for:不是必须的表示不被触发进行回滚的 Exception(s),以逗号分开。                                        
                       如:'com.foo.MyBusinessException,ServletException'   
                    任何 RuntimeException 将触发事务回滚,但是任何 checked Exception 将不触发事务回滚                     
                -->
                 <tx:method name="save*" propagation="REQUIRED" isolation="DEFAULT" read-only="false"/>
                 <tx:method name="update*" propagation="REQUIRED" isolation="DEFAULT" read-only="false"/>
                 <tx:method name="delete*" propagation="REQUIRED" isolation="DEFAULT" read-only="false"  rollback-for="Exception"/>
                 <!-- 其他的方法之只读的 -->
                 <tx:method name="*" read-only="true"/>
              </tx:attributes>
    </tx:advice>
    

    注意:
    aop方式的是无法拦截私有方法的,因为aop底层是代理,

    jdk是代理接口,私有方法必然不会存在在接口里,所以就不会被拦截到;
    cglib是子类,private的方法照样不会出现在子类里,也不能被拦截

    参考 https://www.cnblogs.com/protected/p/6652188.html

    代码 https://github.com/baiyanlang2016/springboot-transaction

    展开全文
  • 事务模板接入(spring的编程式事务)

    万次阅读 多人点赞 2019-07-31 18:35:32
    事务模板接入 这里接入的是spring的编程式事务,代理一下spring的TransactionTemplate就可以了。 importorg.springframework.transaction.TransactionException; importorg.springframework.transaction....

    事务模板接入

    这里接入的是spring的编程式事务,代理一下spring的TransactionTemplate就可以了。

     

    import org.springframework.transaction.TransactionException;

    import org.springframework.transaction.support.TransactionCallback;

    import org.springframework.transaction.support.TransactionTemplate;

     

    /**

     * 事务模板

     *

     * @author jiacheng.yjc

     * @version $Id: TranscationTemplate.java, v 0.1 2015年11月18日 上午11:17:58 jiacheng.yjc Exp $

     */

    public class TrancTemplateImpl implements TrancTemplate {

     

        private TransactionTemplate transactionTemplate;

        //这个是为了一个事务不够的时候也不用再new一个,直接用这个就行

        private TransactionTemplate transactionNewTemplate;

     

        /**

         *

         * @see com.mybank.bkloanapply.core.service.component.tx.TrancTemplate#execute(org.springframework.transaction.support.TransactionCallback)

         */

        @Override

        public <T> T execute(TransactionCallback<T> actionthrows TransactionException {

            return transactionTemplate.execute(action);

        }

     

        /**

         *

         * @see com.mybank.bkloanapply.core.service.component.tx.TrancTemplate#executeReqNew(org.springframework.transaction.support.TransactionCallback)

         */

        @Override

        public <T> T executeReqNew(TransactionCallback<T> actionthrows TransactionException {

            return transactionNewTemplate.execute(action);

        }

     

        /**

         * Setter method for property <tt>transactionTemplate</tt>.

         *

         * @param transactionTemplate value to be assigned to property transactionTemplate

         */

        public void setTransactionTemplate(TransactionTemplate transactionTemplate) {

            this.transactionTemplate = transactionTemplate;

        }

     

        /**

         * Setter method for property <tt>transactionNewTemplate</tt>.

         *

         * @param transactionNewTemplate value to be assigned to property transactionNewTemplate

         */

        public void setTransactionNewTemplate(TransactionTemplate transactionNewTemplate) {

            this.transactionNewTemplate = transactionNewTemplate;

        }

    }

     

    模板的接入使用

    /**

         * 测试用例,插入一条日志记录

         *

         */

        @Override

        public String logTest(LogModel logModel) {

            final LogModel logModel_ = logModel;

            trancTemplate.execute(new TransactionCallback<LogModel>() {

                @Override

                public LogModel doInTransaction(TransactionStatus status) {

                    logComponent.insert(logModel_);

                    //do otherthings…

                    return logModel_;

                }

            });

            return "执行成功";

    }

    当insert语句执行出错或者do otherthings时出错都会自动回滚,不需要手动trycatch然后status.setRollbackOnly();回滚,很方便。

    展开全文
  • 事务的隔离级别

    万次阅读 多人点赞 2019-05-20 20:22:47
    事务的隔离级别 事务的四大特性分别是:原子性、一致性、隔离性、持久性 幻读和不可重复读都是在同一个事务中多次读取了其他事务已经提交的事务的数据导致每次读取的数据不一致,所不同的是不可重复读读取的是同一条...

    事务的隔离级别

    事务的四大特性分别是:原子性、一致性、隔离性、持久性

    幻读和不可重复读都是在同一个事务中多次读取了其他事务已经提交的事务的数据导致每次读取的数据不一致,所不同的是不可重复读读取的是同一条数据,而幻读针对的是一批数据整体的统计(比如数据的个数)

    以MYSQL数据库来分析四种隔离级别

    第一种隔离级别:Read uncommitted(读未提交)
    如果一个事务已经开始写数据,则另外一个事务不允许同时进行写操作,但允许其他事务读此行数据,该隔离级别可以通过“排他写锁”,但是不排斥读线程实现。这样就避免了更新丢失,却可能出现脏读,也就是说事务B读取到了事务A未提交的数据

    解决了更新丢失,但还是可能会出现脏读

    第二种隔离级别:Read committed(读提交)
    如果是一个读事务(线程),则允许其他事务读写,如果是写事务将会禁止其他事务访问该行数据,该隔离级别避免了脏读,但是可能出现不可重复读。事务A事先读取了数据,事务B紧接着更新了数据,并提交了事务,而事务A再次读取该数据时,数据已经发生了改变。

    解决了更新丢失和脏读问题

    第三种隔离级别:Repeatable read(可重复读取)
    可重复读取是指在一个事务内,多次读同一个数据,在这个事务还没结束时,其他事务不能访问该数据(包括了读写),这样就可以在同一个事务内两次读到的数据是一样的,因此称为是可重复读隔离级别,读取数据的事务将会禁止写事务(但允许读事务),写事务则禁止任何其他事务(包括了读写),这样避免了不可重复读和脏读,但是有时可能会出现幻读。(读取数据的事务)可以通过“共享读镜”和“排他写锁”实现。

    解决了更新丢失、脏读、不可重复读、但是还会出现幻读

    第四种隔离级别:Serializable(可序化)
    提供严格的事务隔离,它要求事务序列化执行,事务只能一个接着一个地执行,但不能并发执行,如果仅仅通过“行级锁”是无法实现序列化的,必须通过其他机制保证新插入的数据不会被执行查询操作的事务访问到。序列化是最高的事务隔离级别,同时代价也是最高的,性能很低,一般很少使用,在该级别下,事务顺序执行,不仅可以避免脏读、不可重复读,还避免了幻读

    解决了更新丢失、脏读、不可重复读、幻读(虚读)
    在这里插入图片描述
    以上四种隔离级别最高的是Serializable级别,最低的是Read uncommitted级别,当然级别越高,执行效率就越低,像Serializeble这样的级别,就是以锁表的方式(类似于Java多线程中的锁)使得其他线程只能在锁外等待,所以平时选用何种隔离级别应该根据实际情况来,在MYSQL数据库中默认的隔离级别是Repeatable read(可重复读)。

    在MYSQL数据库中,支持上面四种隔离级别,默认的为Repeatable read(可重复读);而在Oracle数据库中,只支持Serializeble(串行化)级别和Read committed(读已提交)这两种级别,其中默认的为Read committed级别

    在MYSQL数据库中查看当前事务的隔离级别

    SELECT @@tx_isolation;
    

    在MYSQL数据库中设置事务的隔离级别:
    在这里插入图片描述
    在这里插入图片描述
    在这里插入图片描述
    记住:设置数据库的隔离级别一定要是在开启事务之前:

    如果是使用JDBC对数据库的事务设置隔离级别的话,也应该是在调用Connecton对象的setAutoCommit(false)方法之前,调用Connection对象的setTransactionIsolation(level)即可设置当前连接的隔离级别,至于参数level,可以使用Connection对象的字段:
    在这里插入图片描述
    在JDBC中设置隔离级别的部分代码:
    在这里插入图片描述
    隔离级别的设置只对当前连接有效,对于使用MYSQL命令窗口而言,一个窗口就相当于一个连接,当前窗口设置的隔离级别只对当前窗口中的事务有效,对于JDBC操作数据库来说,一个Connection对象相当与一个连接,而对于Connection对象设置的隔离级别只对该Connection对象有效,与其他连接Connection对象无关

    展开全文
  • 在Spring AOP切面中启用新事务

    万次阅读 多人点赞 2019-07-31 19:16:01
    在工作中有一个在切面中需要记录一下操作日志的需求,而且要求这些操作日志要存入数据库,并且无论业务层有什么异常,日志照常记录,那就不能沿用业务层的事务,而是需要新启一个事务了。 sping的声明式事务就是靠...

    在工作中有一个在切面中需要记录一下操作日志的需求,而且要求这些操作日志要存入数据库,并且无论业务层有什么异常,日志照常记录,那就不能沿用业务层的事务,而是需要新启一个事务了。
    sping的声明式事务就是靠AOP来实现的,一般事务都在业务层中启用,那如果要在AOP的逻辑中启用一个新的事务要怎么做呢?比如下面的例子:

    //定义一个切点,这里指com.lidehang.remote包下所有的类的方法
    @Pointcut("execution(public * com.lidehang.remote..*.*(..))")
     public void remote(){}
    
    //切点指定的方法执行完返回后调用
    @AfterReturning(returning = "ret", pointcut = "remote()")
     public void doAfterReturning(JoinPoint joinPoint,Object ret) throws Throwable {
     	//一些切面逻辑,包含了数据库操作,为了即便业务层的原事务回滚也不会影响切面中的数据库操作,需要启用新的事务
    ...
     }
    

    经过我的测试,通过在doAfterReturning方法上加上注解@Transactional,并指定传播行为是REQUIRES_NEW依然不行。因为@Transactional也是声明式事务,本身就是AOP实现的,在AOP的代码中使用不起作用。所以就只能使用spring的编程式事务了,需要引入TransactionTemplate。如下:

    @Autowired
    private TransactionTemplate transactionTemplate;
    
    @AfterReturning(returning = "ret", pointcut = "remote()")
     public void doAfterReturning(JoinPoint joinPoint,Object ret) throws Throwable {
    //声明式事务在切面中不起作用,需使用编程式事务
    //设置传播行为:总是新启一个事务,如果存在原事务,就挂起原事务
    transactionTemplate.setPropagationBehavior(TransactionDefinition.PROPAGATION_REQUIRES_NEW);
    transactionTemplate.execute(new TransactionCallback<T>() {
    @Override
    		public T doInTransaction(TransactionStatus arg0) {
     			//一些切面逻辑,包含了数据库操作
    ...
    }
    });
     }
    

    通过以上的步骤,切面里的逻辑会在新事务中执行,执行完就会提交,和业务层中的原事务无关,即便执行完切面逻辑后继续执行业务代码的过程中出现异常,业务层中的数据库操作因为有原事务而回滚,但切面中的数据库操作不会回滚,因为这是个新的事务!

    展开全文
  • MySQL——事务(Transaction)详解

    万次阅读 多人点赞 2018-03-23 13:05:50
    该博客详解MySQL中的事务 一、事务定义 Transaction 事务:一个最小的不可再分的工作单元;通常一个事务对应一个完整的业务(例如银行账户转账业务,该业务就是一个最小的工作单元) 一个完整的业务需要批量的DML...
  • 分布式事务解决方案

    千次阅读 2018-10-12 19:35:33
    2.分布式事务场景 1. 跨库事务 2. 分库分表 3.服务化 3.两阶段提交 &amp; 三阶段提交 &amp; paxos CAP + BASE 4. 典型的柔性事务方案 5. 场景的分布式事务解决方案 1. 基于XA协议的两阶段提交 2. ...
  • 事务的隔离级别3.1 无隔离性的问题3.1.1 脏读3.1.2 不可重复读3.1.3 幻读3.2 事务的隔离级别3.2.1 设置事务的隔离级别3.2.2 查看当前的隔离级别4.事务的特性4.1 原子性4.2 一致性4.3 隔离性4.4 持久性 1.什么是事务...
  • 事务ACID理解

    万次阅读 多人点赞 2018-09-06 21:26:20
    事务管理(ACID) 谈到事务一般都是以下四点 原子性(Atomicity) 原子性是指事务是一个不可分割的工作单位,事务中的操作要么都发生,要么都不发生。 一致性(Consistency) 事务前后数据的完整性必须保持一致...
  • 太惨了,面试又被吊打
  • MySQL事务介绍

    万次阅读 2020-05-04 21:46:12
    ##数据库事务 ###含义 通过一组逻辑操作单元(一组DML——sql语句),将数据从一种状态切换到另外一种状态 ###特点 (ACID) 原子性:要么都执行,要么都回滚 一致性:保证数据的状态操作前和操作后保持一致 ...
  • Spring事务和MySQL事务详解面试

    万次阅读 2020-09-10 23:56:36
    文章目录数据库事务事务是什么事务的四大特性MySQL事务隔离级别查看MySQL当前事务隔离级别MySQL默认操作模式为自动提交模式JDBC处理事务Spring事务Spring的事务传播PROPAGATION_REQUIREDPROPAGATION_...
  • MongoDB4.0将支持多文档事务

    万次阅读 2020-07-30 13:55:21
    在早期,我们说的MongoDB支持事务是指针对MongoDB的单文档级别,与我们MySQL等关系型数据库中的事务是不同的,那什么是单文档事务呢? db.username.update({'name': 'helei'}, {$set: {'age': 26, 'score': 85}}) ...
  • 事务的四大特性

    万次阅读 2020-08-12 15:25:06
    数据库中事务的四大特性(ACID),以及事务的隔离级别。 如果一个数据库声称支持事务的操作,那么该数据库必须要具备以下四个特性: ⑴ 原子性(Atomicity) 原子性是指事务包含的所有操作要么全部成功,要么全部...
  • MySQL 事务

    万次阅读 2019-04-21 19:05:56
    MySQL 事务主要用于处理操作量大,复杂度高的数据。比如说,在人员管理系统中,你删除一个人员,你即需要删除人员的基本资料,也要删除和该人员相关的信息,如信箱,文章等等,这样,这些数据库操作语句就构成一个...
  • 事务 | Spring Cloud 分布式事务管理 LCN、GTX、ByteTCC

    万次阅读 多人点赞 2018-03-18 21:03:04
    事务 | Spring Cloud 分布式事务管理 LCN、GTX、ByteTCC 在微服务如火如荼的情况下,越来越多的项目开始尝试改造成微服务架构,微服务即带来了项目开发的方便性,又提高了运维难度以及网络不可靠的概率. Spring ...
  • Spring事务实现原理

    万次阅读 2020-09-10 09:39:51
    对于一个应用而言,事务的使用基本是不可避免的。虽然Spring给我们提供了开箱即用的事务功能——@Transactional。 但是,自带的事务功能却也存在控制粒度不够的缺点。更糟糕的是,@Transactional在某些情况下就失效...
  • 事务ACID理解复习

    万次阅读 2019-10-17 19:50:51
    谈到事务一般都是以下四点 原子性(Atomicity) 原子性是指事务是一个不可分割的工作单位,事务中的操作要么都发生,要么都不发生。 一致性(Consistency) 事务前后数据的完整性必须保持一致。 隔离性(Isolation...
  • Spring事务和MySQL事务详解

    万次阅读 2020-04-24 01:06:49
    文章目录数据库事务事务是什么事务的四大特性MySQL事务隔离级别查看MySQL当前事务隔离级别MySQL默认操作模式为自动提交模式JDBC处理事务Spring事务Spring的事务传播PROPAGATION_REQUIREDPROPAGATION_...
  • SpringBoot事务

    万次阅读 2019-07-13 18:33:49
    每一条语句处于一个单独的事务中,在这条语句执行完毕时,如果执行成功则隐式的提交事务,如果执行失败则隐式的回滚事务。对于正常的事务管理,是一组相关的操作处于一个事务之中,因此必须关闭数据库的自动提交模式...
  • 数据库事务

    万次阅读 2018-08-18 07:51:35
    数据库事务是数据库运行中的逻辑工作单位,单个逻辑工作单元所执行的一系列操作,要么都执行,要么都不执行。例如银行取款事务分为2个步骤(1)存折减款(2)提取现金,2个步骤必须同时完成或者都不完成。 数据库事务的...
  • RocketMQ事务消息实现分布式事务

    万次阅读 2020-05-12 15:11:01
    使用RocketMQ事务消息实现分布式事务
  • 分布式事务

    万次阅读 2020-09-05 10:24:23
    【1】分布式事务框架 【2】分布式事务 【3】tx-lcn 【1】分布式事务框架 TransactionsEssentials(atomikos免费版) tcc-transaction ByteTCC hmily tx-lcn GTS EasyTransaction 【2】分布式事务 1> TCC...
  • MySQL事务

    万次阅读 2020-06-23 09:53:05
    1、INNODB事务原理 事务(Transaction)是数据库区别于文件系统的重要特性之一,事务会把数据库从一种一致性状态转换为另一种一致性状态。 在数据库提交时,可以确保要么所有修改都已保存,要么所有修改都不保存。 ...
  • Spring事务

    万次阅读 2020-04-29 17:16:36
    Spring事务以及相关概念的介绍

空空如也

1 2 3 4 5 ... 20
收藏数 249,860
精华内容 99,944
关键字:

事务