PL/SQL程序之触发器

时间:2022-01-21 23:39:25
触发器
1、数据库触发器是一个与表相关联的、存储的PL/SQL程序。每当一个特定的数据操作语句(Insert,update,delete)在指定的表上发出时,Oracle自动地执行触发器中定义的语句序列。
2、触发器的类型
1)、语句级触发器
在指定的操作语句操作之前或之后执行一次,不管这条语句影响了多少行 。
2)、行级触发器(FOR EACH ROW)
触发语句作用的每一条记录都被触发。在行级触发器中使用old和new伪记录变量, 识别值的状态。
创建触发器:
   CREATE  [or REPLACE] TRIGGER  触发器名
   {BEFORE | AFTER}
   {DELETE | INSERT | UPDATE [OF 列名]}
   ON  表名
   [FOR EACH ROW [WHEN(条件) ] ]
   PLSQL 块

实例一:限制非工作时间向数据库中插入数据
构建触发器:
create or replace trigger insertEmp
  before insert on emp  
  for each row
declare
  -- local variables here
begin
  if to_char(sysdate,'day') in ('星期六') or to_number(to_char(sysdate,'hh24')) between 8 and 24
    then 
      raise_application_error(-20001,'星期六或者8-24不能插入数据');
      end if;
end insertEmp;
写sql语句触发
SQL> insert into emp(empno,deptno) values (1245,10);
结果:
insert into emp(empno,deptno) values (1245,10)
ORA-20001: 星期六或者8-24不能插入数据
ORA-06512: 在 "SCOTT.INSERTEMP", line 6
ORA-04088: 触发器 'SCOTT.INSERTEMP' 执行过程中出错

触发语句与伪记录变量的值
触发语句     :old                        :new
Insert		所有字段都是空话(null)		将要插入的数据
Update      更新以前该行的值            更新后的值
Delete       删除以前改行的值            所有字段都是空(null)

实例二:确认数据(检查emp表中sal的修改值不低于原值)
构建触发器
create or replace trigger updateEmp
  before update on emp  
  for each row
declare
  -- local variables here
begin
  if :new.sal<:old.sal then
    raise_application_error(-20002,'更改的数据不能小于原有的值');
    end if;
end updateEmp;
书写sql语句触发
SQL> update emp set sal=100 where empno=7369;
结果:
update emp set sal=100 where empno=7369
ORA-20002: 更改的数据不能小于原原有的值
ORA-06512: 在 "SCOTT.UPDATEEMP", line 5
ORA-04088: 触发器 'SCOTT.UPDATEEMP' 执行过程中出错

练习:限制每个部门只招聘5名职工,超过计划则报出错误报告
构建触发器
create or replace trigger insertEmp
  before insert on emp  
  for each row
declare
  -- local variables here
  cursor c1 is select count(*) from emp group by deptno;
  count1 number;
begin
  open c1;
  fetch c1 into count1;
   if 
     count1>=5
   then
     raise_application_error(-20003,'本部门不能再插入了');
   end if;
   
   --  dbms_output.put_line(count1);
    close c1;
end insertEmp;
书写sql语句触发:
SQL> insert into emp (empno,deptno) values(2435,30);
结果:
insert into emp (empno,deptno) values(2435,30)
ORA-20003: 本部门不能再插入了
ORA-06512: 在 "SCOTT.INSERTEMP", line 11
ORA-04088: 触发器 'SCOTT.INSERTEMP' 执行过程中出错

触发器总结:
1、	触发器可用于
a)	数据确认  
b)	实施复杂的安全性检查
c)   做审计,跟踪表上所做的数据操作等
2、	查询触发器、过程及函数
a)	Select * from user_triggers;
b)	Select * from user_source;