跳到主要内容

事务

前言

在数据库操作中使用事务是为了保持逻辑数据的一致性和可恢复性。

事务特性

  • A——原子性,Atomicity,要么全部成功,要么全部失败
  • C——一致性,Consistency,事务开始前后,数据库中的数据完整性没有被破坏
  • I——隔离型,Isolation,隔离数据操作,以防止各事务并发执行时由于交叉执行导致数据不一致
  • D——持久性,Durability,事务对数据的操作是永久的。

控制事务

  • begin或start transaction,显式开启一个事务
  • commit或commit work,提交事务
  • rollback或rollback work,回滚事务
  • savepoint,创建一个保存点
  • release savepoint,删除保存点
  • rollback to,回滚到指定保存点
  • set transaction,设置事务隔离级别

示例

-- 使用事务从King账号转账给Jones
start transaction;
update emp set sal=sal-100 where ename='King';
update emp set sal=sal+100 where ename='Jones';
commit;

-- 使用savepoint
start transaction;
update emp set sal=sal-100 where ename='King';
savepoint sp1;
update emp set sal=sal+100 where ename='Jones';
rollback to savepoint sp1; -- 只有第一个update生效了,第二个update被回滚了

-- 回滚整个事务
rollback;

事务隔离级别

Postgres提供4种事务隔离级别,默认的事务隔离级别是读已提交。

  • 读未提交(READ-UNCOMMITTED)
  • 读已提交(READ-COMMITTED)
  • 可重复读(REPEATABLE-READ)
  • 可序列化读(SERIALIZABLE)

查看当前的事务隔离级别

show default_transaction_isolation;

不同的事务隔离级别会产生不同的问题,主要包含以下4种问题

  • 脏读:一个事务读取了另一个并行未提交写入的数据
  • 不可重复读:一个事务重新读取之前读取过的数据,发现该数据已经被另一个事务修改
  • 幻读:一个事务重新执行一个返回符合搜索条件的行集合的查询,发现满足条件的行集合因为另一个最近提交的事务而发生变化
  • 序列化异常:成功提交一组事务结果与这些事务所有可能的串行结果都不一致。
事务隔离级别脏读不可重复读幻读序列化异常
读未提交OOOO
读已提交XOOO
可重复读XXOO
可序列化读XXXX