分析Oracle資料庫日誌檔案(3)

kitesky發表於2005-06-02
作為Oracle DBA,我們有時候需要追蹤資料誤刪除或使用者的惡意操作情況,此時我們不僅需要查出執行這些操作的資料庫賬號,還需要知道操作是由哪臺客戶端(IP地址等)發出的。針對這些問題,一個最有效實用而又低成本的方法就是分析Oracle資料庫的日誌檔案。本文將就Oracle日誌分析技術做深入探討。[@more@]四、如何利用LogMiner分析Oracle8的日誌檔案

雖然說LogMiner是Oracle8i才推出來,但我們同樣可以用它來分析Oracle8的日誌檔案,只不過稍微麻煩了一點,並且有一定的限制,下面是具體做法:

我們首先複製Oracle8i的$ORACLE_HOME/rdbms/admin/dbmslmd.sql指令碼到Oracle8資料庫所在主機的同樣目錄;這個指令碼用於建立dbms_logmnr_d包(注意,Oracle9i中還將建立dbms_logmnr包),如果是8.1.5指令碼名字為dbmslogmnrd.sql。然後在Oracle8的資料庫上執行這個指令碼,之後使用dbms_logmnr_d.build過程建立字典資訊檔案。現在我們就可以把Oracle8的歸檔日誌連同這個字典資訊檔案複製到Oracle8i資料庫所在的主機上,之後在Oracle8i資料庫中從上面分析過程的第三步開始分析Oracle8的日誌,不過

dbms_logmnr.start_logmnr()中使用的是Oracle8的字典資訊檔案。

按照我前面所說的那樣,如果不是字典檔案,我們則可以直接將Oracle8的歸檔日誌複製到Oracle8i資料庫所在主機,然後對它進行分析。

其實這裡涉及到了一個跨平臺使用LogMiner的問題,筆者做過試驗,也可以在Oracle9i中來分析Oracle8i的日誌。但這些都是有所限制的,主要表現在:

1、LogMiner所使用的字典檔案必須和所分析的日誌檔案是同一個資料庫所產生的,並且該資料庫的字符集應和執行LogMiner資料庫的相同。這很好理解,如果不是同一個資料庫所產生就不存在對應關係了。

2、生成日誌的資料庫硬體平臺和執行LogMiner資料庫的硬體平臺要求一致,作業系統版本可以不一致。筆者做試驗時(如果讀者有興趣可以到我網站上下載試驗全過程,因為太長就不放在這裡了),所用的兩個資料庫作業系統都是Tru64 UNIX,但一個是 V5.1A,另一個則是V4.0F。如果作業系統不一致則會出現下面的錯誤:

ORA-01284: file /data6/cyx/logmnr/arch_1_163570.arc cannot be opened
ORA-00308: cannot open archived log '/data6/cyx/logmnr/arch_1_163570.arc'
ORA-27048: skgfifi: file header information is invalid
ORA-06512: at "SYS.DBMS_LOGMNR", line 63
ORA-06512: at line 1


五、分析v$logmnr_contents

前面我們已經知道了LogMiner的分析結果是放在v$logmnr_contents中,這裡面有很多資訊,我們可以根據需要追蹤我們感興趣的資訊。那麼我們通常感興趣的有哪些呢?

1、追蹤資料庫結構變化情況,即DDL操作,如前所述,這個只有Oracle9i才支援:

SQL> select timestamp,sql_redo from v$logmnr_contents2 
where upper(sql_redo) like '%CREATE%';
TIMESTAMP
-------------------
SQL_REDO
-------------------------
2003-09-21 10:01:55
create table t (c1 number);


2、追蹤使用者誤操作或惡意操作:

例如我們現實中有這樣需求,有一次我們發現一位員工透過程式修改了業務資料庫資訊,把部分電話的收費型別改成免費了,現在就要求我們從資料庫中查出到底是誰幹的這件事?怎麼查?LogMiner提供了我們分析日誌檔案的手段,其中v$logmnr_contents的SESSION_INFO列包含了下面的資訊:

login_username=NEW_97 
client_info= OS_username=oracle8 Machine_name=phoenix1
 OS_terminal=ttyp3 OS_process_id=8004 OS_program name=sqlplus@phoenix1
 (TNS V1-V3)


雖然其中資訊已經很多了,但在我們的業務資料庫中,程式是透過相同的login_username登入資料庫的,這樣單從上面的資訊是很難判斷的。

不過我們注意到,因為公司應用伺服器不是每個人都有許可權在上面寫程式的,一般惡意程式都是直接透過他自己的PC連到資料庫的,這就需要一個準確的定位。IP追蹤是我們首先想到的,並且也滿足我們的實際要求,因為公司內部IP地址分配是統一管理的,能追蹤到IP地址我們就可以準確定位了。但從面的SESSION_INFO中我們並不能直接看到IP,不過我們還是有辦法的,因為這個SESSION_INFO裡面的內容其實是日誌從V$SESSION檢視裡提取的,我們可以在生產資料庫中建立一個追蹤客戶端IP地址的觸發器:

create or replace trigger on_logon_trigger
after logon on database
begin
  dbms_application_info.set_client_info(sys_context('userenv', 'ip_address'));
end;
/


現在,我們就可以在V$SESSION檢視的CLIENT_INFO列中看到新登入的客戶端IP地址了。那麼上面的提出的問題就可以迎刃而解了。假如被更新的表名為HMLX,我們就可以透過下面的SQL來找到所需資訊:

SQL > select session_info ,sql_redo from v$logmnr_contents 
2 where upper(operation) = 'UPDATE'  and upper(sql_redo) like '%HMLX%'
3 /
SESSION_INFO
-----------------------------------------
SQL_REDO
-----------------------------------------
login_username=C client_info=10.16.98.26 OS_username=sz-xjs-chengyx Machine_name
=GDTELSZ-XJS-CHENGYX
update "C"."HMLX" set "NAME" = 'free' where "NAME" = 'ncn.cn' and ROWID = 'AAABhTAA
FAAABRaAAE';


(完)

來自 “ ITPUB部落格 ” ,連結:http://blog.itpub.net/66009/viewspace-799631/,如需轉載,請註明出處,否則將追究法律責任。

相關文章