我正在编写一个从存储库中读取一些PL / SQL代码的过程,然后验证每个过程/函数是否具有相应的文档头。给出变量my_code中包含的以下PL / SQL代码:
my_code varchar2(1024) := '
script package test_lib
is
-------------------------------------------------------------------------------
-- <function name="my_func" begin="9-Dec-2010">
-- <summary>
-- Test function.
-- </summary>
-- <authors>
-- <author name="Giuseppe Greco" email="giuseppe.greco@b-source.ch"/>
-- </authors>
-- <params>
-- <param name="num" mandatory="yes" type="input">
-- Test param.
-- </param>
-- </params>
-- <return>
-- True if it is an alarm; otherwise, false.
-- </return>
-- </function>
--------------------------------------------------------------------------------
function my_func(par1 NUMBER)
return boolean
is
l_num NUMBER := 0;
begin
if l_num < 1 then
dbms_output.put_line(''my_func'');
end if;
return true;
end my_func;
end test_lib;
';
我尝试过类似的东西......但它不起作用:
if REGEXP_LIKE(my_code, 'function (\w).+end \1;') then
l_number_of_funcs := LENGTH(
REGEXP_REPLACE(
my_code,
'([^f]+[^u]+[^n]+[^c]+[^t]+[^i]+[^o]+[^n]+)(.+)is(.*)begin(.*)end([a-z0-9_\-]+);'));
end if;
在上面的语句中,REGEXP_LIKE永远不会返回true,因此从不执行REGEXP_REPLACE。我正在做的是确定代码是否包含至少一个过程,如果是,我调用REGEXP_REPLACE来确定代码包含多少个过程(在上面的例子中它应该返回1)。我首先调用REGEXP_LIKE,因为如果代码不包含任何过程,则REGEXP_REPLACE崩溃。
有任何想法或建议吗?任何帮助都会非常感激。
谢谢, 杰夫
答案 0 :(得分:0)
我认为使用NVL你不需要两次检查。试试:
l_number_of_funcs :=
NVL(LENGTH(REGEXP_REPLACE(l_code,'(f)unction [^(]+\(|.','\1',1,0,'in')),0);
我无法测试,但它应该朝着正确的方向发展。
答案 1 :(得分:0)
尝试更简单的正则表达式
'^.*function.*return.*(is|as).*begin.*end'
在此上下文中,REGEXP_COUNT函数可能更合适。
多条线的存在将打破这一点。如果有多行,即使上面(1)中的简化正则表达式也不起作用。我建议您编写一个comment-stripper和newline-remover,将代码字符串传递给这些函数,然后通过正则表达式运行。
在任何情况下,使用正则表达式来解析文本往往不像希望的那样有用。你真的需要一个PL / SQL解析器 - 见
http://database-geek.com/2009/02/06/building-a-plsql-code-parser-using-plsql-part-1-2/
分享并享受。