DML ERROR LOGGING總結

litterbaby發表於2007-05-12

DML ERROR LOGGING總結

總結:康標

email

[@more@]

DML ERROR LOGGING總結

總結:康標

email

為什麼要使用DML ERROR LOGGING

Oracle 10之前執行一些大規模的操作的時候,尤其是一些長時間bulk DML操作的時候,會發現如果在執行過程中如果有一行發生錯誤的時候,就會放棄這個DML操作而回滾。這樣的話就會浪費大量的時間和系統資源。是不是能有一種途徑使得在執行bulk DML操作,將成功的部分插入到表中,而將未能正確插入的部分的錯誤插入到其他表中,以後來處理。

Oracle 10g release 2:中引入了一個特性:DML ERROR LOGGING這個特性就能夠實現以上的功能。

新增一個ERROR-LOGGING

新增ERROR-LOGGING表需要使用的是包DBMS_ERRLOG這個包。這個表在Oracle 10g中只有一個過程:CREATE_ERROR_LOG

DBMS_ERRLOG.CREATE_ERROR_LOG (

dml_table_name IN VARCHAR2,

err_log_table_name IN VARCHAR2 := NULL,

err_log_table_owner IN VARCHAR2 := NULL,

err_log_table_space IN VARCHAR2 := NULL,

skip_unsupported IN BOOLEAN := FALSE);

這裡指定的有兩個表名,一個是DML處理的表名。一個是建立這個ERROR-LOGGING表名。

建立一個表:

SQL> create table dml(a varchar2(2) primary key,b varchar2(1));

表已建立。

建立一個ERROR LOGGING

SQL> exec dbms_errlog.create_error_log('DML','DML_LOG');

PL/SQL 過程已成功完成。

看看這個表都是有什麼?

SQL> desc dml_log

名稱 是否為空? 型別

----------------------------------------- -------- -----------------

ORA_ERR_NUMBER$ NUMBER

ORA_ERR_MESG$ VARCHAR2(2000)

ORA_ERR_ROWID$ ROWID

ORA_ERR_OPTYP$ VARCHAR2(2)

ORA_ERR_TAG$ VARCHAR2(2000)

A VARCHAR2(4000)

B VARCHAR2(4000)

這時候會發現這個表中有兩部分:

固定部分:

ORA_ERR_NUMBER$ NUMBER

ORA_ERR_MESG$ VARCHAR2(2000)

ORA_ERR_ROWID$ ROWID

ORA_ERR_OPTYP$ VARCHAR2(2)

ORA_ERR_TAG$ VARCHAR2(2000)

ORA_ERR_NUMBER$

Oracle的錯誤號。

ORA_ERR_MESG$

Oracle錯誤資訊文字。

ORA_ERR_ROWID$

Oracle的錯誤行ROWID。(UPDATEDELETE

ORA_ERR_OPTYP$

操作型別(INSERT UPDATE/DELETE

ORA_ERR_TAG$

使用者支援標籤

可變部分:

A VARCHAR2(4000)

B VARCHAR2(4000)

使用方法:

使用方法其實很簡單。

LOG ERRORS [INTO schema.table] [ (simple_expression) [ REJECT LIMIT {integer|UNLIMITED} ]

看看錯誤的產生:

SQL> insert into dml select rownum,rownum from all_objects where rownum < 11;

insert into dml select rownum,rownum from all_objects where rownum < 11

*

1 行出現錯誤:

ORA-12899: "TEST"."DML"."B" 的值太大 (實際值: 2, 最大值: 1)

SQL> select * from dml;

未選定行

如果這樣使用看看效果。

SQL> insert into dml

2 select rownum,rownum from all_objects where rownum < 11

3 log errors into dml_log ('my_log') reject limit 10;

已建立9行。

沒有出現問題,看看log表中都是什麼東西:

SQL> select * from dml_log;

ORA_ERR_NUMBER$ ORA_ERR_MESG$ ORA_ERR_ROWID$ ORA_ERR_OPTYP$ ORA_ERR_TAG$ A B

--------------- -------------------------------------------------------------------------------- -------------------------------------------------------------------------------- -------------- -------------------------------------------------------------------------------- -------------------------------------------------------------------------------- --------------------------------------------------------------------------------

12899 ORA-12899: "TEST"."DML"."B" 的值太大 (實際值: 2, 最大值: 1) I my_log 10 10

這裡面會發現存放著錯誤的資訊。已經錯誤發生的值。

需要注意的問題:

1、所有型別的DML操作都能夠被記錄在日誌中。

2、每一個ERROR LOGGING表對於一個特定的操作表。兩種表之間是一一對應的。不能被混用。

3、被記錄的型別是:

值太大。

約束問題

由觸發器產生的錯誤

型別轉換

分割槽對映

4LONG/CLOB/BLOB/BFILE/ADTs不能為error-logging表的一部分。

5、多次重複出現錯誤的時候,資訊會被重複記錄在表中,需要在執行之前刪除表。

SQL> insert into dml

2 select rownum,rownum from all_objects where rownum < 11

3 log errors into dml_log ('my_log') reject limit 10;

已建立0行。

SQL> select count(*) from dml_log;

COUNT(*)

----------

11

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

相關文章