使用PL/Scope分析PL/SQL代码(3)

6、验证命名是否规范 Validate Naming Conventions
假设我有以下要求:
IN parameters: end with _in
OUT parameters: end with _out
IN OUT parameters: end with _io

为了验证一个程序单元符合这个规则,我将针对FORMAL IN, FORMAL OUT, or FORMAL IN OUT检索其声明情况。
假设我声明了以下测试包:

Code Listing 5: Creating the package specification for plscope_demo CREATE OR REPLACE PACKAGE plscope_demo IS PROCEDURE my_procedure (param1_in IN INTEGER, param2 IN DATE); FUNCTION my_function (param1 IN INTEGER , in_param2 IN DATE , param3_in IN employees.last_name%TYPE ) RETURN VARCHAR2; END plscope_demo; Code Listing 6: Querying to find naming violations SELECT prog.name subprogram, parm.name parameter FROM all_identifiers parm, all_identifiers prog WHERE parm.owner = USER AND parm.object_name = 'PLSCOPE_DEMO' AND parm.object_type = 'PACKAGE' AND prog.owner = parm.owner AND prog.object_name = parm.object_name AND prog.object_type = parm.object_type AND parm.usage_context_id = prog.usage_id AND parm.TYPE IN ('FORMAL IN', 'FORMAL IN OUT', 'FORMAL OUT') AND parm.usage = 'DECLARATION' AND ( (parm.TYPE = 'FORMAL IN' AND LOWER (parm.name) NOT LIKE '%\_in' ESCAPE '\') OR (parm.TYPE = 'FORMAL OUT' AND LOWER (parm.name) NOT LIKE '%\_out' ESCAPE '\') OR (parm.TYPE = 'FORMAL IN OUT' AND LOWER (parm.name) NOT LIKE '%\_io' ESCAPE '\')) ORDER BY prog.name, parm.name

‘7、识别违反最佳做法的操作 Identify Violations of Best Practices

1)声明在包说明中的变量 Variables declared in the specification of a package,
这种情况下任何对包有执行权限的用户都可直接读取该变量。

2)已声明但未在程序中抛出的异常 Exception declared but not raised in a program unit.

以上2类操作都是不合理的。

检查第一种情况简单:

SELECT object_name, name, line FROM all_identifiers ai WHERE ai.owner = USER AND ai.TYPE = 'VARIABLE' AND ai.usage = 'DECLARATION' AND ai.object_type = 'PACKAGE';

第二种情况,先要观察一下异常在程序中的各种使用类型(USAGES)

PROCEDURE plscope_demo_proc IS e_bad_data EXCEPTION; PRAGMA EXCEPTION_INIT ( e_bad_data, -20900); BEGIN RAISE e_bad_data; EXCEPTION WHEN e_bad_data THEN log_error (); END plscope_demo_proc;

Let’s see what PL/Scope has to say about the e_bad_data identifier:

SELECT line , TYPE , usage FROM all_identifiers WHERE owner = USER AND object_name = 'PLSCOPE_DEMO_PROC' AND name = 'E_BAD_DATA' ORDER BY line / LINE TYPE USAGE ----- ------------ --------------- 3 EXCEPTION DECLARATION 4 EXCEPTION ASSIGNMENT 6 EXCEPTION REFERENCE 8 EXCEPTION REFERENCE

可以推断出EXCEPTION_INIT被当做赋值操作;RAISE statement and the WHEN clause被认为是引用操作。
如此一来,我们声明一下语句即可:

Code Listing 7: Querying all subprograms in which an exception is declared but not referenced WITH subprograms_with_exception AS (SELECT DISTINCT owner , object_name , object_type , name FROM all_identifiers has_exc WHERE has_exc.owner = USER AND has_exc.usage = 'DECLARATION' AND has_exc.TYPE = 'EXCEPTION'), subprograms_with_raise_handle AS (SELECT DISTINCT owner , object_name , object_type , name FROM all_identifiers with_rh WHERE with_rh.owner = USER AND with_rh.usage = 'REFERENCE' AND with_rh.TYPE = 'EXCEPTION') SELECT * FROM subprograms_with_exception MINUS SELECT * FROM subprograms_with_raise_handle ;

Oracle数据库之PL/SQL程序基础设计 

PL/SQL Developer实用技巧分享

内容版权声明:除非注明,否则皆为本站原创文章。

转载注明出处:https://www.heiqu.com/a3d58c44ae31c75554a30b7e2400330e.html