达梦数据库事务管理

1.事务介绍

  数据库中由用户自定义发起的一些列操作集合简称事务。只要可以连接数据库中进行一组操作序列都可以称为事务。

  COMMIT 操作会将该语句所对应事务对数据库的所有更新持久化(即写入磁盘),数据库此时进入一个新的一致性状态,同时该事务成功地结束。ROLLBACK 操作将该语句所对应事务对数据库的所有更新全部撤销,把数据库恢复到该事务初启动前的一致性状态。

事务最简单的例子就是转账:

例如:

A 500 B 500 ,A向B转账100;

事务开始:A-100,B+100

操作成功:A400 B600

操作失败:A500 B500

不可能发生 A500 B600或者A400 B500

2.事务特性

原子性:事务为最小单位不允许单独分开,所有一系列操作要么全部成功,要么全部失败回滚。

一致性:事务执行前后,数据保持一致。

隔离性:各并发事务是隔离的相互不受影响。事务的隔离行为依赖于指定的隔离级别。

永久性:事务一旦提交,它对数据库的改变是永久的,即使数据库出现故障对其也不应该产生影响。

3.事务隔离级别

1.脏读(DirtyRead)所谓脏读就是对脏数据的读取,而脏数据所指的就是未提交的已修改数据。

2.不可重复度(Non-RepeatableRead)一个事务先后读取同一条记录,但两次读取的数据不同,我们称之为不可重复读。

3.幻想读(PhantomRead)一个事务按相同的查询条件重新读取以前检索过的数据,却发现其他事务插入了满足其查询条件的新数据,这种现象就称为幻像读

在 SQL-92 标准中,定义了四种隔离级别:读未提交、读提交、可重复读和串行化。每种隔离级别下对于读数据有不同的要求,下表中列出四种隔离级别下系统允许/禁止哪些类型的读数据现象。其中―Y‖表示允许,―N‖表示禁止。

分类脏读不可重复读幻像读
读未提交YESYESYES
读提交NOYESYES
可重复读NONOYES
串行化NONONO

DM 数据库支持三种事务隔离级别:读未提交、读提交和串行化。

达梦数据库默认隔离级别与Oracle一样:读提交

读未提交隔离级:

读未提交隔离级别是最不严格的隔离级别。实际上,在使用这个隔离级别时,有可能发生脏读、不可重复读和幻像。一般来说,读未提交隔离级别通常只用于访问只读表和只读视图,以消除可见性判断带来的系统开销,提升查询性能。

会话A设置会话事务隔离级别:

 set transaction isolation level read uncommitted;

会话B插入数据后不提交:
 insert into t1 values(6,'dm@dameng.com','达梦');

会话A查询:

 select * from t1;

ID          MAIL             NAME  
----------- ---------------- ------
1           123@qq.com       周丽
2           123123@126.com   金湖
3           zgc@dameng.com   刘少
4           liuhu@163.com    刘虎
5           liling@dameg.com 李玲

读提交隔离级别:

DM 数据库的读提交隔离可以确保只访问到已提交事务修改的数据,保证数据处于一致性状态,能够满足大多数应用的要求,并最大限度的保证系统并发性能,但可能会出现不可重复读取和幻像读

会话A设置会话事务隔离级别:

 set transaction isolation level read committed;

会话B插入数据后并提交:
 insert into t1 values(6,'dm@dameng.com','达梦');

commit;

会话A查询:

 select * from t1 where id=6;

ID          MAIL          NAME  
----------- ------------- ------
6           dm@dameng.com 达梦

串行化隔离级别:

在要求消除不可重复读取或幻像读的情况下,我们可以设置事务隔离级为串行化。跟读提交隔离级相比,串行化事务的查询本身不会增加任何代价,但修改数据可能引发―串行化事务被打断错误。

 会话A设置会话事务隔离级别:

 set transaction isolation level serializable;

会话A查询T1表:

select * from t1;

ID          MAIL             NAME  
----------- ---------------- ------
1           123@qq.com       周丽
2           123123@126.com   金湖
3           zgc@dameng.com   刘少
4           liuhu@163.com    刘虎
5           liling@dameg.com 李玲
6           dm@dameng.com    达梦
7           1234321@126.com  李龙

会话A修改会话并提交

SQL> update t1 set mail='1234321@163.com' where id=7;
影响行数 1

已用时间: 1.518(毫秒). 执行号:1470104.
SQL> commit;
操作已执行
已用时间: 1.034(毫秒). 执行号:1470105.

会话B设置隔离级别并更新

SQL> set transaction isolation level serializable;
操作已执行
已用时间: 0.286(毫秒). 执行号:1469301.
SQL> select * from t1;

ID          MAIL             NAME  
----------- ---------------- ------
1           123@qq.com       周丽
2           123123@126.com   金湖
3           zgc@dameng.com   刘少
4           liuhu@163.com    刘虎
5           liling@dameg.com 李玲
6           dm@dameng.com    达梦
7           1234321@126.com  李龙

7 rows got

已用时间: 0.596(毫秒). 执行号:1469303.
SQL>  update t1 set mail='1234321@126.com' where id=7;
 update t1 set mail='1234321@126.com' where id=7;
[-7066]:串行化事务被打断.
已用时间: 1.286(毫秒). 执行号:0.

4.事务提交

事务提交是指对数据库所做的修改,将事务开始所有的变更操作保存到数据库中,任何更改记录都会记录到数据库里,无论是先写入到日志最终写入到磁盘(数据文件)。达梦数据库存在3种提交模式:自动提交、手动提交和隐士提交。

5.事务锁定

达梦数据库支持多用户并发、修改数据,会出现多个事务同时访问、修改相同数据的情况。封锁机制是实现数据库并发控制的一个非常重要的技术。当事务在对某个数据库对象进行操作前,需要先对其封锁。封锁后事务就对该数据库对象有了一定的控制,在该事务释放锁之前,其他的事务不能对此数据库对象进行相应操作。

达梦数据库锁模式

锁模式指定并发用户如何访问锁定资源。DM 数据库使用四种不同的锁模式:共享锁、排他锁、意向共享锁和意向排他锁。

1.共享锁:共享锁(Share Lock,简称 S 锁)用于读操作,防止其他事务修改正在访问的对象。
这种封锁模式允许多个事务同时并发读取相同的资源,但是不允许任何事务修改这个资源。

2.排它锁:排他锁(Exclusive Lock,简称 X 锁)用于写操作,以独占的方式访问对象,不允
许任何其他事务访问被封锁对象;防止多个事务同时修改相同的数据,避免引发数据错误;防止访问一个正在被修改的对象,避免引发数据不一致。一般在修改对象定义时使用。

3.意向锁:意向锁(Intent Lock)用于读取或修改被访问对象数据时使用,多个事务可以同时
对相同对象上意向锁,DM 支持两种意向锁:

3.1意向共享锁(Intent Share Lock,简称 IS 锁):一般在只读访问对象时使用;

3.2意向排他锁(Intent Exclusive Lock,简称 IX 锁):一般在修改对象数据时使用。

四种锁模式的相容矩阵如下表所示,其中―Y‖表示相容;―N‖表示不相容。如表中第二行第二列为―Y‖,表示如果某个事务已经加了 IS 锁时,其他事务还可以继续添加 IS 锁,第二行第五列为―N‖,表示如果某个事务已经加了 IS 锁时,其他事务不能添加 X 锁。

显式锁定表:

用户可以根据自己的需要显式的对表对象进行封锁。显式锁定表的语法如下:
LOCK TABLE <table_name> IN <lock_mode> MODE [NOWAIT];

--共享锁

lock table test1 in share mode;

--排它锁

lock table test1 in EXCLUSIVE mode;

--意向共享锁

lock table test1 in INTENT SHARE mode;

--意向排它锁

lock table test1 in INTENT EXCLUSIVE mode;

lock_mode 是锁定的模式,可以选择的模式有 INTENT SHARE(意向共享)、INTENT EXCLUSIVE(意向排他)、SHARE(共享)和 EXCLUSIVE(排他),其含义分别如下:
1) 意向共享:不允许其他事务独占修改该表。意向共享锁定后,不同事务可以同时增、删、改、查该表的数据,也支持在该表上创建索引,但不支持修改该表的定义;
2) 意向排他:不允许其他事务独占访问和独占修改该表。被意向排他后,不同事务可以同时增、删、改、查该表的数据,不支持在该表上创建索引,也不支持修改该表定义;
3) 共享:只允许其他事务共享访问该表,仅允许其他事务查询表中的数据,但不允许增、删、改该表的数据;
4) 排他:以独占访问方式锁定整个表,不允许其他事务访问该表,是封锁力度最大的一种封锁方式。
当使用 NOWAIT 时,若不能立即上锁成功则立刻返回报错信息,不再等待。

分类ISIXSX
ISYYYN
IXYYNN
SYNYN
XNNNN

6. 多版本控制

  DM 数据库的多版本实现完全消除了行锁对系统资源的消耗,查询永远不会被阻塞也不需要上行锁,并通过 TID 锁机制消除了插入、删除、更新操作的行锁。数据库的读操作与写操作不会相互阻塞,并发度大幅度提高。DM 数据库基于物理记录和回滚记录实现行级多版本支持,数据页中只保留物理记录的最新版本,通过回滚记录维护历史版本,所有事务针对特定的版本进行操作。

物理记录:为了适应多版本机制,高效地获取历史记录,每一条物理记录中包含了两个字段:TID
和 RPTR。TID 保存修改记录的事务号,RPTR 保存回滚段中上一个版本回滚记录的物理地址。插入、删除和更新物理记录时,RPTR 指向操作生成的回滚记录的物理地址。

回滚记录:回滚记录与物理记录一样,增加了两个字段:TID 和 RPTR。TID 保存回滚记录对应的
事务号,RPTR 保存回滚段中上一个版本回滚记录的物理地址。插入物理记录时,由于没有更老的版本数据,回滚记录的 RPTR 值为 NULL;更新和删除物理记录时,RPTR 指向原始物理记录的 RPTR。

7.相关动态视图

视图描述
V$SESSIONS显示会话的具体信息
V$TRX显示所有活动事务的信息
V$TRXWAIT显示事务等待信息
V$LOCK显示当前系统中锁的状态
V$DEADLOCK_HISTORY显示死锁的历史信息

8.闪回

闪回技术主要是通过回滚段存储的 UNDO 记录来完成历史记录的还原。

设置ENABLE_FLASHBACK 为 1 后,开启闪回功能。DM 会保留回滚段一段时间,回滚段保留的
时间代表着可以闪回的时间长度。由 UNDO_RETENTION 参数指定。

    开启闪回功能后,DM 会在内存中记录下每个事务的起始时间和提交时间。通过用户指
定的时刻,查询到该时刻的 LSN,结合当前记录和回滚段中的 UNDO 记录,就可以还原出特
定 LSN 的记录。即指定时刻的记录状态。从而完成闪回查询。闪回查询功能完全依赖于回
滚段管理,对于 DROP 等误操作不能恢复。闪回特性可应用在以下方面:
    1. 自我维护过程中的修复:当一些重要的记录被意外删除,用户可以向后移动到一个时间点,查看丢失的行并把它们重新插入现在的表内恢复;
    2. 用于分析数据变化:可以对同一张表的不同闪回时刻进行链接查询,以此查看变化的数据。

#查询闪回功能并开启闪回

SQL> select sf_get_para_value(1,'ENABLE_FLASHBACK');

SF_GET_PARA_VALUE(1,'ENABLE_FLASHBACK')
---------------------------------------
0   

SQL> sp_set_para_value(1,'ENABLE_FLASHBACK','1');
DMSQL 过程已成功完成

SQL> select sf_get_para_value(1,'ENABLE_FLASHBACK');

SF_GET_PARA_VALUE(1,'ENABLE_FLASHBACK')
---------------------------------------
1                                      

1 rows got

已用时间: 11.266(毫秒). 执行号:1470115.

##设置UNDO_RETENTION值

SQL> select  sf_get_para_double_value(1,'undo_retention');

SF_GET_PARA_DOUBLE_VALUE(1,'undo_retention')
--------------------------------------------
9.000000000000000E+01                       

1 rows got

已用时间: 11.888(毫秒). 执行号:1470116.

SQL> sp_set_para_double_value(1,'undo_retention','3600');
DMSQL 过程已成功完成
已用时间: 13.970(毫秒). 执行号:1470118.

#测试模拟

SQL> insert into t1 values(1,'123131412@qq.com','张毅');
影响行数 1

SQL> insert into t1 values(2,'zhanglong@126.com','张龙');
影响行数 1

已用时间: 0.904(毫秒). 执行号:2829712.
SQL> insert into t1 values(3,'lihong@163.com','李红');
影响行数 1

已用时间: 0.724(毫秒). 执行号:2829713.
SQL> commit;
操作已执行
已用时间: 0.989(毫秒). 执行号:2829714.
SQL> insert into t1 values(4,'zhaohu@163.com','赵虎');
影响行数 1

已用时间: 1.023(毫秒). 执行号:2829715.
SQL> commit;

SQL> select * from t1;

ID          MAIL              NAME  
----------- ----------------- ------
1           123131412@qq.com  张毅
2           zhanglong@126.com 张龙
3           lihong@163.com    李红
4           zhaohu@163.com    赵虎

4 rows got

已用时间: 0.396(毫秒). 执行号:2829717.

SQL> select sysdate;

SYSDATE            
-------------------
2023-01-18 10:16:10

1 rows got

已用时间: 0.656(毫秒). 执行号:2829718.

SQL> delete from t1;
影响行数 4

已用时间: 0.566(毫秒). 执行号:2829719.
SQL> commit;
操作已执行
已用时间: 0.985(毫秒). 执行号:2829720.
SQL> select * from t1 when timestamp '2023-01-18 10:16:10';

ID          MAIL              NAME  
----------- ----------------- ------
1           123131412@qq.com  张毅
2           zhanglong@126.com 张龙
3           lihong@163.com    李红
4           zhaohu@163.com    赵虎

4 rows got

已用时间: 0.950(毫秒). 执行号:2829721.
SQL> select * from t1 when timestamp '2023-01-18 10:16:10' where id =4;

ID          MAIL           NAME  
----------- -------------- ------
4           zhaohu@163.com 赵虎

1 rows got

已用时间: 0.897(毫秒). 执行号:2829722.

需要注意的是开启闪回功能,仅对开启后时间的数据有效,闪回功能开启前的数据是无法查询的,例如是开启闪回后创建的表和新增数据。

-- 删除开启闪回功能前的数据

SQL> delete from t2 where id=1;
影响行数 1

 --删除开启闪回功能后的数据

SQL> delete from t2 where id=12;
影响行数 1

已用时间: 1.398(毫秒). 执行号:2829747.

--提交

SQL> commit;

#进行删除前时间点的闪回查询:只能查到开启闪回功能后的插入的数据ID=12  ,ID=1数据查询不到。

在线服务平台地址:

https://eco.dameng.com

 

  • 0
    点赞
  • 2
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值