mysql开启事务没有提交(MySQL 事务autocommit自动提交操作)
mysql开启事务没有提交
MySQL 事务autocommit自动提交操作MySQL默认操作模式就是autocommit自动提交模式。这就表示除非显式地开始一个事务,否则每个查询都被当做一个单独的事务自动执行。我们可以通过设置autocommit的值改变是否是自动提交autocommit模式。
通过以下命令可以查看当前autocommit模式
|
mysql> show variables like 'autocommit' ; + ---------------+-------+ | Variable_name | Value | + ---------------+-------+ | autocommit | ON | + ---------------+-------+ 1 row in set (0.04 sec) |
从查询结果中,我们发现Value的值是ON,表示autocommit开启。我们可以通过以下SQL语句改变这个模式
|
mysql> set autocommit = 0; |
值0和OFF都是一样的,当然,1也就表示ON。通过以上设置autocommit=0,则用户将一直处于某个事务中,直到执行一条commit提交或rollback语句才会结束当前事务重新开始一个新的事务。
举个例子,张三给李四转账500元。那么在数据库中应该是以下操作:
1,先查询张三的账户余额是否足够
2,张三的账户上减去500元
3,李四的账户上加上500元
以上三个步骤就可以放在一个事务中执行提交,要么全部执行要么全部不执行,如果一切都OK就commit提交永久性更改数据;如果出错则rollback回滚到更改前的状态。利用事务处理就不会出现张三的钱少了李四的账户却没有增加500元或者张三的钱没有减去李四的账户却加了500元。
MySQL默认的存储引擎是MyISAM,MyISAM存储引擎不支持事务处理,所以改变autocommit没有什么作用。但不会报错,所以要使用事务处理的童鞋一定要确定你所操作的表示支持事务处理的,如InnoDB。如果不知道表的存储引擎可以通过查看建表语句查看建表的时候有没有指定事务类型的存储引擎,如果没有指定存储引擎默认则是MyISAM不支持事务的存储引擎。
当然,事务处理是为了保障表数据原子性、一致性、隔离性、持久性。
这些都是要消耗系统资源的,要谨慎选择。
补充:MySQL的事务处理(Transation)和自动执行(AutoCommit)与提交类型(Completion)
1、事务(transaction)
事务在计算机术语中是指访问并可能更新数据库中各种数据项的一个程序执行单元(unit)。事务主要用于处理操作量大,复杂度高的数据。如果你要删除一条主表信息,而主表有多个从表的时候,你需要有步骤地删除明细后再删除主表信息,这个过程极其容易出错,那么这个时候就是用事务才处理是最合适的了。
2、事务(Transcation)的用法
事务开始(start transaction or begin)
提交(commit)
回滚(rollback)
3、MYSQL支持的引擎(InnoDB)
|
show engines; |
4、自动执行(AutoCommit)与提交类型(Completion)
使用事务有两种方式,分别为隐式事务和显式事务。隐式事务实际上就是自动提交,Oracle 默认不自动提交,需要手写 COMMIT。在MySQL中,自动提交(autocommit)在支持事务(transaction)的引擎中,若autocommit=true,则不需要commit的情况下直接提交语句形成永久性修改,Mysql默认打开autocommit,也可以通过配置设置。
|
set autocommit=0;(AutoCommit Off ) set autocommit=1;(AutoCommit On ) set completion_type=0;( No Chain) set completion_type=1;(Chain) set completion_type=2;(Release) |
也可以通过语句查询当前配置
|
show variables like '%autocommit%' ; show variables like '%completion%' ; |
5、验证例子
|
mysql> BEGIN ; -> INSERT INTO test SELECT '关羽' ; -> COMMIT ; -> BEGIN ; -> INSERT INTO test SELECT '张飞' ; -> INSERT INTO test SELECT '张飞' ; -> ROLLBACK ; -> SELECT * FROM test; -> // Query OK, 0 rows affected (0.00 sec) Query OK, 1 row affected (0.00 sec) Records: 1 Duplicates: 0 Warnings: 0 Query OK, 0 rows affected (0.02 sec) Query OK, 0 rows affected (0.03 sec) Query OK, 1 row affected (0.03 sec) Records: 1 Duplicates: 0 Warnings: 0 ERROR 1062 (23000): Duplicate entry '张飞' for key 'PRIMARY' mysql> select * from test;// |
当前窗口结果:
新建窗口结果:
结论:由于test表中name的唯一性约束,看代码的话,两个"张飞"执行后(无论有无触发主键约束),实际由于第二个"张飞"触发了唯一性约束异常,所以我认为事务会跳出,所以在当前连接中,test表中可以看到一个张飞,实际上第二个事务,并没有提交成功。
接下来,我们试试正常提交的数据。
|
mysql> BEGIN ; -> INSERT INTO test SELECT '关羽' ; -> COMMIT ; -> BEGIN ; -> INSERT INTO test SELECT '张飞' ; -> INSERT INTO test SELECT '刘备' ; -> ROLLBACK ; -> // Query OK, 0 rows affected (0.00 sec) Query OK, 1 row affected (0.00 sec) Records: 1 Duplicates: 0 Warnings: 0 Query OK, 0 rows affected (0.02 sec) Query OK, 0 rows affected (0.02 sec) Query OK, 1 row affected (0.03 sec) Records: 1 Duplicates: 0 Warnings: 0 Query OK, 1 row affected (0.04 sec) Records: 1 Duplicates: 0 Warnings: 0 Query OK, 0 rows affected (0.04 sec) mysql> select * from test;// |
当前窗口结果:
新建窗口结果:
结论:对比这次的测试结果,所以我认为第一个测试,并没有执行rollback,而是跳出事务处理异常机制了。
因为mysql默认打开了autocommit,那么我想验证下在无显示事务的情况下(即无begin开头),两个"张飞"是如何自处的?
|
mysql> BEGIN ; -> INSERT INTO test SELECT '关羽' ; -> COMMIT ; -> INSERT INTO test SELECT '张飞' ; -> INSERT INTO test SELECT '张飞' ; -> ROLLBACK ; -> // Query OK, 0 rows affected (0.00 sec) Query OK, 1 row affected (0.00 sec) Records: 1 Duplicates: 0 Warnings: 0 Query OK, 0 rows affected (0.02 sec) Query OK, 1 row affected (0.05 sec) Records: 1 Duplicates: 0 Warnings: 0 ERROR 1062 (23000): Duplicate entry '张飞' for key 'PRIMARY' mysql> select * from test;// |
当前窗口结果:
新建窗口结果:
结论:其实看执行结果就知道了,第1个"张飞"作为单独的事务已经执行成功了,第二个"张飞"由于触发了主键约束所以执行失败了。除了显示事务外,有没有办法在没结束事务前(无Commit)前,可以让两个"张飞"合并成一个事务呢?
可以设置set completion_type=1;(chain),也就是说无论几个"张飞"在还没提交之前,都是一个事务。
代码与上面的一样。
|
mysql> SET @@completion_type = 1; -> BEGIN ; -> INSERT INTO test SELECT '关羽' ; -> COMMIT ; -> INSERT INTO test SELECT '张飞' ; -> INSERT INTO test SELECT '张飞' ; -> ROLLBACK ; -> // Query OK, 0 rows affected (0.00 sec) Query OK, 0 rows affected (0.00 sec) Query OK, 1 row affected (0.02 sec) Records: 1 Duplicates: 0 Warnings: 0 Query OK, 0 rows affected (0.02 sec) Query OK, 1 row affected (0.02 sec) Records: 1 Duplicates: 0 Warnings: 0 ERROR 1062 (23000): Duplicate entry '张飞' for key 'PRIMARY' |
当前窗口结果:
新建窗口结果:
结论:因为我设置了set completion_type=1(chain),相当与在第一个"张飞"前加了begin,所以第二个"张飞"由于触发了主键约束所以导致事务失败,插入数据失败。
以上为个人经验,希望能给大家一个参考,也希望大家多多支持开心学习网。如有错误或未考虑完全的地方,望不吝赐教。
原文链接:https://www.qttc.net/175-mysql-autocommit.html
- oraclemysql知识点(详解Mysql和Oracle之间的误区)
- mysql触发器入门(MySQL中触发器和游标的介绍与使用)
- mysql实验总结分析(MySQL查询截取的深入分析)
- mysql连接查询原理(MySQL连接查询你真的学会了吗?)
- mysql的三种模式(详解 MySQL的FreeList机制)
- 操作mysql的jdbc(JDBC连接的六步实例代码与mysql连接)
- mysql字符串默认长度(MySQL 字符类型大小写敏感)
- centos7.5安装mysql教程(CentOS8下MySQL 8.0安装部署的方法)
- 最新版MySQL 8.0.22下载安装超详细教程(Windows 64位)(最新版MySQL 8.0.22下载安装超详细教程Windows 64位)
- mysql索引原理及使用(再有人问你MySQL索引原理,就把这篇文章甩给他!)
- python对mysql数据分析(python使用adbapi实现MySQL数据库的异步存储)
- mysql字符类型长度限制
- mysql3种日志(mysql中的7种日志小结)
- mysql经典问题(MySQL null的一些易错点)
- mysql 如何选择隔离级别(全面解析MySQL中的隔离级别)
- 在mysql中如何授权(MySQL 角色role功能介绍)
- 今日大雪,大雪养生这样做,一年都有好气色(大雪养生这样做)
- 粗盐是什么 粗盐的功效与作用(粗盐的功效与作用)
- 会 吃人 的客机 从天堂到地狱只需5分钟,图-104如何做到(会吃人的客机)
- 男人犯的错,为什么要女人来承担(为什么要女人来承担)
- 心理学 四个金蟾,哪个最招财 测你今生的运势有多棒(心理学四个金蟾)
- 吉善缘《聚宝金蟾》金蟾招财摆件 三足全铜蟾蜍客厅店铺开业礼品(吉善缘聚宝金蟾金蟾招财摆件)
热门推荐
- easyui datebox的用法
- docker推荐单个容器运行(docker容器状态的转换实现)
- php怎么弄不重复字符串(PHP中将一个字符串部分字符用星号*替代隐藏的实现代码)
- docker容器启动自动执行命令(docker run 运行容器自动结束的解决)
- wordpress的静态php页面在哪(如何让PHPnow支持wordpress静态化链接的方法)
- linux系统查看nginx系统版本(Linux中Nginx的防盗链和优化的实现代码)
- iframe怎么设置域名(iframe与window.onload如何使用详解)
- docker推荐单个容器运行(docker容器状态的转换实现)
- css浮动小例子教程(使用css transition属性实现一个带动画显隐的微信小程序部件)
- laravel mysql 操作方式(Laravel使用原生sql语句并调用的方法)