一、事务的基本要素(ACID)
1、原子性(Atomicity)
事务开始后所有操作,要么全部做完,要么全部不做,不可能停滞在中间环节。事务执行过程中出错,会回滚到事务开始前的状态,所有的操作就像没有发生一样。也就是说事务是一个不可分割的整体,就像化学中学过的原子,是物质构成的基本单位。
2、一致性(Consistency)
事务开始前和结束后,数据库的完整性约束没有被破坏 。比如A向B转账,不可能A扣了钱,B却没收到。
3、隔离性(Isolation)
对同一数据的操作,不同的事务之间彼此没有任何干扰。比如A正在从一张银行卡中取钱,在A取钱的过程结束前,B不能向这张卡转账。隔离性引申出很多问题,下面的事务隔离级别就是针对事务的隔离性的
4、持久性(Durability)
事务完成后,事务对数据库的所有更新将被保存到数据库,即使服务器宕机,重启后数据还是存在且正确的。
二、MySQL事务隔离级别
幻读和不可重复读的区别:
不可重复读
重点是修改:在同一事务中,同样的条件,第一次读的数据和第二次读的数据不一样。(一个事务多次读取同一范围内数据时,另外一个发生了事务发生insert操作并提交了)。数据变化。
幻读
重点在于新增或者删除:在同一事务中,同样的条件,,第一次和第二次读出来的记录数不一样。(一个事务多次读取同一条数据时,另外一个发生了事务发生update,delete操作并提交了。insert操作一条新数据并不会影响刚才被读的那条数据。)。行数变化。
不可重复读针对的是同一条数据,幻读针对的是一片数据。
事务隔离级别 | 含义 | 解决问题 |
读未提交(read-uncommitted) | 在这种隔离级别下,可能会出现脏读、不可重复读、幻读问题。 | |
读已提交(read-committed) | 在同一个事务中多次读取数据,当在读取间隔有其它事务修改数据,则在本事务中本次读取和之前读取结果就不一样了 | 解决脏读问题。 |
可重复读(repeatable-read) | 简单来说就是在同一个事务中多次读取同样的记录的结果是一样的,Innodb使用MVCC来实现。 | 解决脏读、不可重复读问题。 |
串行化(serializable) | 解决脏读、不可重复读、幻读问题。 |
三、TiDB的事务隔离级别
类似于读已提交。
为什么这么说呢?因为TiDB是数据强一致性,即一定拿查到提交后的正确数据。怎么做到的?其实很简单,Raft协议半数提交成功则认为是成功的,并将这些成功的打上标记,让App去使用,这意味着其它还没提交的则不提供服务,即查不到;所以一定是强一致性的。
四、分布式事务
最经典的是2PC,即两阶段提交协议。
1、2PC的第一步就是询问,目的就是检测是否有其它事务正在对要操作的数据进行操作,即解决隔离性问题;
2、第一阶段要求所有参与者反馈YES响应,同时第二阶段要都返回ACK消息,这保证了原子性(只要有一个不成功即全部回滚);
其实经过前两不,多个事务不干扰,且操作成功,也保证了一致性;都操作成功了,即持久化了,所以肯定也满足了持久性。