一、事务的特性
原子性:事务中包含的逻辑,不可再分。如几个逻辑单元加起来构成一个事务,银行转账你增我减
一致性:事务执行前后,数据完整性
隔离性:事务在执行期间不应该收到其它事务的影响
持久性:事务执行成功,数据应该持久保存到磁盘上
二、事务的安全隐患
不考虑隔离级别(@@tx_isolation 表)设置,那么会出现一下问题(读和写问题)
1、脏读
一个事务读到另一个事务还未提交的数据。因为读取到的是数据库内存中的数据,而非真正磁盘上的数据。可开启两个DOS验证。分别开启事务进行查询更新操作,记得设置隔离级别为“读未提交”,隔离级别很低。
读未提交、读已提交
2、不可重复读
一个事务读到了另外一个事务提交的数据,造成了前后两次查询结果不一致。
重复读
3、幻读
一个事务读到了另一个事务已提交的插入的数据,导致多次查询结果不一致。
可串行化
隔离级别比较
注:可串行化隔离级别,如果有一个连接的隔离级别设置为了串行化,那么谁先打开了事务,谁就有了先执行的权利,谁后打开事务,就只能等着,等前面那个事务提交或者回滚后,才能执行。但是这种隔离级别一般比较少用,性能、效率低。
按效率划分:
读未提交 > 读已提交 > 可重复读 > 可串行化
按拦截程度:
可串行化 > 可重复读 > 读已提交 > 读未提交
4、丢失更新
一个事务A修改名字,一个事务B修改金额,最终查询结果是后一个事务的处理结果,那前一个事务的更新丢失。如果B提交,A名字更新失败,如果B回滚,A更新丢失。
解决办法:锁
悲观锁:预设一定会产生“丢失更新”,所以在更新后,查询时会加上 for update来确定更新内容
乐观锁:预设肯定不会产生“丢失更新”,要求程序员自己控制,如,加版本标识区分更新版本来达到一致性,添加字段或者其它标识。