Oracle LogMiner 是Oracle公司从产品8i以后提供的一个实际非常有用的分析工具,使用该工具可以轻松获得Oracle 重作日志文件(归档日志文件)中的具体内容,特别是,该工具可以分析出所有对于数据库操作的DML(insert、update、delete等)语句,另外还可分析得到一些必要的回滚SQL语句。该工具特别适用于调试、审计或者回退某个特定的事务。
LogMiner 分析工具实际上是由一组PL/SQL包和一些动态视图(Oracle8i内置包的一部分)组成,它作为Oracle数据库的一部分来发布,是8i产品提供的一个完全免费的工具。但该工具和其他Oracle内建工具相比使用起来显得有些复杂,主要原因是该工具没有提供任何的图形用户界面(GUI)。本文将详细介绍如何安装以及使用该工具。
日志文件中存放着所有进行数据库恢复的数据,记录了针对数据库结构的每一个变化,也就是对数据库操作的所有DML语句。
在Oracle 8i之前,Oracle没有提供任何协助数据库管理员来读取和解释重作日志文件内容的工具。系统出现问题,对于一个普通的数据管理员来讲,唯一可以作的工作就是将所有的log文件打包,然后发给Oracle公司的技术支持,然后静静地等待Oracle 公司技术支持给我们最后的答案。然而从8i以后,Oracle提供了这样一个强有力的工具-LogMiner。
LogMiner 工具即可以用来分析在线,也可以用来分析离线日志文件,即可以分析本身自己数据库的重作日志文件,也可以用来分析其他数据库的重作日志文件。
总的说来,LogMiner工具的主要用途有:
1. 跟踪数据库的变化:可以离线的跟踪数据库的变化,而不会影响在线系统的性能。
2. 回退数据库的变化:回退特定的变化数据,减少point-in-time recovery的执行。
3. 优化和扩容计划:可通过分析日志文件中的数据以分析数据增长模式。
一:安装
1、创建DBMS_LOGMNR包
@D:\oracle\ora92\rdbms\admin\dbmslm.sql;
--指定日志文件名
--指定筛选标准
--确定LodMiner会话特性
2、创建DBMS_LOGMNR_D包
@D:\oracle\ora92\rdbms\admin\dbmslmd.sql;
--该包用来创建数据字典文件
--查询当前数据库的字典表
二、提取字典
1、提取到平面文件
必须在启动文件中指定UTL_FILE_DIR参数,以放置字典文件的目录
执行 DBMS_LOGMNR_D.BUILD('dictionary.ora', 'D:/oracle/logminer', options => DBMS_LOGMNR_D.STORE_IN_FLAT_FILE); 来创建平面文件
< 注:不加STORE_IN_FLAT_FILE也可,因为有地址的默认均是FLAT_FILE >
2、提取到重做日志文件
DBMS_LOGMNR_D.BUILD(options => DBMS_LOGMNR_D.STORE_IN_REDO_LOGS);
< 注:要提取到重做日志文件时,数据库必须要运行在ARCHIVELOG模式下 >
三、指定要分析的重做日志文件
1、通过NEW来创建重做日志文件的列表
DBMS_LOGMNR.ADD_LOGFILE(LOGFILENAME => 'D:\oracle\oradata\kaka\redo01.log', options => DBMS_LOGMNR.NEW);
--若再次NEW时,则前面的记录全部丢弃
2、通过ADDFILE来添加更多的重做日志文件
DBMS_LOGMNR.ADD_LOGFILE(LOGFILENAME => 'D:\oracle\oradata\kaka\redo02.log', options => DBMS_LOGMNR.ADDFILE);
3、通过REMOVEFILE来删除列表中的重做日志文件
DBMS_LOGMNR.ADD_LOGFILE(LOGFILENAME => 'D:\oracle\oradata\kaka\redo02.log', options => DBMS_LOGMNR.REMOVEFILE);
四、启动LogMiner
使用DBMS_LOGMNR.START_LOGMNR()来启动LogMiner
1、指定数据字典
DBMS_LOGMNR.START_LOGMNR(DICTFILENAME => 'D:/oracle/logminer/dictionary.ora');
重做日志:DICT_FROM_REDO_LOGS
联机字典:DICT_FROM_ONLINE_CATALOG
2、可以指定时间筛选
DBMS_LOGMNR.START_LOGMNR(DICTFILENAME => 'D:/oracle/logminer/dictionary.ora', STARTTIME => TO_DATE('2008-12-15 08:30:00', 'YYYY-MM-DD HH24:MI:SS'), ENDTIME => TO_DATE('2008-12-15 17:30:00', 'YYYY-MM-DD HH24:MI:SS'));
3、使用SCN判断时间
DBMS_LOGMNR.START_LOGMNR(DICTFILENAME => 'D:/oracle/logminer/dictionary.ora', STARTSCN => 100, ENDSCN => 150);
4、使用OPTIONS参数设置以下特性:
① COMMITTED_DATA_ONLY:只显示已提交事务的行
这个特性可以筛选出回滚事务以及进程中事务,但是若事务长时间运行,将引起“Out of Memory”错误
② SKIP_CORRUPTION:跳过重做日志损坏的地方
对于每个受损坏的记录,都会返回一行信息指出跳过多少块,若第1个信息就损坏则中断操作
③ DDL_DICT_TRACKING:使用平面/重做日志数据字典时保持更新
确保了SQL_REDO和SQL_UNDO的正确性,但对于DICT_FROM_RESET_ONSELECT无效
④ NO_DICT_RESET_ONSELECT:在查询V$LOGMNR_CONTENTS时避免重载数据字典
这个指令与DDL_DICT_TRACKING正好相反,但是优先级大于DDL_DICT_TRACKING
⑤ DICT_FROM_ONLINE_CATALOG:采用数据库当前使用的字典
这个指令优先级小于DDL_DICT_TRACKING,若设置了那个则这个无效
⑥ DICT_FROM_REDO_LOGS:在重做日志文件列表中找到一个字典
这个特性有利于分析某一特定时间内的数据
多个特性列表的举例:
DBMS_LOGMNR.START_LOGMNR(OPTIONS => DBMS_LOGMNR.DDL_DICT_TRACKING + DBMS_LOGMNR.NODICT_RESET_ONSELECT + ...);
五、分析V$LOGMNR_CONTENTS的输出
使用SQL查询V$LOGMNR_CONTENTS视图,会从重做日志文件中依次获得记录返回,直到满足启动时指定的筛选标准,或重做日志结束。 除非使用了COMMITTED_DATA_ONLY,否则LogMiner将按SCN返回所有行。
举例说明SELECT V$LOGMNR_CONTENTS的性质:
第一次查询:SELECT SQL_REDO FROM V$LOGMNR_CONTENTS;
SQL_REDO
-----------------------------------------------------------------------------------------------
create table scott.t1(id int,name varchar2(30),mark varchar2(100));
insert into "SCOTT"."T1"("ID","NAME","MARK") vlues (10,'bob','aaaaa');
insert into "SCOTT"."T1"("ID","NAME","MARK") vlues (11,'tom','bbbbb');
commit;
alter table scott.t1 drop(mark);
insert into "SCOTT"."T1"("ID","NAME") vlues (12,'jac');
commit;
此时在内部的数据字典中,由于执行了drop,内部字典已经没有了mark列,若设置了NO_DICT_RESET_ONSELECT,则会出现以下情况:
第二次查询:SELECT SQL_REDO FROM V$LOGMNR_CONTENTS;
SQL_REDO
-----------------------------------------------------------------------------------------------
create table scott.t1(id int,name varchar2(30),mark varchar2(100));
insert into "SCOTT"."T1"("COL 1","COL 2","COL 3") vlues (HEXTORAW('78fes78r'),HEXTORAW('vtf43tf4'),HEXTORAW('32f4eff8'));
insert into "SCOTT"."T1"("COL 1","COL 2","COL 3") vlues (HEXTORAW('4gf3revw'),HEXTORAW('32frdsf3'),HEXTORAW('b432cer3'));
commit;
alter table scott.t1 drop(mark);
insert into "SCOTT"."T1"("ID","NAME") vlues (12,'jac');
commit;
前面两个insert语句因为字典中缺少了mark列,所以要使用COL 和 HEXTORAW
所以:若需要多次查询,则不可以设置NO_DICT_RESET_ONSELECT
六、结束LogMiner
DBMS_LOGMNR.END_LOGMNR;
① 当使用该语句时,将关闭所有日志文件,并释放所有LogMiner分配的数据库和系统资源。
② 若没有使用该语句,则会保持分配的资源直到启动LogMiner的会话结束。
③ 若使用了DDL_DICT_TRACKING或DICT_FROM_REDO_LOGS选项,则务必要使用该语句,否则会造成系统资源的浪费。