数据库的隐式提交

先看一段SQL,最后一条SQL的输出你认为是什么?

1
2
3
4
5
6
7
SET AUTOCOMMIT = 1;
BEGIN;
INSERT INTO t1 VALUES (1);
CREATE TABLE t2 (pk int primary key);
INSERT INTO t2 VALUES (2);
ROLLBACK;
SHOW TABLES;

答案是:t1, t2都存在!

1
2
3
4
5
6
7
8
mysql> show tables;
+----------------+
| Tables_in_test |
+----------------+
| t1             |
| t2             |
+----------------+
2 rows in set (0.00 sec)

更奇怪的是:t1中的1也插入成功了!

1
2
3
4
5
6
7
mysql> select * from t1;
+----+
| pk |
+----+
|  1 |
+----+
1 row in set (0.00 sec)

为什么ROLLBACK没有生效呢?答案是:Implict Commit
执行CREATE TABLE语句前,之前的事务被隐式提交。因为AUTOCOMMIT=1,所以提交后也不会自动新创建任何事务,INSERT语句执行后立即提交,ROLLBACK不会作用在任何事务上,所以得到了我们最后看到的结果。

稍微改一下,让AUTOCOMMIT=0,会怎样呢?

1
2
3
4
5
6
7
SET AUTOCOMMIT = 0;
BEGIN;
INSERT INTO t1 VALUES (1);
CREATE TABLE t2 (pk int primary key);
INSERT INTO t2 VALUES (2);
ROLLBACK;
SHOW TABLES;

答案是:t1, t2都存在!插入到t1中的1被提交(插入成功)但插入到t2中得2被回滚(没有插入成功)。之所以t1中的1被提交,是因为CREATE TABLE导致ImplictCOMMIT(注意,是COMMIT,不是ROLLBACK哦!),执行INSERT的时候,会自动开启一个新事务(AUTOCOMMIT=0的语义要求的行为)。所以t2中的2被ROLLBACK回滚。

为什么部分操作会导致Implict Commit?为什么这样设计?

为了保证直观上的原子性。假设不做Implict Commit,看看上面的语句会怎样:用户的心理预期是回滚t1的INSERT操作,以及t2的CREATE操作,INSERT操作。如果我们有能力做到这样,那的确是很完美的。但实际上我们很难做到,特别是在分布式系统中更难!因为CREATE TABLE操作背后涉及到了大量的操作,不仅仅包括对核心表的操作,还包括大量内存数据结构的更新(如Schema),以及存储系统的变更(如创建相应的数据块),工程上很难把这些操作做成原子的。

那么,应该如何做呢?比较折中的方式就是跟用户做一个约定:CREATE TABLE操作总默认COMMIT它之前的事务,这就是implict commit。

从MySQL文档看,他们做这一块的时候遇到了很多问题,至少在这里踩过两个坑。并且,随着版本的进化,他们还不断的让更多语句能引发implict commit。(转)

save?commit的更多相关文章

  1. modelform save

    ModelForm表单 save()方法 每一个ModelForm都有一个save()方法,这个方法可以更具绑定的form表单创建并且保存一个数据库对象,ModelForm的子类可以接受一个model ...

  2. Django:form.save()方法

    参考:https://blog.csdn.net/it_yuan/article/details/53580756 背景: 之前的博客是不支持上传文章缩略图的,后来新增了此功能,但是发现修改老的文章时 ...

  3. Django-ModelFrom中修改save后的字段值

    在ModelForm提交中,保持原未修改字段的值,views中部分代码: project = Iredmail.objects.get(id=id) ssh_crt_name = project.ss ...

  4. 《Django By Example》第四章 中文 翻译 (个人学习,渣翻)

    书籍出处:https://www.packtpub.com/web-development/django-example 原作者:Antonio Melé (译者注:祝大家新年快乐,这次带来<D ...

  5. 《Django By Example》第二章 中文 翻译 (个人学习,渣翻)

    书籍出处:https://www.packtpub.com/web-development/django-example 原作者:Antonio Melé (译者注:翻译完第一章后,发现翻译第二章的速 ...

  6. Django--自定义用户认证

    Django自带的用户认证 以前都是用Django自带的用户认证,用户名字段一对一关系对应Django--User表(其实它也是继承了abstractbaseuser). 1 2 3 from dja ...

  7. 【Django】--ModelForm组件

    ModelForm a.class Meta: model,#对应Model的 fields=None,#字段 exclude=None,#排除字段 labels=None,#提示信息 help_te ...

  8. Python之路【第二十二篇】CMDB项目

    浅谈ITIL TIL即IT基础架构库(Information Technology Infrastructure Library, ITIL,信息技术基础架构库)由英国政府部门CCTA(Central ...

  9. 尝试封装适用于权限管理的通用API

    谈谈我对权限系统的简单理解 最近一段时间在研究权限系统,在园子里看到个很牛逼的开源的基于DDD-Lite的权限管理系统,并有幸加入了作者的QQ群,呵呵,受到了很大的影响.对于权限管理我有我自己的一些简 ...

随机推荐

  1. unixbench安装及使用

    unixbench 是一个用于測试 unix 系统性能的工具.也是一个比較通用的 benchmark, 此測试的目的是对类Unix 系统提供一个主要的性能指示,非常多測试用于系统性能的不同方面,这些測 ...

  2. Pascal之Hello World

    Pascal入门篇. 平台:Windows 7 ultimate x64 工具:Free Pascal 下载安装,界面如下: 右键属性,选择“437(OEM-美国)”,重新打开程序,乱码消失.     ...

  3. 【[ZJOI2015]诸神眷顾的幻想乡】

    题目 听说这是广义\(SAM\)的板子 看来对于广义\(SAM\)我也就只会板子了 叶子数很少,所以可以枚举每一个叶子节点作为根建一遍\(Trie\)树 只需要对\(Trie\)树建出\(SAM\)就 ...

  4. C sharp #003# 面向对象编程基本构件

    饮水思源:金老师的自学网站 索引 类的属性 简化字段/属性的初始化 命名空间 程序集 类的属性 字段+get/set方法=属性 (之前都是把字段和属性混着用..) 经典写法: using System ...

  5. 递归函数之阶乘和字符串反转-基于R和Python

    Python课第五周开始讲函数了.递归函数.递归在python中不能超过900多层,否则报错内存溢出什么的.同样在R中递归太深也会报错,阈值和python中大概一样,900多次就报错了. error ...

  6. 搭建ssm中遇到的问题

    1.多模块pom.xml文件无效 原因是没有指定模块

  7. 【书籍连载】《STM32 HAL 库开发实战指南—基于F7》-第一章

    从今天起,每天开始连载一章<STM32 HAL 库开发实战指南—基于F7>.欢迎各位阅读.点评.学习. 第1章  如何使用本书 1.1  本书的参考资料 本书参考资料为:<STM32 ...

  8. poj_1995_Raising Modulo Numbers

    Description People are different. Some secretly read magazines full of interesting girls' pictures, ...

  9. MySQL - Mac下安装MySQL

    1. 去官网下载dmg的安装文件. 2. 下载完成后,运行安装文件,按步骤进行安装,安装完成后会弹出一个框显示临时密码! 3. 编辑~/.bashrc文件,配置快速启动/停止/重启/cdhome/别名 ...

  10. 注释java中某个方法过时

    添加一个注解即可 @Deprecated