MySQL 事务

事务

事务特性

原子性(A)

事务要么全部成功,要么全部失败,不会处于中间状态

一致性(C)

对数据有特定的预期状态,如非空,外键等等,这些更应该由应用层提供,数据库应该只用来保存数据而不处理具体逻辑

根据论文作者评论所说 C 只是为了使 ACID 更加顺口

隔离性(I)

并发执行的多个事务之间需要一定的隔离级别来保证数据的正确性

持久性(D)

数据库需要保证事务一旦提交,就应该永久保存到磁盘中

事务隔离级别

隔离级别越高,并行性能越低,从而导致性能下降

查看 MySQL 的默认隔离级别,可以看到 MySQL 默认隔离级别为:可重复读

mysql> show variables like 'transaction_isolation';
+-----------------------+-----------------+
| Variable_name         | Value           |
+-----------------------+-----------------+
| transaction_isolation | REPEATABLE-READ |
+-----------------------+-----------------+

读未提交

当事务还没提交时,其所做的更改就会被其它事务看到,会导致脏读(Dirty Read)

读提交

当一个事务提交后,所做修改才会被其它事务所看到

该隔离级别是大多数数据库默认的,如 Oracle, PostgreSQL, SQL Server 等

可重复读

在同一个事务执行过程中多次读取同样记录的结果是一样的,会导致幻读(Phantom Read)
当事务中需要使用 SELECT 语句查询,根据结果再更新数据就会导致更新错误

如:给员工没任务时安排新任务,当事务开始的时候查询到该员工需要安排新任务,在执行 INSERT 操作安排新任务时,别的事务在这个期间也安排了新任务,就会导致任务安排两份

MySQL 通过多版本并发控制(MVCC)技术解决了幻读问题,用于提高高并发下的吞吐性能

MVCC

通过保存某个时间点的快照来实现的,InnoDB 的 MVCC 是通过在每行记录后面保存两个隐藏的列实现的,一个是创建时间,另一个是删除时间(存储的不是具体的时间,而是系统版本号,每次开启事务会自动递增)

串行化

对于某一行数据的读取修改都会加锁,会严重影响性能

MySQL 采用两阶段提交(2PL)来实现可串行化隔离

MySQL 事务启动方式

显示启动事务

beginstart transaction 配套的提交语句是 commit,回滚语句是 rollback。

set autocommit=0 这个命令会将这个线程的自动提交关掉。意味着如果你只执行一个 select 语句,这个事务就启动了,而且并不会自动提交。这个事务持续存在直到你主动执行 commitrollback 语句,或者断开连接。

可以通过 select * from information_schema.INNODB_TRX; 查询当前数据库的所有事务

你可能感兴趣的:(mysql)