我正在尝试做以下事情;假设我在Oracle中创建了一个对象类型
create type test as object(
name varchar2(12),
member procedure print1);
/
create type body test is
member procedure print1 is
begin
dbms_output.put_line('Test');
end print1;
end;
/
现在我想添加一个新的成员程序print2 - 再次,我可以通过输入:
来实现alter type test
add member procedure print2 cascade;
现在,我的问题是:如何定义主体并添加print2而不重复其他定义?我知道我可以为两个程序创建或替换正文测试和列表实现,但这不实用,因为我必须维护其他人编写的对象类型的代码,我不知道他们是如何实现代码的,只是这些程序和功能存在。
我浏览过文档和网页,但找不到答案,对我来说,Oracle希望开发人员再次输入所有定义似乎很愚蠢。
此致 乔治
答案 0 :(得分:2)
如何创建一个动态添加定义到类型的过程:
create or replace procedure add_procedure(p_new_procedure_definition varchar2)
authid current_user
is
v_object_type_body varchar2(32767) := 'create or replace ';
begin
--Build string with current definitions
for source_code in
(
select text
from user_source
where name = 'TEST'
and type = 'TYPE BODY'
order by line
) loop
--Don't include the last "END;" yet.
--(Huge assumption that the package ends with "END;")
if replace(upper(trim(source_code.text)),chr(10)) <> 'END;' then
v_object_type_body := v_object_type_body||source_code.text;
end if;
end loop;
--Add new definition
v_object_type_body := v_object_type_body||chr(10)||
p_new_procedure_definition||chr(10)||'end;';
--For debugging
--dbms_output.put_line(v_object_type_body);
--Compile the type
execute immediate v_object_type_body;
end;
/
然后像这样运行:
begin
add_procedure(
'
member procedure print2 is
begin
dbms_output.put_line(''Test2'');
end print2;
'
);
end;
/
虽然您需要对包裹如何结束做出一些相当大的假设。要使这成为一个真正通用的解决方案,您需要构建一个PL / SQL解析器,这基本上是不可能的。并且该过程仅适用于32K,如果类型非常大,您可能需要使用CLOB。
答案 1 :(得分:1)
使用Oracle SQL Developer更改类型主体。
或使用任何文本编辑器更改源文件并在您喜欢的SQL提示符中运行它。
对象类型是Oracle中最先进的编程概念。也许你最好使用独立功能?
但是,我理解你的观点。 AFAIK类型主体不能包含规范中未列出的功能。方法的顺序也无关紧要,因此似乎没有理由不选择此选项。