1. 程式人生 > >關於在PLSQL中實現DEBUG除錯功能的方法

關於在PLSQL中實現DEBUG除錯功能的方法

關於在PLSQL中實現DEBUG除錯功能的方法

2017年04月07日 14:27:52 samt007 閱讀數:2179 標籤: oracle除錯plsql 更多

個人分類: Oracle PL/SQL技巧

前言 
一個健康的PLSQL,應該都帶有一套完整的除錯邏輯。特別是那些功能很複雜的PLSQL,就更加有必要具備除錯功能了。否則,當PLSQL處理資料出現問題的時候,分析(處理)起來會相當的困難。 
舉個例子,Oracle EBS標準功能的PLSQL(特別是API),如果Oracle沒有自帶除錯功能給我們做看每一步驟的除錯結果,單單通過看程式碼模擬其執行邏輯來找問題,基本上是不可能處理問題的! 
當然,我們編寫的程式碼,實際上大部分的都並沒有很複雜,所以對除錯部分沒太高的要求。這裡也建議按照實際情況來做。但是一些重要的並且是複雜的功能,還是必須要考慮如何新增除錯! 
實現除錯的辦法 
現在根據這幾年寫PLSQL的經驗,得出的一套如何在PLSQL中實現除錯的方法,特意分享一下。如果有更加好的方法,也可以一起討論一下!

具體實現辦法: 
1 首先,統一新建3個客戶化的Profile配置來實現除錯功能的開關: 
CUX:程式除錯級別 
設定除錯的級別。這裡是仿照標準功能的除錯邏輯來做的一個設定。作用就是是否啟用除錯,以及除錯的資料輸出的明細級別! 
具體: 
XYG_ALD_DEBUG_LEVEL:設定檢視除錯訊息的級別 
0:不檢視除錯(預設值) 
1:檢視除錯程式主要訊息級別=1的訊息 
2:檢視訊息的除錯級別<=2的資訊 
3:檢視訊息的除錯級別<=3的資訊 
4:檢視訊息的除錯級別<=4的資訊 
5:檢視訊息的除錯級別<=5的資訊

舉個例子,如果我的除錯訊息設定是:除錯級別3,除錯顯示3的資訊。 
則當XYG_ALD_DEBUG_LEVEL級別是2的時候,這個3的除錯資訊是不會顯示的。 
當XYG_ALD_DEBUG_LEVEL級別大於等於3的時候,這個訊息才會顯示出來! 
具體可以自己寫一個例子來理解。

CUX:程式除錯方式 
就是除錯結果顯示的方式。 
一般來說有下面幾種方式: 
除錯方式XYG_ALD_DEBUG_TYPE: 
DBMS_OUTPUT直接輸出 
FILE_DEBUGLOG文件輸出 
REQUEST_DEBUGLOG請求日誌輸出 
DATA_DEBUGLOG表格資料輸出 
DBMS_OUTPUT:這個不用多說了,實際上就是呼叫DBMS_OUTPUT.PUT_LINE在開發工具直接顯示訊息。 
FILE_DEBUGLOG:這個很重要!不過要配合一些額外的定義,才可以看到這種輸出的結果。這種方式的除錯結果以檔案的形式存在伺服器裡面。適合那種超大資料量輸出的除錯資訊。 
REQUEST_DEBUGLOG:如果PLSQL是在請求中呼叫的話,可以考慮用這種方式檢視除錯資訊。除錯資訊會直接顯示在請求的日誌裡面。 
DATA_DEBUGLOG表格資料輸出:就是將除錯的結果輸出在fnd_log_messages表。和標準功能的保持一致!

CUX:程式除錯檔案 
結合除錯方式= FILE_DEBUGLOG文件輸出使用。 
就是定義除錯結果產生的檔案是什麼。 
注意:如果這個設定為空,則預設檔案= XYG_PUB_AUTOMAIL_PKG.XYG_DF_UTL_FILE_DIR||’/’||userenv(‘SESSIONID’)||’.log’

2 PLSQL裡面如何使用除錯的方法: 
首先,在要新增除錯邏輯的PKG包體裡面,建議直接新增下面這些指令碼,二次簡單封裝一下公用的除錯處理包,方便呼叫: 
例如:

 
  1. CREATE OR REPLACE PACKAGE BODY APPS.XYG_ALBND_PACK_PKG

  2. AS

  3. --===============================================================

  4. -- Debug 處理

  5. --===============================================================

  6. --P_DEBUG_LEVEL:該除錯資訊的級別

  7. PROCEDURE DEBUGLOG (P_DEBUG_LEVEL IN NUMBER,P_DEBUG_MSG IN VARCHAR2)

  8. IS

  9. BEGIN

  10. XYG_ALD_DEBUG_PKG.DEBUGLOG(' XYG_ALBND_PACK_PKG ',P_DEBUG_LEVEL,P_DEBUG_MSG);

  11. END DEBUGLOG;

  12. --簡化版本,預設該訊息的是level=1的

  13. PROCEDURE DEBUGLOG1 (P_DEBUG_MSG IN VARCHAR2)

  14. IS

  15. BEGIN

  16. XYG_ALD_DEBUG_PKG.DEBUGLOG(' XYG_ALBND_PACK_PKG ',1,P_DEBUG_MSG);

  17. END DEBUGLOG1;

  18. ….

  19. 接著,在需要顯示除錯訊息的地方,直接呼叫這個函式即可:

  20. DEBUGLOG(1,'GENERATE_XXXXXXXXXXXXX(+)'); 或者:DEBUGLOG1('GENERATE_XXXXXXXXXXXXX(+)');

  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7
  • 8
  • 9
  • 10
  • 11
  • 12
  • 13
  • 14
  • 15
  • 16
  • 17
  • 18
  • 19
  • 20

需要注意的是,DEBUGLOG的第一個引數是該訊息的顯示級別。換句話說,就是你希望這個訊息在什麼級別顯示它! 
舉個例子,如果設定為3,則訊息基本是3級,當設定顯示的訊息級別大於等於3的時候,該訊息會顯示。

3 程式如何檢視除錯的結果:

 
  1. ------------------------------

  2. ---1 普通在Toad的output除錯樣例:

  3. DECLARE

  4. L_RETCODE NUMBER;

  5. L_ERRBUF VARCHAR2(4000);

  6. BEGIN

  7. FND_PROFILE.PUT('XYG_ALD_DEBUG_LEVEL',1);

  8. FND_PROFILE.PUT('XYG_ALD_DEBUG_TYPE','DBMS_OUTPUT');

  9. XYG_ALBND_PACK_PKG.AUTO_CREATE_PACK(

  10. 'PO_HEADERS_ALL'

  11. ,2579287

  12. ,SYSDATE

  13. ,5954

  14. ,'NORMAL'

  15. ,l_retcode

  16. ,l_errbuf

  17. );

  18. DBMS_OUTPUT.PUT_LINE(L_RETCODE||'-'||L_ERRBUF);

  19. END;

  20.  
  21. ------------------------------

  22. ---2 除錯結果檔案輸出樣例:

  23. DECLARE

  24. L_RETCODE NUMBER;

  25. L_ERRBUF VARCHAR2(4000);

  26. BEGIN

  27. FND_PROFILE.PUT('XYG_ALD_DEBUG_LEVEL',2);

  28. FND_PROFILE.PUT('XYG_ALD_DEBUG_TYPE','FILE_DEBUGLOG');

  29. FND_PROFILE.PUT('XYG_ALD_DEBUG_FILE'

  30. ,'/oracle/vis/apps/apps_st/appl/attchment/12.0.0/BATCH_UPLOAD_TEMP/SAMT_TEST001.log');

  31. XYG_ALBND_PACK_PKG.AUTO_CREATE_PACK(

  32. 'PO_HEADERS_ALL'

  33. ,2579287

  34. ,SYSDATE

  35. ,5954

  36. ,'NORMAL'

  37. ,l_retcode

  38. ,l_errbuf

  39. );

  40. DBMS_OUTPUT.PUT_LINE(L_RETCODE||'-'||L_ERRBUF);

  41. END;

  42.  
  43. --檢視檔案的路徑

  44. SELECT FND_PROFILE.VALUE('XYG_ALD_DEBUG_FILE') FROM DUAL

  45.  
  46. ------------------------------

  47. --3 如果用資料輸出的

  48. DECLARE

  49. L_RETCODE NUMBER;

  50. L_ERRBUF VARCHAR2(4000);

  51. BEGIN

  52. FND_PROFILE.PUT('XYG_ALD_DEBUG_LEVEL',2);

  53. FND_PROFILE.PUT('XYG_ALD_DEBUG_TYPE','DATA_DEBUGLOG');

  54. XYG_ALBND_PACK_PKG.AUTO_CREATE_PACK(

  55. 'PO_HEADERS_ALL'

  56. ,2579287

  57. ,SYSDATE

  58. ,5954

  59. ,'NORMAL'

  60. ,l_retcode

  61. ,l_errbuf

  62. );

  63. DBMS_OUTPUT.PUT_LINE(L_RETCODE||'-'||L_ERRBUF);

  64. END;

  65. ---檢視除錯資訊:

  66. select to_char(systimestamp, 'yyyy-mm-dd hh24:mi:ss:ff3') debug_time,session_id,module||'[---]'||message_text

  67. from fnd_log_messages

  68. where timestamp > sysdate-1

  69. and session_id=userenv('SESSIONID')

  70. order by LOG_SEQUENCE;

  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7
  • 8
  • 9
  • 10
  • 11
  • 12
  • 13
  • 14
  • 15
  • 16
  • 17
  • 18
  • 19
  • 20
  • 21
  • 22
  • 23
  • 24
  • 25
  • 26
  • 27
  • 28
  • 29
  • 30
  • 31
  • 32
  • 33
  • 34
  • 35
  • 36
  • 37
  • 38
  • 39
  • 40
  • 41
  • 42
  • 43
  • 44
  • 45
  • 46
  • 47
  • 48
  • 49
  • 50
  • 51
  • 52
  • 53
  • 54
  • 55
  • 56
  • 57
  • 58
  • 59
  • 60
  • 61
  • 62
  • 63
  • 64
  • 65
  • 66
  • 67
  • 68
  • 69
  • 70
  • 71

完工!就是這麼的簡單,讓您寫的PLSQL就擁有了完整的而且有非常好擴充套件性的除錯功能!

文件下載以及原始碼下載的連結: 
http://download.csdn.net/detail/samt007/9806450

https://blog.csdn.net/samt007/article/details/69537289

 

 

 

試玩了plsql中test視窗declare宣告變數|lpad函式||plsql sql command test window區別|

在這裡先感謝一下itpub高手的帖子答覆

Q:

看到的oracle中的for迴圈or i in 1..100 loop,i都是從1,2,3這樣遞增的,可是我這裡需要i從01,02,03這樣遞增,9開始是09,10,11,12.
請問這樣的for迴圈怎麼寫。
具體問題可見http://www.itpub.net/thread-1620912-1-1.html,我想在觸發器中加入迴圈變數,精簡我的觸發器長度。
ps:我是新手,謝謝大家的幫助

A:

lpad('tech', 7);        would return ' tech'

lpad('tech', 2);        would return 'te'

lpad('tech', 8, '0');        would return '0000tech'

lpad('tech on the net', 15, 'z');        would return 'tech on the net'

lpad('tech on the net', 16, 'z');        would return 'ztech on the net'

每次看到itpub的答覆都很激動,一個恢復解決問題。

lpad函式說明

語法格式如下:

 

  lpad( string, padded_length, [ pad_string ] )

 

  string

 

  準備被填充的字串;

 

  padded_length

 

  填充之後的字串長度,也就是該函式返回的字串長度,如果這個數量比原字串的長度要短,lpad函式將會把字串擷取成從左到右的n個字元;

 

  pad_string

 

  填充字串,是個可選引數,這個字串是要貼上到string的左邊,如果這個引數未寫,lpad函式將會在string的左邊貼上空格。 

下面說plsq中的塊。

經常看到有人和書上直接寫declare,也不在觸發器或者儲存過程中,可是照樣使用,比如:http://zhidao.baidu.com/question/113921713.html

1,我剛開始直接在plsql中的查詢視窗sql window使用,報錯:

13:51更新:

sql windows視窗也是可以顯示的,在第二列就是output,僅僅select不行

 

 

2,想到在測試視窗test window,通過(需要點選左上角的start debugger按鈕,然後點選run)

複製程式碼

-- Created on 2012-6-13 by DELL 
declare 
  -- Local variables here
  i number;
begin
  -- Test statements here
  for i in 1..100 loop
    dbms_output.put_line(lpad(i,2,'0'));
    end loop;
end;

複製程式碼

 

下面是結果

 

 拓展:

1 Command window實現了SQL*Plus的所有功能,允許執行sql*plus命令,sql命令,sql指令碼。
2 SQL window用於執行sql語句,顯示sql輸出,執行統計資訊。(測試sql語句,查看錶中的資料,更新資料)
  例如 desc table(查看錶結構)不能在SQL window中執行,必須在Command window中才能執行。

3 Program window中建立一個儲存過程(或者直接在plsql左邊對應的procedures和trigger右鍵新建),如下:

create or replace procedure TEST is
begin
DBMS_SESSION.set_nls('NLS_DATE_FORMAT','''YYYY-MM-DD HH24:MI:SS''');
DBMS_OUTPUT.PUT_LINE('HelloWorld!');
DBMS_OUTPUT.put_line(SYSDATE);
end TEST;

需要注意,SET_NLS的第二個引數VALUE
輸入的值除了需要的格式外,還需要包含引號,否則會引發錯誤(選項缺失或無效)
在Command window中執行(或者在Test window中測試),如下:
set   serveroutput   on
exec TEST();
或者begin
  2  test();
  3  end;
  4  / ......

分類: ORACLE

好文要頂 關注我 收藏該文  

sumsen
關注 - 5
粉絲 - 21

+加關注

https://www.cnblogs.com/sumsen/archive/2012/06/13/2547512.html