原子性:(Atomicity)
事务是不可分割的最小操作单元,要么全部成功,要么全部失败;
一致性:(Consistency)
事务完成时,必须是所有数据保持一直状态;
隔离性:(Isolation)
多组事务存在并发,但是根据数据库系统提供的隔离机制,互不干扰;
持久性:(Durability)
事务一旦提交或回滚,其对数据库中数据的更改是持久性的。
脏读:
事务A 读取到 事务B 还没有提交的数据;
# 切换到最低事务隔离级别
set session transaction isolation level read uncommitted;
# 启动事务A与事务B
start transaction;
# 事务A查看表内容(并行1)
select * from account;
# 事务B修改表内容(并行1)
update account set money = money - 1000 where name= "张三";
# 事务A查看表内容
select * from account; # 发现数据库内容变化,但是事件B仍未提交commit;出现错误脏读;
解决方法:切换到 read committed 模式下;
不可重复读:
事务A 先后两次读取同一条记录时,两次读取到的数据不同;
解决方法:切换到 repeated read 模式下
不管事件B是否提交数据,事件A读取同一条记录一直保持不变,直到事件A也提交数据后再次查询;
幻读:
事务A 查询数据时,没有对应数据行,但是插入数据时,发现数据已经存在;事务B 插入数据并提交,但是事务A 由于具有不可重复性,所以虽然显示查询不到,但是也插入不了;
解决方法:切换到 serializable 模式下
事务A阻塞事务B,直到事务A提交后,事务B才可以进行插入操作;
存在四种事务隔离级别,事务隔离级别越高,数据越安全,但是性能越低;
Read uncommitted # 存在问题:脏读、不可重复度、幻读
Read committed # 存在问题:不可重复读、幻读
Repeatable Read # 存在问题:幻读(MySQL默认)
Serializable # 存在问题:无
查看事务隔离级别
select @@transaction_isolation;
设置事务隔离级别
set session transaction isolation level read uncommitted;
# 修改事务隔离级别为 Read uncommitted
事务的隔离级别越高,事务越安全,但是性能会越低;
事务的隔离级别越低,事务越不安全,但是性能高;
我们需要权衡事务隔离级别,一般采用默认的 Repeatable Read