Mybatis【2.3】-- Mybatis一定要使用commit才能成功修改數據么?


代碼直接放在Github倉庫【https://github.com/Damaer/Mybatis-Learning】,mybatis-02可直接運行,就不占篇幅了。

為什么我們有時候不使用commit也能修改數據庫成功?

1.從數據庫的層面上來講,其實這個主要看你用什么“存儲引擎”

像以下的代碼就是使用了自動提交的mysql引擎。

CREATE TABLE `student` ( `id` INT NOT NULL AUTO_INCREMENT , `name` VARCHAR(20) NOT NULL , 
`age` INT NOT NULL , `score` DOUBLE NOT NULL , PRIMARY KEY (`id`)) ENGINE = MyISAM; 

如果是不支持事務的引擎,如myisam,則是否commit都沒有效的。
如果是支持事務的引擎,如innodb,則有系統參數設置是否自動commit,查看參數如下:

mysql> show variables like '%autocommit%';
+---------------+-------+
| Variable_name | Value |
+---------------+-------+
| autocommit    | ON    |
+---------------+-------+
1 row in set (0.00 sec)
mysql>

顯示結果為on表示事務自動提交,不用手工去commit,當然,你可以設置其為OFF,然后自己手工去commit。

2.使用myIsam引擎,不需要commit

比如下面的代碼:

public class StudentDaoImpl implements IStudentDao {
    private SqlSession sqlSession;
	public void insertStu(Student student) {
		try {
			InputStream inputStream;
			inputStream = Resources.getResourceAsStream("mybatis.xml");
			SqlSessionFactory sqlSessionFactory=new SqlSessionFactoryBuilder().build(inputStream);
			sqlSession=sqlSessionFactory.openSession();
			sqlSession.insert("insertStudent",student);
		} catch (IOException e) {
			e.printStackTrace();
		}
	}
}

我們可以看到已經更新了一行,我們完全不使用commit

3.創建數據表(使用Innodb),也不提交,結果沒有插入

CREATE TABLE `student` ( `id` INT NOT NULL AUTO_INCREMENT , `name` VARCHAR(20) NOT NULL , 
`age` INT NOT NULL , `score` DOUBLE NOT NULL , PRIMARY KEY (`id`)) ENGINE = Innodb; 

我們再執行插入時,發現控制台輸出是這樣的:

好像輸入也成功了,但是我去數據庫看了一下,居然是空的:

那我們將代碼換成這樣,加入提交事務:

public class StudentDaoImpl implements IStudentDao {
    private SqlSession sqlSession;
	public void insertStu(Student student) {
		try {
			InputStream inputStream;
			inputStream = Resources.getResourceAsStream("mybatis.xml");
			SqlSessionFactory sqlSessionFactory=new SqlSessionFactoryBuilder().build(inputStream);
			sqlSession=sqlSessionFactory.openSession();
			sqlSession.insert("insertStudent",student);
			// 提交事務
			sqlSession.commit();
		} catch (IOException e) {
			e.printStackTrace();
		}finally {
		    if(sqlSession!=null){
		        sqlSession.close();
            }
        }
	}
}

執行代碼,我們會發現事務提交成功了,同時我們也關閉數據庫了:

打開數據庫,我們會發現,居然沒有id為1的記錄,為什么直接跳到2了呢?還記不記得之前插入一次但是沒有提交,所以問題就在這里。上一次的提交已經寫到事務里面了,只是沒有提交,所以這一次提交的時候,上一次默認已經占用了那條記錄,只是不寫進數據庫中。有提交就可以回滾,所以要使用回滾的話,可以使用sqlsession.rollback()

如果我們使用sqlsession.close()的話,我們就不需要使用回滾了。
下面是我把commit去掉,但是留下close的結果,我們可以看到沒有commit,但是已經會自動rollback了,所以只要使用sqlsession.close()就會自動回滾再關閉。

【作者簡介】
秦懷,公眾號【秦懷雜貨店】作者,技術之路不在一時,山高水長,縱使緩慢,馳而不息。這個世界希望一切都很快,更快,但是我希望自己能走好每一步,寫好每一篇文章,期待和你們一起交流。

此文章僅代表自己(本菜鳥)學習積累記錄,或者學習筆記,如有侵權,請聯系作者核實刪除。人無完人,文章也一樣,文筆稚嫩,在下不才,勿噴,如果有錯誤之處,還望指出,感激不盡~


免責聲明!

本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



 
粵ICP備18138465號   © 2018-2025 CODEPRJ.COM