spring事務(Transaction )報 marked as rollback-only異常的緣由及解決方法

不少朋友在使用spring+hibernate或mybatis等框架時常常遇到報Transaction rolled back because it has been marked as rollback-only的異常,這個異常是怎麼形成的java

呢,下面將給你們進行詳細的分析。mysql

    這是專門寫的一個形成該異常的代碼:spring

@Transactional
    public void add(OperateLog entity)throws Exception {
        // TODO Auto-generated method stub
        operateLogDao.add(entity);
    }
@Transactional
    public void save(Member member) throws Exception {
        memberDao.add(member);
    }
 
    @Transactional
    public void add(Member member) throws Exception {
        try {
            this.save(member);
            /*
             * 日誌的title長度爲10 我把值設置爲add111111111111111111是爲了形成異常
             */
            OperateLog entity = new OperateLog("add111111111111111111", "1111");
            operateLogService.add(entity);
        } catch (Exception e) {
            e.printStackTrace();
            // throw e;
        }
 
    }

執行以上代碼就會報改異常,當我把
//throw e;的註釋//去掉,當我執行後就不會有改異常,只會報標題title太長的異常。以下面提示:sql

Caused by: com.mysql.jdbc.MysqlDataTruncation: Data truncation: Data too long for column '_title' at row 1
    at com.mysql.jdbc.MysqlIO.checkErrorPacket(MysqlIO.java:4072)
    at com.mysql.jdbc.MysqlIO.checkErrorPacket(MysqlIO.java:4006)
    at com.mysql.jdbc.MysqlIO.sendCommand(MysqlIO.java:2468)
    at com.mysql.jdbc.MysqlIO.sqlQueryDirect(MysqlIO.java:2629)
    at com.mysql.jdbc.ConnectionImpl.execSQL(ConnectionImpl.java:2719)
    at com.mysql.jdbc.PreparedStatement.executeInternal(PreparedStatement.java:2155)
    at com.mysql.jdbc.PreparedStatement.executeUpdate(PreparedStatement.java:2450)
    at com.mysql.jdbc.PreparedStatement.executeUpdate(PreparedStatement.java:2371)
    at com.mysql.jdbc.PreparedStatement.executeUpdate(PreparedStatement.java:2355)
    at org.apache.commons.dbcp.DelegatingPreparedStatement.executeUpdate(DelegatingPreparedStatement.java:105)
    at org.apache.commons.dbcp.DelegatingPreparedStatement.executeUpdate(DelegatingPreparedStatement.java:105)
    at org.hibernate.id.IdentityGenerator$GetGeneratedKeysDelegate.executeAndExtract(IdentityGenerator.java:94)
    at org.hibernate.id.insert.AbstractReturningDelegate.performInsert(AbstractReturningDelegate.java:57)

做者:Mr_Smile2014
來源:CSDN
原文:https://blog.csdn.net/mr_smile2014/article/details/49455483
版權聲明:本文爲博主原創文章,轉載請附上博文連接!apache

經過以上的問題咱們能夠發現。在spring中,在事務方法中調用多個事務方法時,spring將會把這些事務合二爲一。當整個方法中每一個子方法沒報錯時,整個方法執行完才提交事務(你們能夠使用debug測試),若是某個子方法有異常,spring將該事務標誌爲rollback only。若是這個子方法沒有將異常往上整個方法拋出或整個方法未往上拋出,那麼改異常就不會觸發事務進行回滾,事務就會在整個方法執行完後就會提交,這時就會形成Transaction rolled back because it has been marked as rollback-only的異常,就如上面代碼中未拋throw e 同樣。若是咱們往上拋了改異常,spring就會獲取異常,並執行回滾。mybatis

相關文章
相關標籤/搜索