这是一个非常实用的功能,特别用在记录错误日志同时要回滚主事务的时候,我们在实际开发中就是这么用的,感觉还是很方便的。转载一篇详细的介绍,感谢原作者。
在基于低版本的ORACLE做一些项目的过程中,有时会遇到一些头疼的问题.,比如想在执行当前一个由多个DML组成的transaction(事务)时,为每一步DML记录一些信息到跟踪表中,由于事务的原子性,这些跟踪信息的提交将决定于主事务的commit或rollback. 这样一来写程序的难度就增大了, 程序员不得不把这些跟踪信息记录到类似数组的结构中,然后在主事务结束后把它们存入跟踪表.哎,真是麻烦!
有没有一个简单的方法解决类似问题呢?
ORACLE8i的AUTONOMOUS TRANSACTION(自治事务,以下AT)是一个很好的回答。
AT 是由主事务(以下MT)调用但是独立于它的事务。在AT被调用执行时,MT被挂起,在AT内部,一系列的DML可以被执行并且commit或rollback.
注意由于AT的独立性,它的commit和rollback并不影响MT的执行效果。在AT执行结束后,主事务获得控制权,又可以继续执行了。
见图1:
图1:
如何实现AT的定义呢?我们来看一下它的语法。其实非常简单。
只需下列PL/SQL的声明部分加上PRAGMA AUTONOMOUS_TRANSACTION
就可以了。
1. 顶级的匿名PL/SQL块
2. Functions 或 Procedure(独立声明或声明在package中都可)
3. SQL Object Type的方法
4. 触发器。
比如:
在一个独立的procedure中声明AT
CREATE OR REPLACE PROCEDURE
Log_error(error_msg IN VARCHAR2(100))
IS
PRAGMA AUTONOMOUS_TRANSACTION;
BEGIN
Insert into Error_log values ( sysdate,error_msg);
COMMIT;
END;
下面我们来看一个例子,(win2000 advanced server + oracle8.1.6 , connect as scott)
建立一个表:
create table msg (msg varchar2(120));
首先,用普通的事务写个匿名PL/SQL块:
declare
cnt number := -1; --} Global variables
procedure local is
begin
select count(*) into cnt from msg;
dbms_output.put_line('local: # of rows is '||cnt);
insert into msg values ('New Record');
commit;
end;
begin
delete from msg ;
commit;
insert into msg values ('Row 1');
local;
select count(*) into cnt from msg;
dbms_output.put_line('main: # of rows is '||cnt);
rollback;
local;
insert into msg values ('Row 2');
commit;
local;
select count(*) into cnt from msg;
dbms_output.put_line('main: # of rows is '||cnt);
end;
运行结果(注意打开serveroutput)
local: # of rows is 1 -> 子程序local中可以’看到’主匿名块中的uncommitted记录
main: # of rows is 2 -> 主匿名块可以’看到’2条记录(它们都是被local commit掉的)
local: # of rows is 2 -> 子程序local首先’看到’2条记录,然后又commit了第三条记录
local: # of rows is 4 -> 子程序local又’看到’了新增加的记录(它们都是被local commit掉的),然后又commit了第五条记录
main: # of rows is 5 -> 主匿名块最后’看到’了所有的记录.
从这个例子中,我们看到COMMIT和ROLLBACK的位置无论是在主匿名块中或者在子程序中,都会影响到整个当前事务.
现在用AT改写一下匿名块中的procedure local:
...
procedure local is
pragma AUTONOMOUS_TRANSACTION;
begin
...
重新运行(注意打开serveroutput)
local: # of rows is 0 -> 子程序local中无法可以’看到’主匿名块中的uncommitted记录 (因为它是独立的)
main: # of rows is 2 -> 主匿名块可以’看到’2条记录,但只有一条是被commited.
local: # of rows is 1 -> 子程序local中可以’看到’它前一次commit的记录,但是主匿名块中的记录已经被提前rollback了
local: # of rows is 3 -> 子程序local 中可以’看到’3条记录包括主匿名块commit的记录
main: # of rows is 4 ->主匿名块最后’看到’了所有的记录.
很明显,AT是独立的,在它执行时,MT被暂停了. AT的COMMIT,ROLLBACK并不影响MT的执行.
运用AT时,有一些注意事项,简单列举如下:
1. 在匿名PL/SQL块中,只有顶级的匿名PL/SQL块可以被设为AT
2. 如果AT试图访问被MT控制的资源,可能有deadlock发生.
3. Package 不能被声明为AT,只有package所拥有的function和procedure 才能声明为AT
4. AT程序必须以commit 或rollback结尾,否则会产生Oracle错误ORA-06519: active autonomous transaction detected and rolled back
在程序开发时,如果充分运用AUTONOMOUS TRANSACTION的特性,一定能取得事倍功半的效果.
参考博客: http://wxy0327.itpub.net/post/16888/99854
相关推荐
Oracle自治事务的介绍(Autonomous_Transactions)PRAGMA_AUTONOMOUS_TRANSACTION
在触发器中使用自制事务及调用存储过程 Declare Pragma Autonomous_Transaction; ...
自治事务是与主事务相分离的,所以它不能检测到被修改过的行的当前状态。这就好像在主事务提交之前,它们一直处于单独的会话里,对自治事务来说,它们是不可用的。然而,反过来情况就不同了:主事务能够检测到已经...
oracle 触发器 调用 存储过程 Oracle自治事务(Autonomous Transaction)
对子程序的调用者权限、管道表函数、传递触发器标识:new和:old以及自治事务也给出了具体的解决方法。第8 章 LOB与面向对象的数据管理. 第9章 Oracle的监听器和网络设置。包括Oracle网络体系结构,Oracle Net参数文件...
对子程序的调用者权限、管道表函数、传递触发器标识:new和:old以及自治事务也给出了具体的解决方法。第8 章 LOB与面向对象的数据管理. 第9章 Oracle的监听器和网络设置。包括Oracle网络体系结构,Oracle Net参数文件...
第一部分 ORACLE系统优化基本知识 23 第1章 ORACLE结构回顾 23 §1.1 Oracle数据库结构 23 §1.1.1 Oracle数据字典 23 §1.1.2 表空间与数据文件 24 §1.1.3 Oracle实例(Instance) 24 §1.2 Oracle文件 26 §1.2.1...
CruiseYoung提供的带有详细书签的电子... 14.12 自治事务 409 14.13 小结 413 第15章 测试与质量保证 415 15.1 测试用例 416 15.2 测试方法 417 15.3 单元测试 418 15.4 回归测试 422 15.5 模式修改 422 15.6...
8.6.1 自治事务如何工作? 273 8.6.2 何时使用自治事务? 276 8.7 小结 279 第9章 redo与undo 281 9.1 什么是redo? 281 9.2 什么是undo? 282 9.3 redo和undo如何协作? 285 9.4 提交和回滚处理 289 9.4.1 ...
Oracle自治事务处理数据库(Oracle ATP)AES256-CBC与其他数据库之间的互操作性 动机 现代软件系统之间的互操作性对于客户而言尤其重要。 借助我的Always Free Oracle ATP中的Oracle RESTful数据服务(ORDS)技术,...
第 1章 开发成功的Oracle应用程序...................................................... 61 1.1 我的方法................................................................................ 63 3 / 976 1.2 ...
[Q]怎么样设置自治事务 5 [Q]怎么样在过程中暂停指定时间 5 [Q]怎么样快速计算事务的时间与日志量 5 [Q]怎样创建临时表 6 [Q]怎么样在PL/SQL中执行DDL语句 6 [Q]怎么样获取IP地址 7 [Q]怎么样加密存储过程 7 [Q] 7 ...
怎么获得今天是星期几,还关于其它日期函数用法 [Q]随机抽取前N条记录的问题 [Q]抽取从N行到M行的记录,如从20行到30行的记录 [Q]怎么样抽取重复记录 [Q]怎么样设置自治事务 [Q]怎么样在过程中暂停指定时间 [Q]...
本文介绍了在记录有关Oracle数据库中的操作的信息时可以使用的技术,例如自治事务和操作信息。
9:数据装载 10:优化策略和工具 11:优化器方案稳定性 12:分析函数 13:物化试图 14:分区 15:自治事务 16:动态SQL 17:intermedia 18:基于C的外部过程 19:JAVA存储过程 20:使用对象关系特性 21:精细存取控制...
Oracle自治数据库是一个创新的数据平台,包括事务数据,关系数据,nosql和分析数据。 在这段时间内,我们将构建一个包含事务处理应用程序和分析应用程序的集成数据平台。 在此期间,我们将执行的主要主题是: 1....
9:数据装载 10:优化策略和工具 11:优化器方案稳定性 12:分析函数 13:物化试图 14:分区 15:自治事务 16:动态SQL 17:intermedia 18:基于C的外部过程 19:JAVA存储过程 20:使用对象关系特性 21:精细存取控制...
PLSQL个人总结最佳实践。