oracle存儲過程—-異常介紹
參考PL/SQL ,存儲過程中的異常來自於程序本身,也有的來自開發人員自定義的數據,而所有的這些錯誤我們稱之為異常(編譯時的錯誤不能稱為異常)。
本篇介紹存儲過程中對於異常的三種分類:
1.預定義異常。
2.非預定義異常。
3.自定義異常。
1、預定義異常
oracle中為每個錯誤提供了一個錯誤號,而捕獲異常則需要異常有名稱,oracle提供了一些已經定義好名稱的異常,這就是預定義異常。oracle一共提供了25種預定義異常。
想要查看oracle預定義異常,輸入下邊的命令:
SELECT * FROM DBA_SOURCE WHERE NAME='STANDARD' AND TEXT LIKE '%EXCEPTION_INIT%'
則會看到如下的結果,即所有的預定義異常:
預定義異常的捕獲,只要名字與上圖中的TEXT
里的 括號中字母下划線那部分,匹配一致即可。
比如如下:
create or replace procedure test_select_procedure AS v_ds ly_ds%rowtype; BEGIN select * into v_ds from ly_ds; EXCEPTION -- 由EXCEPTION開始 WHEN TOO_MANY_ROWS THEN --如果符合這個異常,則進入下邊的執行 DBMS_OUTPUT.PUT_LINE('返回結果超過一條'); END;
上邊的查詢結果,返回多條記錄,即符合了預定義異常中的TOO_MANY_ROWS
,則會進入該異常中的邏輯。
異常的匹配從上而下,這一點注意。
2、非預定義異常
oracle更多的是非預定異常。有些異常是只有錯誤編號和相關的錯誤描述,並沒有名稱,為了解決這一問題,oracle允許開發人員為這樣的異常添加一個名稱,使得它們能夠被異常處理模塊捕捉到。
比如像下邊的這個異常,ORA-12899
,就是這種情況:
ORA-12899: 列 "ZNXD_GATEWAY"."LY_DS"."CREATE_TIME" 的值太大 (實際值: 149, 最大值: 50)
它沒有對應的異常名稱,不屬於預定義異常。
解決辦法就是,只需要將它的錯誤號碼,與異常名稱關聯一下即可,例子寫法如下:
create or replace procedure test_add_procedure (id varchar,createtime varchar,name varchar, age varchar,sex varchar) AS my_12899_exp exception; --定義一個異常,取名為my_12899_exp --編譯當前異常名,並與錯誤號對應 pragma exception_init(my_12899_exp,-12899); BEGIN insert into ly_ds values(id,createtime,name,age,sex); exception when dup_val_on_index then --不符合當前異常則繼續匹配邊的 dbms_output.put_line('主鍵沖突'); when my_12899_exp then --符合該異常則進入執行 dbms_output.put_line('內容超出存儲范圍'); end;
執行如下,當把第二個字段的值設的超出存儲范圍后,會引發異常:
SET SERVEROUTPUT ON; BEGIN test_add_procedure('11','2018-09-081輔導費地方發地方的分擔分擔放到發地方地方','劉七','30','男'); END;
輸出結果如下:
內容超出存儲范圍
3、自定義異常
如果有些並不屬於系統錯誤,可能是因為某段業務邏輯,只是想讓它拋出異常,像這種主動拋出異常的情況,就需要自定義異常了。
異常都會有錯誤名稱和錯誤號,自定義異常的時候,可以使用-20999~-20000 這個范圍的數字作為錯誤號,不會引起沖突的。
如下,數據庫的內容:
想要寫一個,根據性別,匹配條數,如果大於一條,則拋出異常,這樣的存儲過程,如下:
create or replace procedure test_select2_procedure (sex varchar) AS countNum number(10); my_range_exp exception; --聲明一個異常,取名為my_range_exp pragma exception_init(my_range_exp,-20001); --編譯異常 BEGIN select count(*) into countNum from ly_ds where LY_NB=sex; if(countNum >1) then raise my_range_exp; --使用raise拋出異常 end if; dbms_output.put_line(countNum); exception when my_range_exp then dbms_output.put_line('查詢條數大於1,主動拋出異常'); END;
當分別傳入男
、女
兩種參數時,結果如下:
執行男
:
BEGIN test_select2_procedure('男'); END;
結果
1
執行女
:
BEGIN test_select2_procedure('女'); END;
查詢條數大於1,主動拋出異常
原文鏈接:https://blog.csdn.net/wohaqiyi/article/details/81838236