首页 > 代码库 > Oracle 触发器在日志管理开发中的应用

Oracle 触发器在日志管理开发中的应用

摘要: 本文讨论了利用数据库中的触发器对日志管理进行设计与实现的方法, 是对原来在客户端软件中编写日志管理方法的一种
改进, 并给出了 Oracle9i 中的实例演示。
关键词: Oracle; 触发器; 日志管理
中图分类号: TP311
文献标识码: A
文章编号: 1009- 3044(2008)16- 21186- 02
The Application of Oracle Trigger in the Developing of Log Management
WU Heng- liang, ZHANG Wei- wei
(Shandong Business Colloge,Management Science and Engineering Institute,Yantai 264005,China)
Abstract:This article describes a new developing method of log management by the trigger of data base, that is an improvement to the o-
riginal method of writing log management in the client software, and the article gives the example of application in Oracle9i.
Key words:Oracle; trigger; log management
1 引言
日志对于安全来说非常重要, 它记录了系统每天发生的各种各样的事情。日志主要的功能有: 审计和监测。一方面可以通过它
来检查错误发生的原因, 或者受到攻击时攻击者留下的痕迹。另一方面还可以实时的监测系统状态, 监测和追踪侵入者等等。
在每一个企业管理信息系统软件的开发过程中, 一般都会涉及到日志管理模块, 因为每个软件都有各种操作权限的操作人员
从事其权限范围内的操作, 我们必须记录下这些操作的全部历史记录, 对监测系统运行状态, 为事后监督提供直接依据, 对防范系
统安全有重要作用。
在开发 C/S 或 B/S 模式的系统软件时, 日志管理的一般方法是在客户端(C/S) 或应用服务器(B/S) 上对每个功能模块编写日志
处理子模块, 这种方法编程量比较大, 开发效率低, 维护起来也比较繁琐。本文试图采用数据库中的触发器编程, 把日志管理全部或
部分转到数据库中, 对比前一种方法可以大大减少编程代码, 降低开发的工作量。
2 触发器介绍
对表中数据进行修改、删除或插入是非常常见的操作, 当表被修改时, 应该自动给其他需要执行操作的程序发信号。触发器可
以完成这一功能, 触发器是存储在数据库中的一个与数据表相关联的存储过程, 当发生 insert、update 或 delete 操作时被自动执行,
与一般存储过程的调用方法不同, 当某事件的发生引起连环更新或其它的相应操作时, 通过自动执行触发器代码实现而不用人工
干预, 大大减轻了维护工作, 同时也很好地保证了数据的一致性。
触发器的优点是自动激发, 不管是什么引起数据修改( 来自程序的或是来自用户的) , 它们都工作, 所以常常用于不同数据表中
的相关数据的串接修改。采用这种方法实现数据表间接的数据关联, 可以由数据库集中维护控制, 规则变化时只需修改相应的触发
器即可, 这样系统易于维护, 提高了工作效率。
本文的基本思想就是利用了这一点, 在客户端软件每次发出对表的这些操作时自动触发触发器, 实现日志的记录。在各种
RDBMS 中基本都提供了这种程序, 本文以 Oracle9i 为例介绍触发器的使用方法。
在 Oracle9i 中, 触发器就是 PL/SQL 的一种编程结构。下文将简单介绍一下触发器的使用方法。
2.1 建立触发器的主要语法
create [or replace] trigger trigger_name {before|after}event
on {table | view |database}
[for each row[when condition]]
trigger_body
注释:
trigger_name: 触发器的名字;
event: 为 insert、update、delete 或 update of 列名 1,列名 2?;
on {table | view |database}: 触发器的触发对象( 表、视图或数据库) ;
[for each row]: 可选项, 使用这个选项时, 对每条相应行将引起触发器触发;
trigger_body: 触发器触发时执行的 PL/SQL 块。
2.2 触发器的主要应用
收稿日期: 2008- 04- 17
作者简介: 吴恒亮(1978- ) , 男, 山东莱芜人, 山东工商学院讲师, 硕士, 研究方向为管理信息系统、电子商务、数据仓库和数据挖掘
等; 张巍巍(1978- ) , 女( 满族) , 辽宁丹东人, 山东工商学院讲师, 硕士, 研究方向为工程管理、数据仓库和数据挖掘等。
1186
数据库与信息管理
(1) 实施表的完整性限制, 比如设置数据表的约束条件、参照完整性等。特别是对那些在表创建阶段通过声明限制无法实现的
复杂的安全性、完整性限制, 比如限制用户的访问时间等等;
(2) 实现表操作的前处理与后处理, 比如表的内容发生变更时, 给其它需要运行的程序发信号, 采取相应的处理;
(3) 实现跨节点表的同步更新, 维护同步表的复制;
(4) 应用于审计, 可以跟踪表上所实施的数据操作, 通过记录修改内容和修改者来审计表中的信息;
(5) 自动生成派生列的值, 实现自动获得列值的功能;
(6) 透明的记录事件, 提供透明的事件日志。
3 触发器在日志管理中的实现
下面的日志管理的实现方法, 就是利用了上文提到的触发器的第四个主要应用, 基本思想是在数据库中对需要做日志的数据
表分别建立一个触发器, 该触发器记录此时客户端的操作员、操作对象、操作时间、操作动作等。当在客户端程序中只要涉及到 in-
sert、update 或 delete 等操作时就触发该触发器, 从而实现日志管理。这种方法避免了程序员在客户端或中间服务器应用程序的每个
模块中编写很多重复的程序代码, 在数据库中建立的触发器代码较少, 也比较简单、类似, 编写、维护都比较省时省力。
下面将以 Oracle9i 提供的示例用户 scott 的 emp 表为例, 通过建立触发器来实现对该数据表的日志管理, 对客户端发出的各种
操作进行记录。具体步骤如下:
步骤一: 建立所需要的数据表。
首先要创建两个表 emp_log 和 cur_user。其中, emp_log 表用于记录操作日志; cur_user 表记录操作客户端软件的当前用户。
需要说明一下, 为了在数据库的触发器中能够访问到客户端软件的当前用户, 需要在客户端软件的登录窗口中编写代码, 记录
当前登录到系统的用户, 并存入 cur_user 表, 在触发器中就可以通过访问 cur_user 表实现在服务器端的数据库中对客户端当前用户
的访问, 当然大家可以尝试其它方法。代码如下:
- - 创建用户对数据表 emp 的操作日志表 emp_log
create table scott.emp_log(
user_name varchar2(10),
- - 操作员
opera_time date,
- - 操作时间
operator varchar2(8),
- - 操作动作
opera_obj varchar2(20)
- - 操作对象
);
- - 创建记录客户端软件的当前用户的数据表 cur_user
create table scott.cur_user(
userid varchar2(6),
- - 操作员标志
username varchar2(10) - - 当前操作员
);
步骤二: 为用户 scott 建立一个函数 get_operator( ), 从 cur_user 表中取出正在操作客户端软件的当前用户。
create or replace function scott.get_operator
return varchar
as
v_operator scott.cur_user.username%type;
begin
select username into v_operator
from scott.cur_user;
- - cur_user 表中最多只有一条记录
return(v_operator);
- - 返回当前用户
end get_operator;
步骤三: 为 scott 用户的 emp 表建立触发器。
create or replace trigger scott.operator_emp
after insert or delete or update
on scott.emp
for each row - - 行级
declare
v_user scott.cur_user.username%type;
begin
v_user:=scott.get_operator(); - - 获得当前操作员
if inserting then
- - 插入操作
insert into scott.emp_log(user_name,opera_time,operator,opera_obj)
values(v_user,sysdate,‘ 插入 ‘,‘emp 表 ‘);
elsif updating then
- - 更新操作
insert into scott.emp_log(user_name,opera_time,operator,opera_obj)
values(v_user,sysdate,‘ 更新 ‘,‘emp 表 ‘);
elsif deleting then
- - 删除操作
( 下转第 1266 页)
1187
谢媛媛
软件设计开发
⑵若标示卡无效 (过期或不是本停车场卡), 系统通过视觉和声音报警, LED 提示牌根据错误原因提示以下内容: “卡已过期”、
“非本场卡”, 持续 30 秒后自动清除, 控制道闸不抬起, 这时保安可通过内部通话系统与管理中心联系, 及时处理。
道闸抬起后, 中心控制系统自动保存入场车辆信息(进场时间、卡号、图像等), 车辆通过道闸时, 系统启动防砸车检测装置, 防止
砸车, 车辆通过道闸, 自动关闭道闸。
车辆到达出口时, 系统通过读取 RFID 卡的信息自动识别卡号。通过内部数据库里的信息检索, 查到相应的车辆记录。界面显示
出记录提供的用户类型、车牌号码、车辆照片, 以及动态提供的出场时间。同时通过摄像头再次抓拍车辆照片。系统并排显示车辆原
始照片和当前照片, 并醒目地显示车牌号, 以便员工进行核对数验。非法用户系统将报警提示。
临时用户缴付停车费用后, 归还 ID 卡, 然后出口道闸启动(如图 3), 用户可以出场。
固定用户系统自动判断账户内余额, 自动刷去相应停车费用, 然后允许出场。如果余额不足则系统报
警, 用户可以选择续费或停回。
4 结束语
射频识别系统在不停车收费系统中的应用, 实现了不停车自动缴费、免现金、免找赎、与银行联网结
算、货币电子化、高效的智能化收费管理, 解决了因停车交费而产生的交通堵塞、资源浪费、空气污染以及
资金失控等问题。
参考文献:
[1] 游战清,李苏剑.无线射频识别技术(RFID)理论与应用[M].北京:电子工业出版社,2004.
[2] 陈大才.射频识别(RFID)技术[M].北京:电子工业出版社社,2001.
[3] 杜丽丽,曹虎山,杨化庭.基于射频识别(RFID)技术的门禁管理系统的研究[J].北京工商大学学报,2003,12.
图 3
停车场出口流程
( 上接第 1187 页)
insert into scott.emp_log(user_name,opera_time,operator,opera_obj)
values(v_user,sysdate,‘ 删除 ‘,‘emp 表 ‘);
else
- - 其他操作
insert into scott.emp_log(user_name,opera_time,operator,opera_obj)
values(v_user,sysdate,‘ 其他 ‘,‘emp 表 ‘);
end if;
end;
说明: 本触发器在客户端程序对 scott.emp 表执行 insert、update 或 delete 之后触发, 其中利用了触发器的 inserting、updating 和
deleting 三个谓词来帮助判断执行的是哪种操作(insert、update 或 delete) 。
步骤四: 在 Oracle9i 的 SQL Worksheet 中测试触发器。
set serveroutput on
declare
cursor c_emp
is select user_name,opera_time,operator,opera_obj from scott.emp_log;
begin
- - 触发 scott.operator_emp 触发器( 一个 insert、update 和两个 delete 操作)
insert into scott.emp(empno,ename,job) values(1209,‘ 王刚 ‘,‘ 销售员 ‘);
delete from scott.emp
where empno=1167;
delete from scott.emp
where empno=1168;
update scott.emp set job=‘ 销售主管 ‘ where empno=1189;
commit;
- - 生效
for r_emp in c_emp loop
- - 输出操作日志 emp_log
dbms_output.put_line(‘ 用户名: ‘||r_emp.user_name);
dbms_output.put_line(‘ 操作时间: ‘||r_emp.opera_time);
dbms_output.put_line(‘ 执行操作: ‘||r_emp.operator);
dbms_output.put_line(‘ 操作对象: ‘||r_emp.opera_obj);
end loop;
end;
4 结束语
本文给出了一个比较简单的日志管理的演示实例, 所做的操作记录还不够完整。如果需要更详细的日志, 可以利用触发器的标
识符(:old 和:new) , 记录用户插入(insert) 的新记录、删除(delete) 的旧记录或修改(update) 某些字段的前后值的变化, 本文不再赘述。