近来在自学PLSQL,接触时间尚浅,写了一个维护SCOTT名下dept表的触发器和存储过程.就当练习了.欢迎大牛们指出缺点.
这是维护表的表结构
create table dept_history(
id number primary key,
deptno number(4),
dname varchar2(14),
loc varchar2(13));
删除时的触发器:
create or replace trigger add_dept_his
before delete on dept
for each row
declare
begin
insert into dept_history values (dept_his_seq.nextval,:old.deptno,:old.dname,:old.loc);
end;
恢复表中所有数据的存储过程:
create or replace procedure back_all_dept as
cursor his_cursor is select * from dept_history;
type his_list is table of dept_history%rowtype;
hisl his_list;
begin
open his_cursor;
fetch his_cursor bulk collect into hisl;
close his_cursor;
for i in hisl.first..hisl.last loop
insert into dept values(hisl(i).deptno,hisl(i).dname,hisl(i).loc);
dbms_output.put_line(hisl(i).deptno||' 编号的数据已经恢复');
delete from dept_history where id=hisl(i).id;
end loop;
end;
下面是根据条件恢复数据的存储过程:
/*此方法用于维护dept表中的数据恢复,可以根据dept_history的id来恢复,
也可以根据dname,deptno,loc 来恢复 格式如下:
exec back_dept_bydata(null,null,null,'PHOENIX');
其他情况类似于.如果有多种查询条件,则只按照先后顺序进行查询,不满足条件则退出.
*/
create or replace procedure back_dept_bydata(
his_id in dept_history.id%type,
his_name in dept_history.dname%type,
his_no in dept_history.deptno%type,
his_loc in dept_history.loc%type
) is
type his_list is table of dept_history%rowtype;
hisl his_list;
procedure re_back_all(hisll in his_list) is
back_state boolean :=false;
begin
if hisll.count<>0 then
back_state:=true;--结果集中是否有数据,如果有,则表示有更新.
for i in hisll.first..hisll.last loop
dbms_output.put_line(hisll(i).dname||' 已经恢复完毕');
insert into dept values(hisll(i).deptno,hisll(i).dname,hisll(i).loc);
delete from dept_history where dept_history.id=hisll(i).id;
end loop;
end if;
if not back_state then dbms_output.put_line(' 无数据匹配'); end if;--如果没有找到数据则打印
end;
begin
--判断参数id是否为空值.
if his_id is not null then
select * bulk collect into hisl from dept_history where dept_history.id=his_id;
re_back_all(hisl);
--判断his_name是否为空
elsif his_name is not null then
select * bulk collect into hisl from dept_history where dept_history.dname=his_name;
re_back_all(hisl);
--判断his_no是否为空
elsif his_no is not null then
select * bulk collect into hisl from dept_history where dept_history.deptno=his_no;
re_back_all(hisl);
--判断his_loc是否为空
elsif his_loc is not null then
select * bulk collect into hisl from dept_history where dept_history.loc=his_loc;
re_back_all(hisl);
end if;
end;
欢迎大家指正.
|