首頁
編程語言
C語言|JAVA編程
Python編程
網頁編程
ASP編程|PHP編程
JSP編程
數據庫
MYSQL數據庫|SqlServer數據庫
Oracle數據庫|DB2數據庫
您现在的位置: 程式碼之家 >> 數據庫知識 >  >> Oracle 資料庫 >> Oracle 資料庫基礎

Oracle 存儲過程測試與日誌記錄最佳實踐:自建包 vs Log4plsql

     編輯:Oracle 資料庫基礎

方案一:自建測試日誌包 (PKG_Test_Info)

核心物件

  • 日誌表 TESTINFOLOG + 序列 SEQ_TestInfoLog。
  • Package PKG_Test_Info 提供:
    • SET_LOG_CONTEXT(context, program, level):設定測試上下文。
    • LOG_INFO(msg):寫入訊息。
    • CLEAR_ALL_LOG_INFO:清空緩衝/表。

使用範例

-- 匿名區塊
DECLARE
  i INTEGER := 1;
BEGIN
  PKG_Test_Info.CLEAR_ALL_LOG_INFO;
  PKG_Test_Info.SET_LOG_CONTEXT('匿名區塊測試', '無', 1);
  PKG_Test_Info.LOG_INFO('i=1');
  PKG_Test_Info.LOG_INFO('當前日期=' || TO_CHAR(SYSDATE, 'YYYY-MM-DD'));
END;
/

-- 存儲過程中嵌入
CREATE OR REPLACE PROCEDURE Test_PKG_Test_Info(p_Param1 INT, p_Param2 INT, p_Log_Flag INT DEFAULT 1) IS
BEGIN
  IF p_Log_Flag = 1 THEN
    PKG_Test_Info.CLEAR_ALL_LOG_INFO;
    PKG_Test_Info.SET_LOG_CONTEXT('存儲過程測試', 'Test_PKG_Test_Info', 1);
    PKG_Test_Info.LOG_INFO('p_Param1=' || TO_CHAR(p_Param1) || ', p_Param2=' || TO_CHAR(p_Param2));
  END IF;
END;
/

方案二:Log4plsql (Open Source, 移植自 Log4j)

專案地址:https://log4plsql.sourceforge.net/

核心優勢:

  • 分級日誌 (DEBUG, INFO, WARN, ERROR, FATAL)。
  • ASSERT(condition, msg) 斷言機制,條件失效自動記錄並可選拋出異常。
  • 支援樹狀 Section 結構 (SET_BEGIN_SECTION/SET_END_SECTION),閱讀性極佳。
  • 上下文物件 LOG_CTX 串聯調用鏈。

實戰範例

1. 觸發器審計日誌

CREATE OR REPLACE TRIGGER LOG_DML
BEFORE INSERT OR UPDATE OR DELETE ON T_ESSAIS
FOR EACH ROW
BEGIN
  IF DELETING OR UPDATING THEN
    PLOG.INFO('T_ESSAIS:OLD:' || USER || ':' || :OLD.data);
  END IF;
  IF INSERTING OR UPDATING THEN
    PLOG.INFO('T_ESSAIS:NEW:' || USER || ':' || :NEW.data);
  END IF;
END;

2. 存儲過程參數驗證與業務斷言

CREATE OR REPLACE PROCEDURE testAssert(p_Param1 INT, p_Param2 VARCHAR2) IS
  pCTX PLOG.LOG_CTX;
BEGIN
  PLOG.ASSERT(pCTX, p_Param1 > 1, 'p_Param1>1 always false');
  PLOG.ASSERT(p_Param2 = 'man', 'p_Param2<>man');
  PLOG.ASSERT(1 IS NULL, '1 is null always false');
  PLOG.ASSERT(NOT 1 > 1, 'NOT 1>1 never false');
  -- 失敗即拋出自定義異常
  PLOG.ASSERT(1 > 2, '1>2 always false', -20001, pRaiseExceptionIfFALSE => TRUE, pLogErrorReplaceError => FALSE);
  PLOG.ASSERT(1 > 3, 'Never test there is a raise in previous assert');
END;

3. 樹狀結構完整業務流程日誌

CREATE OR REPLACE PROCEDURE testAssert2(p_Param1 INT, p_Param2 VARCHAR2) IS
  v_CTX PLOG.LOG_CTX;
  v_Year VARCHAR2(4);
BEGIN
  v_CTX := PLOG.INIT('測試信息');           -- 根節點
  PLOG.SET_BEGIN_SECTION(v_CTX, 'procedure_testAssert2_測試信息');  -- 1級
  PLOG.SET_BEGIN_SECTION(v_CTX, '檢測入口參數');                   -- 2級
  PLOG.ASSERT(v_CTX, p_Param1 > 1, 'p_Param1>1 always false');
  PLOG.ASSERT(p_Param2 = 'man', 'p_Param2<>man');
  PLOG.SET_END_SECTION(v_CTX, '檢測入口參數');

  NULL; -- 業務邏輯

  PLOG.SET_BEGIN_SECTION(v_CTX, '檢查業務處理結果');
  SELECT TO_CHAR(SYSDATE, 'YYYY') INTO v_Year FROM DUAL;
  PLOG.ASSERT(v_CTX, v_Year = '2003', '當前年份應為2003,實際=' || v_Year);
  PLOG.SET_END_SECTION(v_CTX, '檢查業務處理結果');

  PLOG.SET_END_SECTION(v_CTX, 'procedure_testAssert2_測試信息');
END;

進階擴展建議

  1. 擴充日誌表 TLOG:加入 Client IP、Session ID 等欄位。利用 SYS_CONTEXT('USERENV','IP_ADDRESS')、SYS_CONTEXT('USERENV','CURRENT_USER') 獲取。修改 PLOG.ADD_ROW 持久化。
  2. 二次封裝:建議自建 Wrapper Package (如 PKG_ConDebug) 封裝 PLOG,隔離第三方依賴,提供專案專用 API。
  3. 視圖優化:建立 VLOG2 視圖,轉換 Level 代碼為文字、格式化時間,供 BI/報表直連。
  4. 自動化回歸測試:結合動態測試資料生成 (參考 PKG_ConDebugInfo.Normal_Owner_UpdateData3)、斷言驗證 (PKG_ConDebugInfo.Normal_Owner_Check_Data3),構建 PL/SQL 單元測試流水線。

總結

自建包適合輕量級、專案專用需求;Log4plsql 提供企業級日誌框架能力 (分級、斷言、樹狀結構)。**核心原則**:測試碼不侵入業務碼,透過開關控制是否啟用;日誌結構化,便於事後分析與自動化驗證。

  1. 上一篇文章:
  2. 下一篇文章:
Copyright © 程式碼之家 All Rights Reserved