我有一个包含不同程序的程序包,以及一个主程序,我通过它调用其他程序。
通过前端,我将程序名称传递给main()
。有没有什么方法可以调用过程只需编写包含的参数名称('需要调用的过程名称')?
CREATE OR REPLACE PACKAGE BODY UPLOAD_PKG
IS
--This procedure will populate LOG with messages
PROCEDURE PRINT_LOG_PR IS
BEGIN
fnd_file.put_line(fnd_file.LOG,'ABC');
END PRINT_LOG_PR;
--This procedure will populate LOG with messages
PROCEDURE PRINT_LOG1 IS
BEGIN
fnd_file.put_line(fnd_file.LOG, 'XYZ');
END PRINT_LOG1;
PROCEDURE Main( p_obj_type VARCHAR2
, errbuf VARCHAR2
, retcode VARCHAR2) IS
BEGIN
-Is this possible for eg i have passed PRINT_LOG1 here and calling PRINT_LOG1
p_obj_type ;-
END main;
END UPLOAD_PKG
答案 0 :(得分:4)
是
PROCEDURE Main( p_obj_type VARCHAR2
, errbuf VARCHAR2
, retcode VARCHAR2) IS
BEGIN
CASE p_obj_type
WHEN 'PRINT_LOG_PR' THEN PRINT_LOG_PR;
WHEN 'PRINT_LOG1' THEN PRINT_LOG1;
END CASE;
END main;
答案 1 :(得分:3)
使用:
CREATE OR REPLACE PACKAGE BODY UPLOAD_PKG
IS
--This procedure will populate LOG with messages
PROCEDURE PRINT_LOG_PR IS
BEGIN
fnd_file.put_line(fnd_file.LOG,'ABC');
END PRINT_LOG_PR;
--This procedure will populate LOG with messages
PROCEDURE PRINT_LOG1 IS
BEGIN
fnd_file.put_line(fnd_file.LOG, 'XYZ');
END PRINT_LOG1;
PROCEDURE MAIN( p_obj_type VARCHAR2
, errbuf VARCHAR2
, retcode VARCHAR2) IS
BEGIN
CASE p_obj_type
WHEN 'PRINT_LOG_PR' THEN UPLOAD_PKG.PRINT_LOG_PR;
WHEN 'PRINT_LOG1' THEN UPLOAD_PKG.PRINT_LOG1;
END CASE;
END MAIN;
END UPLOAD_PKG
我在MAIN存储过程中使用的CASE语句是PLSQL CASE语句,而不是ANSI SQL CASE。您可以告诉,因为PLSQL版本需要END CASE
来结束CASE语句。
答案 2 :(得分:1)
如果你不想使用动态pl / sql,那么我建议在包头中使用常量变量来选择程序(尽可能避免硬编码)。
主程序调用将是例如:
UPLOAD_PKG.MAIN(UPLOAD_PKG.C_PRINT_LOG_PR, v_errbuf, v_retcode);
在主体中你会使用这样的情况:
CASE p_obj_type
WHEN C_PRINT_LOG_PR THEN UPLOAD_PKG.PRINT_LOG_PR;
WHEN C_PRINT_LOG1 THEN UPLOAD_PKG.PRINT_LOG1;
ELSE RAISE SOME_ERROR;
END CASE;
在标题中,您可以定义常量变量以包含任何内容:
CREATE OR REPLACE PACKAGE UPLOAD_PKG
IS
C_PRINT_LOG_PR CONSTANT VARCHAR2(22) := 'What ever';
C_PRINT_LOG1 CONSTANT VARCHAR2(22) := 'What ever2';
...
但是有些情况下客户端应用程序无法引用包的全局变量,因此您需要为每个常量变量创建函数以返回它们。但是如果你能打电话给那些正确的程序,那就太复杂了......
但是好奇心可以告诉我们为什么你需要这样使用包裹?
答案 3 :(得分:0)
与CASE解决方案一样,可能使用动态PL / SQL执行此操作。
PROCEDURE MAIN( p_obj_type VARCHAR2
, errbuf VARCHAR2
, retcode VARCHAR2) IS
BEGIN
EXECUTE IMMEDIATE 'begin upload_pkg.'||p_obj_type|| '; end;';
END MAIN;
简单参数(Date,Varhar2,Number)可以使用USING命令在IN OUT中传递。
关键问题是它是否可取。
与任何动态语言一样,它留下了只能在运行时找到的错误的范围,而不是编译时间 - 即传递不存在的p_obj_type的值。您可以通过常量或抽象数据类型来缓解这种情况。
此外,每个动态sql或pl / sql命令都会导致与实际编译代码相比较小的解析开销。这种开销很小,但如果在循环内执行则会变得明显。
最后,被调用的代码必须具有相同的参数签名。