참으로 흥미로운 질문입니다. 이것에는 두 가지 측면이 있습니다.
첫 번째는 좋은 생각인지 여부입니다. 문제는 RULE의 텍스트가 데이터베이스에 보이지 않는다는 것입니다. 의존성 검사에서 나타나지 않으므로 영향 분석이 어려워집니다. 분명히 (또는 분명히는 아닐지라도) 규칙의 구문은 그것을 실행함으로써 만 검증 될 수 있습니다. 이로 인해 규칙을 추가 할 때 문제가 발생할 수 있습니다. 따라서 유지 관리 문제가 될 수도 있습니다. 그리고 우리가 볼 수 있듯이 단순한 쿼리를 넘어 서면 프로그램하기가 어렵습니다.
두 번째 측면은 가능한지 여부입니다. 그것은. 동적 SQL을 사용해야합니다. 동적 SQL과 정적 SQL을 결합하는 것은 가능하지만 치명적입니다.
create table rules (project_name varchar2(30)
, rule_name varchar2(30)
, rule_text varchar2(4000))
/
insert into rules
values ('SO', 'ACC_SALES'
, 'select ACCOUNTNUMBER from CUSTOMERS where ACCUMULATED_SALES > 500000 ')
/
create table customers (accountnumber number(7,0)
, name varchar2(20)
, accumulated_sales number
, sales_region varchar2(3))
/
insert into customers values (111, 'ACME Industries', 450000, 'AA')
/
insert into customers values (222, 'Tyrell Corporation', 550000, 'BB')
/
insert into customers values (333, 'Lorax Textiles Co', 500000, 'BB')
/
이 함수는 규칙을 가져 와서 실행하고 숫자 배열을 반환합니다.
create or replace type rule_numbers as table of number
/
create or replace function exec_numeric_rule
(p_pname in rules.project_name%type
, p_rname in rules.rule_name%type)
return rule_numbers
is
return_value rule_numbers;
stmt rules.rule_text%type;
begin
select rule_text into stmt
from rules
where project_name = p_pname
and rule_name = p_rname;
execute immediate stmt
bulk collect into return_value;
return return_value;
end exec_numeric_rule;
/
테스트 해보십시오.
SQL> select * from customers
2 where accountnumber in
3 (select * from table (exec_numeric_rule('SO', 'ACC_SALES')))
4/
ACCOUNTNUMBER NAME ACCUMULATED_SALES SAL
------------- -------------------- ----------------- ---
222 Tyrell Corporation 550000 BB
1 row selected.
SQL>
오직 하나의 정답입니다.
하지만 지금 우리는 당신의 suplementary 질문에 와서 : 일이 얻을 시작
이
이 할 수있는 예 "가 저장된 쿼리 가 자신의 변수를 사용하는 경우 수행 할 수 있습니다"하지만, 조금 더 부서지기 쉽다. 새로운 규칙 : 우리는 기능을 개정
insert into rules
values ('SO', 'ACC_SALES_VAR'
, 'select ACCOUNTNUMBER from CUSTOMERS where ACCUMULATED_SALES > :LMT ')
/
을 적용합니다 :
create or replace function exec_numeric_rule
(p_pname in rules.project_name%type
, p_rname in rules.rule_name%type
, p_variable in number := null)
return rule_numbers
is
return_value rule_numbers;
stmt rules.rule_text%type;
begin
select rule_text into stmt
from rules
where project_name = p_pname
and rule_name = p_rname;
if p_variable is null then
execute immediate stmt
bulk collect into return_value;
else
execute immediate stmt
bulk collect into return_value
using p_variable;
end if;
return return_value;
end exec_numeric_rule;
/
손가락을 교차!
SQL> select * from customers
2 where accountnumber in
3 (select * from table (exec_numeric_rule('SO', 'ACC_SALES_VAR', 480000)))
4/
ACCOUNTNUMBER NAME ACCUMULATED_SALES SAL
------------- -------------------- ----------------- ---
222 Tyrell Corporation 550000 BB
333 Lorax Textiles Co 500000 BB
2 rows selected.
SQL>
그래, 그래도 작동합니다. 그러나 순열이 친숙하지 않다는 것을 알 수 있습니다. RULE에 하나 이상의 인수를 전달하려면 더 많은 함수 또는 twistier 내부 논리가 필요합니다.날짜 또는 문자열 집합을 반환하려면 더 많은 기능이 필요합니다. 다른 data_types의 P_VARIABLE 매개 변수를 전달하려면 더 많은 함수가 필요할 수 있습니다. 유형 검사 사전 조건이 필요합니다.
내 첫 번째 지점으로 돌아가는 : 예, 할 수 있지만 그 번거 로움입니까?
흥미로운 질문입니다! – Flukey
내부 플랫폼 효과가 다시 타고납니다! –