Oracle笔记---异常处理
1、什么是异常:
在PL/SQL中的一个警告或错误的情形都可被称为异常。包括编译时错误(PLS)和运行时错误(ORA)。一个异常通常包含一个错误代码和错误文本,分别指示异常的编号和具体错误信息。
2、常用的函数和过程:
SQLCODE: 返回错误代码,没有错误时返回0
SQLERRM:返回错误消息.
PRAGMA EXCEPTION_INIT():把用户自定义异常与相应的错误代码关联,使用用户自定义异常来捕获、处理错误
RAISE_APPLICATION_ERROR:可用于定义用户错误消息和在使用该过程的位置上暂 停程序的执行。
3、异常的分类:
系统预定义异常
未预定义的异常
自定义异常
4、异常的结构:
① 系统预定义异常:
BEGIN
.......
EXCEPTION
WHEN 异常类型1[OR 异常类型2] THEN
......异常处理代码
WHEN 异常类型3[OR 异常类型4] THEN
......异常处理代码
WHEN OTHERS THEN
.....异常处理代码
END;
系统异常:系统异常是有oracle预先定义好的异常类型,当发生这种异常是系统会自动触发
Oracle预定义的21个系统异常类型
命名的系统异常 | 产生原因 |
ACCESS_INTO_NULL | 未定义对象 |
CASE_NOT_FOUND | CASE中若未包含相应的 WHEN,并且没有设置 ELSE时 |
COLLECTION_IS_NULL | 集合元素未初始化 |
CURSER_ALREADY_OPEN | 游标已经打开 |
DUP_VAL_ON_INDEX | 唯一索引对应的列上有重复的值 |
INVALID_CURSOR | 在不合法的游标上进行操作 |
INVALID_NUMBER | 内嵌的 SQL语句不能将字符转换为数字 |
NO_DATA_FOUND | 使用 select into未返回行,或应用索引表未初始化的元素时 |
TOO_MANY_ROWS | 执行 select into时,结果集超过一行 |
ZERO_DIVIDE | 除数为 0 |
SUBSCRIPT_BEYOND_COUNT | 元素下标超过嵌套表或 VARRAY的最大值 |
SUBSCRIPT_OUTSIDE_LIMIT | 使用嵌套表或 VARRAY时,将下标指定为负数 |
VALUE_ERROR | 赋值时,变量长度不足以容纳实际数据 |
LOGIN_DENIED | PL/SQL应用程序连接到 oracle数据库时,提供了不正确的用户名或密码 |
NOT_LOGGED_ON | PL/SQL应用程序在没有连接 oralce数据库的情况下访问数据 |
PROGRAM_ERROR | PL/SQL内部问题,可能需要重装数据字典& pl./SQL系统包 |
ROWTYPE_MISMATCH | 宿主游标变量与 PL/SQL游标变量的返回类型不兼容 |
SELF_IS_NULL | 使用对象类型时,在 null对象上调用对象方法 |
STORAGE_ERROR | 运行 PL/SQL时,超出内存空间 |
SYS_INVALID_ID | 无效的 ROWID字符串 |
TIMEOUT_ON_RESOURCE | Oracle在等待资源时超时 |
例如:
DECLARE
test varchar(10);
BEGIN
SELECT DNAME INTO test FROM DEPT WHERE DEPTNO='11';
DBMS_OUTPUT.PUT_LINE(test);
EXCEPTION
WHEN NO_DATA_FOUND THEN
DBMS_OUTPUT.PUT_LINE('没有找到符合条件的数据');
WHEN TOO_MANY_ROWS THEN
DBMS_OUTPUT.PUT_LINE('返回的数据行过多');
WHEN OTHERS THEN
DBMS_OUTPUT.PUT_LINE('EORROR:'||SQLCODE||'-'||SQLERRM);
END;
② 未预定义异常:
由PL/SQL或SQL触发,没有与之相关联的预定义异常名称。
两个处理方法
A. 使用包含WHEN ...OTHERS字句处理异常程序,使用SQLCODE或SQLERRM捕获错误
B.把用户自定义异常与相应的错误代码关联,使用用户自定义异常来捕获、处理错误,使用PRAGMA EXCEPTION_INIT(exce_name,error_code),其中error_code的范围是:-1 ~ -12999
例如:
DEFINE p_deno = 10
DECLARE
e_emp_remaining EXCEPTION;
PRAGMA EXCEPTION_INIT (e_emp_remaining, -2292);
BEGIN
DELETE FROM departments
WHERE dept_id = &p_dno;
COMMIT;
EXCEPTION
WHEN e_emp_remaining THEN
DBMS_OUTPUT.PUT_LINE ('Cannot delete dept ' ||
TO_CHAR(&p_deptno) || '. employees exist. ');
END;
③ 自定义异常:是由用户根据自己的业务需要定义的异常。
例如:
DECLARE
name varchar(10);
ex EXCEPTION; --定义异常ex
BEGIN
SELECT DNAME INTO name FROM DEPT WHERE DEPTNO='10';
DBMS_OUTPUT.PUT_LINE(name);
IF NAME<>'HR' THEN
RAISE ex; --触发异常
END IF;
EXCEPTION
WHEN ex THEN
DBMS_OUTPUT.PUT_LINE('10号部门不是HR'); --处理异常
END;
用户自定义错误消息:
使用RAISE_APPLICATION_ERROR过程定制,格式RAISE_APPLICATION_ERROR(error_no IN NUMBER,error_message IN VARCHAR2[,keep_errors IN BOOLEAN])
---error_no: -20000~ -20999之间的任意负整数
---error_message:错误提示消息,最大不能超过512个字符
---keep_errors:可选项,如果keep_errors为TRUE,则这个新的错误将加在已产生的错误列表之后。如果keep_errors为FALSE,则这个新错误将代替当前的错误列表。默认为FALSE