用PL/SQL Developer创建Oracle触发器以及触发器的一点点知识与出现的问题

摘自:http://blog.csdn.net/asdsa108/article/details/50540320


本文将介绍如何使用PL/SQL Developer快速的创建一个Oracle触发器,应该明确的是鼠标的所有操作都是可以用代码实现的


一、打开PL/SQL Developer,登录到数据库

用PL/SQL Developer创建Oracle触发器以及触发器的一点点知识与出现的问题

二、在左侧Objects上右击,选new

用PL/SQL Developer创建Oracle触发器以及触发器的一点点知识与出现的问题用PL/SQL Developer创建Oracle触发器以及触发器的一点点知识与出现的问题

左侧如果没有Objects,在菜单里按Tools,下拉菜单中选中Object Browser

用PL/SQL Developer创建Oracle触发器以及触发器的一点点知识与出现的问题

三、弹出对话框

用PL/SQL Developer创建Oracle触发器以及触发器的一点点知识与出现的问题用PL/SQL Developer创建Oracle触发器以及触发器的一点点知识与出现的问题用PL/SQL Developer创建Oracle触发器以及触发器的一点点知识与出现的问题

其中

1.Name是触发器名称

2.Fires是触发时间,选项包括before、after以及instead of

先介绍before和after,顾名思义,before是触发事件执行前触发,after是触发事件执行后触发,触发顺序如下

1.        执行 BEFORE语句级触发器;

2.        对于受语句影响的每一行:

l         执行 BEFORE行级触发器

l         执行 DML语句

l         执行 AFTER行级触发器 

3.        执行 AFTER语句级触发器 

语句级和行级触发器见5

instead of不介绍了,详细可以到我转载的文章里看http://blog.csdn.net/asdsa108/article/details/50540221#t8

3.Event是触发事件,包括insert、update、delete,实际上还可以加上or进行连接,如insert or update

4.Table or view选择表或视图

5.Statement Level?该选项选择是语句级触发器还是行级触发器,介绍如下

行触发器要求当一个DML语句操作影响数据库中的多行数据时,对于其中的每个数据行,只要它们符合触发约束条件,均**一次触发器;而语句触发器将整个语句操作作为触发事件,当它符合约束条件时,**一次触发器。当省略FOR EACH ROW 选项时,BEFORE AFTER 触发器为语句触发器,而INSTEAD OF 触发器则只能为行触发器

Statement level总结:针对语句执行的则勾选,只触发一次,代码中没有For each row;针对语句操作的数据行则不勾选,每条受语句影响且符合触发条件的数据,都会触发一次触发器,代码中有For each row。

四、根据需求选好后,进入Sql语句框(没写完,后面给个例子好了)

随便找的例子:

[sql] view plain copy
  1. CREATE OR REPLACE TRIGGER tr_reg_cou  
  2. AFTER update OF region_id  
  3. ON regions  
  4. FOR EACH ROW  
  5. BEGIN  
  6.  DBMS_OUTPUT.PUT_LINE('旧的region_id值是'||:old.region_id  
  7.                   ||'、新的region_id值是'||:new.region_id);  
  8.  UPDATE countries SET region_id = :new.region_id  
  9.  WHERE region_id = :old.region_id;  
  10. END;  

想要取更改前后数据使用:old/new加上字段名,要注意old、new之前必须加冒号

最后F8运行,没问题的话触发器就开始运行了

延伸阅读:DML触发器相关知识

    触发器名与过程名和包的名字不一样,它是单独的名字空间,因而触发器名可以和表或过程有相同的名字,但在一个模式中触发器名不能相同。 

DML触发器的限制

l         CREATE TRIGGER语句文本的字符长度不能超过32KB

l         触发器体内的SELECT 语句只能为SELECT … INTO …结构,或者为定义游标所使用的SELECT 语句。

l         触发器中不能使用数据库事务控制语句 COMMIT; ROLLBACK, SVAEPOINT 语句;

l         由触发器所调用的过程或函数也不能使用数据库事务控制语句;

l         触发器中不能使用LONG, LONG RAW 类型;

l         触发器内可以参照LOB 类型列的列值,但不能通过 :NEW 修改LOB列中的数据; 

DML触发器基本要点

l         触发时机:指定触发器的触发时间。如果指定为BEFORE,则表示在执行DML操作之前触发,以便防止某些错误操作发生或实现某些业务规则;如果指定为AFTER,则表示在执行DML操作之后触发,以便记录该操作或做某些事后处理。

l         触发事件:引起触发器被触发的事件,即DML操作(INSERTUPDATEDELETE)。既可以是单个触发事件,也可以是多个触发事件的组合(只能使用OR逻辑组合,不能使用AND逻辑组合)。

l         条件谓词:当在触发器中包含多个触发事件(INSERTUPDATEDELETE)的组合时,为了分别针对不同的事件进行不同的处理,需要使用ORACLE提供的如下条件谓词。

1)。INSERTING当触发事件是INSERT时,取值为TRUE,否则为FALSE

2)。UPDATING [column_1,column_2,…,column_x]当触发事件是UPDATE      时,如果修改了column_x列,则取值为TRUE,否则为FALSE。其中column_x是可选的。

3)。DELETING当触发事件是DELETE时,则取值为TRUE,否则为FALSE

解发对象:指定触发器是创建在哪个表、视图上。

l         触发类型:是语句级还是行级触发器。

l         触发条件:WHEN子句指定一个逻辑表达式,只允许在行级触发器上指定触发条件,指定UPDATING后面的列的列表 

  问题:当触发器被触发时,要使用被插入、更新或删除的记录中的列值,有时要使用操作前、        后列的值.

  实现:  :NEW 修饰符访问操作完成后列的值

            :OLD 修饰符访问操作完成前列的值 

特性

INSERT

UPDATE

DELETE

OLD

NULL

实际值

实际值

NEW

实际值

实际值

NULL



出现的问题

当触发器触发条件是对某表的DML操作时,触发器不能对该表再进行DML操作

如触发条件是after update table,触发执行update table,则会报错【表table发生了变化,触发器/函数不能读它】

修改方法只能是触发执行update table2,因为触发的DML命令还没有commit执行完毕就不能执行触发器里的语句