PostgreSQL数据库事务实现方法分析
本文实例讲述了PostgreSQL数据库事务实现方法。分享给大家供大家参考,具体如下:
事务简介
事务管理器:有限状态机 日志管理器 CLOG:事务的执行结果 XLOG:undo/redo日志事务是所有数据库系统的一个基本概念。 一次事务的要点就是它把多个步骤捆绑成了一个单一的,不成功则成仁的操作。 其它并发的事务是看不到在这些步骤之间的中间状态的,并且如果发生了一些问题, 导致该事务无法完成,那么所有这些步骤都完全不会影响数据库。PostgreSQL为每条事务创建一个postgre进程,并发执行事务。采用分层的机制执行事务,上层事务块和底层事务。上层事务块是用户眼中的事务,用于控制事务执行的状态;底层事务是事务中的每条语句,可以改变上层事务块的状态。
上层事务块
每个postgre进程只有一个事务块,上层事务块记录着本次事务执行过程中的各个状态。
typedef enum TBlockState
{
/* not-in-transaction-block states */
TBLOCK_DEFAULT, /* idle */
TBLOCK_STARTED, /* 执行简单查询事务 */
/* transaction block states */
TBLOCK_BEGIN, /* 遇见事务开始BEGIN */
TBLOCK_INPROGRESS, /* 事务正在执行中 */
TBLOCK_PARALLEL_INPROGRESS, /* live transaction inside parallel worker */
TBLOCK_END, /* 遇见事务结束COMMIT/END的时候设置 */
TBLOCK_ABORT, /* 事务出错,等待ROLLBACK */
TBLOCK_ABORT_END, /* 事务出错,收到ROLLBACK */
TBLOCK_ABORT_PENDING, /* 事务处理中,接收到ROLLBACK */
TBLOCK_PREPARE, /* 事务处理中,收到PREPARE(分布式事务) */
/* subtransaction states */
TBLOCK_SUBBEGIN, /* starting a subtransaction */
TBLOCK_SUBINPROGRESS, /* live subtransaction */
TBLOCK_SUBRELEASE, /* RELEASE received */
TBLOCK_SUBCOMMIT, /* COMMIT received while TBLOCK_SUBINPROGRESS */
TBLOCK_SUBABORT, /* failed subxact, awaiting ROLLBACK */
TBLOCK_SUBABORT_END, /* failed subxact, ROLLBACK received */
TBLOCK_SUBABORT_PENDING, /* live subxact, ROLLBACK received */
TBLOCK_SUBRESTART, /* live subxact, ROLLBACK TO received */
TBLOCK_SUBABORT_RESTART /* failed subxact, ROLLBACK TO received */
} TBlockState;
常见的事务块状态转换图
底层事务
底层事务是需要执行的每条命令,负责处理资源和锁的获取和释放,信号的处理,日志记录等等
typedef enum TransState
{
TRANS_DEFAULT, /* idle */
TRANS_START, /* transaction starting */
TRANS_INPROGRESS, /* inside a valid transaction */
TRANS_COMMIT, /* commit in progress */
TRANS_ABORT, /* abort in progress */
TRANS_PREPARE /* prepare in progress */
} TransState;
主要有四个函数:
StartTransaction:由BEGIN的startTransactionCommand调用,调用结束后事务块状态为TBLOCK_STARTED CommitTransaction:由END的commitTransactionCommand调用,提交事务 AbortTransaction和CleanupTransaction:释放资源,恢复默认状态分布式事务
PostgreSQL提供了分布式事务中的,两阶段提交的接口
并发控制
PostgreSQL采用MVCC的方式进行并发控制,每个事务看到的是一段时间前的数据快照。同时,MVCC并不能够解决所有问题,所以也提供了行级和表级的锁。
标准的事务隔离级别有4个,而PostgreSQL只实现了读已提交和可串行化。
锁
PostgreSQL实现了8种锁(可怕)
太多了,就记住几个吧。
行共享锁:select for update/for share 表共享锁:select 行排他锁:insert/update/delete 表排他锁:drop加锁的对象
扩展锁:新增表空间死锁处理
MVCC
关键词:
基于事务ID 行级多版本 无回滚段,行内存储 一次UPDATE,产生记录两个版本 两个版本都存在页面内部TransactionId t_xmin; /* Insert,Update事务 */
TransactionId t_xmax; /* Delete,Update,Row Locks事务ID */
union
{
CommandId t_cid; /* 操作ID */
TransactionId t_xvac; /* old-style VACUUM FULL xact ID */
} t_field3;
} HeapTupleFields;
cmin:插入该元组的命令在插入事务中的命令标识(从0开始累加)
cmax:删除该元组的命令在插入事务中的命令标识(从0开始累加)
ctid:相当于rowid , 数据块ID,偏移量
XID:事务ID
Xid_snapshot:当前系统中未提交的事务
CLOG:事务状态日志(已提交的日志)
隔离级别
RC:读已提交 两个事务可以并发更新同一行 一个事务更新,一个事务删除同一行,删除操作会上锁RR:读未提交,其实是snapshot isolation,(冲突状态会回滚) 可串行化:serialize snapshot isolation,比标准可串行化要高,通过加内存中的意向锁实现,不允许预加锁的数据被其他事务变更
数据可见性判断
记录的头部XID信息比当前事务更早(rr和ssi有这个要求,read commited没有这个要求,读已经提交可以读未来的事务!!) 记录头部的XID信息不在当前的XID_snapshot中,(记录上的事务状态不是未提交的事务) 记录头部的XID信息在CLOG中代表已提交。MVCC需要判断该行数据在这个事务中的有效性,可见性,可更新性(需要锁的帮助才能正确执行隔离级别) 判断条件:若xmin等于当前事务ID,则包含所有xmax=0(未被删除)的元组。
若与xmin相等的事务ID对应的事务已经被提交,则包含所有xmax=0或xmax为当前事务ID的元组。 对读不用加锁,对写加锁(只阻塞写),事务结束对比是否冲突
pg_log:数据库活动日志(也就是数据库的操作日志); pg_xlog:事务日志,记录事务的执行过程,redo日志 pg_clog:事务状态日志(pg_clog是pg_xlog的辅助日志),记录事务的结果。
希望本文所述对大家PostgreSQL数据库程序设计有所帮助。
我想要获取技术服务或软件
服务范围:MySQL、ORACLE、SQLSERVER、MongoDB、PostgreSQL 、程序问题
服务方式:远程服务、电话支持、现场服务,沟通指定方式服务
技术标签:数据恢复、安装配置、数据迁移、集群容灾、异常处理、其它问题
本站部分文章参考或来源于网络,如有侵权请联系站长。
数据库远程运维 PostgreSQL数据库事务实现方法分析
相关文章
- 修复Domino数据库视图索引的两种方法
- 通过一个小项目介绍Python3读写Access数据库(.mdb)的方法
- 查看postgresql数据库用户系统权限、对象权限的方法
- 修改mysql root 密码的方法详解数据库
- mysql 连接闪断自动重连的方法(用在后台运行中的PHP代码)详解数据库
- mysql connect refuse解决方法详解数据库
- PostgreSQL服务器启动和关闭方法介绍详解数据库
- Oracle查询前几条数据的方法详解数据库
- PostgreSQL编码协议:改变数据库架构(postgresql协议)
- 查看Oracle数据库状态的简单方法(oracle查看数据库状态)
- PostgreSQL:实现数据库的继承性(postgresql继承)
- PostgreSQL新建数据库:快速搭建实现数据存储 (postgresql新建数据库)
- 学习PostgreSQL:踏上数据库运维之路(postgresql使用教程)
- Python如何连接PostgreSQL数据库?(python连接postgresql)
- PostgreSQL:未来数据库发展的光明前景(postgresql前景)
- PostgreSQL接口:轻松连接数据库(postgresql接口)
- PostgreSQL库:高可靠性企业级数据库的首选(postgresql库)
- Oracle数据库中日期类型的转换及格式化方法(oracle转日期)
- 数据库PostgreSQL:开放源码的分布式数据库管理系统(postgresql开源)
- PostgreSQL外键:更好的数据库关联性(postgresql外键)
- 查看MySQL数据库容量的方法(查看mysql容量)
- 如何顺利升级PostgreSQL数据库?(升级postgresql)
- PostgreSQL 语法简单易懂的使用方法(postgresql语法)
- Postgresql权威指南:打造完美数据库环境(postgresql手册)
- 利用MSSQL获取数据库中所有数据表的方法(mssql获取所有数据表)
- Postgresql数据库实现事务回滚技术(postgresql回滚)
- 深入了解 PostgreSQL 数据库结构(postgresql结构)
- 解决Oracle数据库中获取余数的方法(oracle中获取余数)
- 字符Oracle数据库中从后截取字符的实现方法(oracle 从后截取)
- php中用文本文件做数据库的实现方法
- 自动定时备份sqlserver数据库的方法
- php连接mssql数据库的几种方法