Я впервые создаю пакет PL/SQL. Это выглядит просто, но я не могу обернуть свою функцию, возвращающую таблицу, в пакет.
Скриншот моей ошибки приведен ниже:
Ниже приведена моя спецификация пакета:
CREATE OR REPLACE PACKAGE P_trdelclvr01 AS
FUNCTION fn_trdelclvr_QADJ return table_trdelclvr_QADJ;
END P_trdelclvr01;
/
Ниже тело пакета:
CREATE OR REPLACE PACKAGE BODY P_trdelclvr01 AS
type type_trdelclvr_QADJ as object(
TOTAL_CLAIMS INTEGER,
calculated_year INTEGER,
MTH varchar2(500),
CLAIM INTEGER,
CIW INTEGER,
PAPER INTEGER,
MBRECLAIM INTEGER,
PRVRDIALUP INTEGER,
PRVRIP INTEGER,
ELECTRONIC INTEGER
);
type table_trdelclvr_QADJ is table of type_trdelclvr_QADJ;
function fn_trdelclvr_QADJ
(P_CLAIM varchar2,
P_CIW varchar2,
P_PP varchar2,
P_PAPER varchar2,
P_MBR varchar2,
P_EDI varchar2,
P_MBR_NatApp varchar2,
P_CDAnet_DialUp varchar2,
P_CDAnet_IP varchar2,
P_CDAnet_ICA varchar2,
P_START_DATE date,
P_END_DATE date,
P_DENTAL varchar2,
P_IVR varchar2
);
--select * from table(fn_trdelclvr_QADJ(1,2,3,1,2,2,6,3,4,7,to_date('01/01/1990','mm/dd/yyyy'),to_date('12/12/2024','mm/dd/yyyy'),80,3));
return table_trdelclvr_QADJ
as
CURSOR CURSEUR_ETAPE
IS
select type_trdelclvr_QADJ(tbl.total_claims, tbl.calculated_year, tbl.mth, tbl.claim, tbl.ciw, tbl.paper, tbl.MbrEclaim, tbl.PrvrDialUp, tbl.PrvrIP, tbl.Electronic)
from
(
select
count(1) total_claims,
to_char(system_date,'YYYY') calculated_year,
to_char(system_date,'YYYY-MM') mth,
sum(decode(document_category, P_CLAIM ,1,0)) claim,
sum(decode(document_category, P_CIW ,1, P_PP ,1,0)) ciw,
sum(decode(document_source,P_PAPER,1,0)) paper,
sum(decode(document_source, P_MBR,decode(edi_app_source,P_MBR,1,0),0)
+ decode(document_source, P_EDI, decode(edi_app_source, P_MBR_NatApp, 1,0),0)) MbrEclaim,
sum(decode(document_source, P_EDI, decode(edi_app_source, P_CDAnet_DialUp, 1,0),0)) PrvrDialUp,
sum(decode(document_source, P_EDI,decode(edi_app_source, P_CDAnet_IP, 1,0),0)
+ decode(document_source, P_EDI, decode(edi_app_source, P_CDAnet_ICA, 1,0),0)) PrvrIP,
sum(decode(document_source, P_EDI, 1,0)) Electronic
from blu_adj_statistics adj
where system_date >= P_START_DATE
and system_date < P_END_DATE + 1
and claim_type = P_DENTAL
and claim_iteration = 1
and document_source <> P_IVR
and ( hsa_indicator is null )
group by to_char ( system_date , 'YYYY' ) ,
to_char ( system_date , 'YYYY-MM' )
ORDER BY 2 DESC,3 DESC
) tbl;
test_type table_trdelclvr_QADJ:=table_trdelclvr_QADJ();
BEGIN
OPEN CURSEUR_ETAPE;
LOOP
FETCH CURSEUR_ETAPE
BULK COLLECT INTO test_type;
EXIT WHEN CURSEUR_ETAPE%NOTFOUND;
END LOOP;
CLOSE CURSEUR_ETAPE;
RETURN test_type;
END;
END P_trdelclvr01;
/
Заранее спасибо.
🤔 А знаете ли вы, что...
Oracle Cloud Infrastructure (OCI) обеспечивает безопасность данных с помощью многоуровневых мер защиты.
Сначала создайте объект типа...
Create Or Replace Type type_trdelclvr_QADJ IS
object( TOTAL_CLAIMS INTEGER,
CALCULATED_YEAR INTEGER,
MTH varchar2(500),
CLAIM INTEGER,
CIW INTEGER,
PAPER INTEGER,
MBRECLAIM INTEGER,
PRVRDIALUP INTEGER,
PRVRIP INTEGER,
ELECTRONIC INTEGER
);
-- table type for use with sql select
create or replace TYPE T1_TAB AS TABLE OF type_trdelclvr_QADJ;
Create Or Replace Package P_trdelclvr01 AS
--
FUNCTION fn_trdelclvr_QADJ(p_Param1 VarChar2 := 'A') Return type_trdelclvr_QADJ;
/* OR ---> Return T1_TAB (if you want to return it as table of ...) */
--
END P_trdelclvr01;
create or replace Package Body
P_trdelclvr01 AS
Function fn_trdelclvr_QADJ(p_Param1 VarChar2 := 'A') Return type_trdelclvr_QADJ As
/* OR ---> Return T1_TAB (if you want to return it as table of ...) */
BEGIN
Declare
Cursor CURSEUR_ETAPE Is
Select type_trdelclvr_QADJ(tbl.total_claims, tbl.calculated_year, tbl.mth, tbl.claim, tbl.ciw, tbl.paper, tbl.MbrEclaim, tbl.PrvrDialUp, tbl.PrvrIP, tbl.Electronic)
/* This if it is table (below row)
Select T1_TAB(type_trdelclvr_QADJ(tbl.total_claims, tbl.calculated_year, tbl.mth, tbl.claim, tbl.ciw, tbl.paper, tbl.MbrEclaim, tbl.PrvrDialUp, tbl.PrvrIP, tbl.Electronic)) */
From ( Select
100 total_claims,
'2024' calculated_year,
'2024-08' mth,
15 claim,
10 ciw,
5 paper,
0 MbrEclaim,
7 PrvrDialUp,
8 PrvrIP,
15 Electronic
From Dual
) tbl;
type_tbl type_trdelclvr_QADJ;
-- below for table
/* type_tbl T1_TAB; */
Begin
Open CURSEUR_ETAPE;
Fetch CURSEUR_ETAPE INTO type_tbl;
Close CURSEUR_ETAPE;
RETURN type_tbl;
End;
END fn_trdelclvr_QADJ;
END P_trdelclvr01;
SET SERVEROUTPUT ON
DECLARE
v_type_tbl type_trdelclvr_QADJ ;
BEGIN
v_type_tbl := P_trdelclvr01.fn_trdelclvr_QADJ('B');
dbms_output.put_line('Year_Month is ' || v_type_tbl.MTH);
END;
/
/* R e s u l t :
Year_Month is 2024-08
PL/SQL procedure successfully completed */
Тот же результат с кодом ниже (T1_TAB для таблицы объекта)
SET SERVEROUTPUT ON
DECLARE
v_mth VARCHAR2(12);
BEGIN
Select MTH Into v_mth From P_trdelclvr01.fn_trdelclvr_QADJ('B');
dbms_output.put_line('Year_Month is ' || v_mth);
END;
/
... ИЛИ проверка таблицы с помощью sql Select * ...
Select * From P_trdelclvr01.fn_trdelclvr_QADJ('B');
/* R e s u l t :
TOTAL_CLAIMS CALCULATED_YEAR MTH CLAIM CIW PAPER MBRECLAIM PRVRDIALUP PRVRIP ELECTRONIC
------------ --------------- -------- ----- --- ----- --------- ---------- ------ ----------
100 2024 2024-08 15 10 5 0 7 8 15 */
База данных Oracle содержит два разных «движка»:
Механизм SQL обрабатывает операторы SQL (т. е. SELECT
, INSERT
, UPDATE
, CREATE TABLE
и т. д.) и может использовать типы, объявленные в операторах области видимости SQL (т. е. с CREATE TYPE
).
Механизм PL/SQL обрабатывает операторы PL/SQL и может использовать типы, объявленные как в областях PL/SQL, так и в области SQL (т. е. объявленные локально в блоке PL/SQL, объявленные глобально в пакете PL/SQL или в области SQL с помощью заявление CREATE TYPE
).
Если вы хотите использовать тип в инструкции SQL, объявите его в области SQL (а не в области PL/SQL).
Кроме того:
OBJECT
является типом SQL и ДОЛЖЕН быть объявлен в области SQL. (Если вам нужен полуэквивалентный тип PL/SQL, используйте RECORD
).CURSOR
, можно просто SELECT ... BULK COLLECT INTO ...
.Так:
CREATE TYPE type_trdelclvr_QADJ as object(
TOTAL_CLAIMS INTEGER,
calculated_year INTEGER,
MTH varchar2(500),
CLAIM INTEGER,
CIW INTEGER,
PAPER INTEGER,
MBRECLAIM INTEGER,
PRVRDIALUP INTEGER,
PRVRIP INTEGER,
ELECTRONIC INTEGER
);
CREATE TYPE table_trdelclvr_QADJ is table of type_trdelclvr_QADJ;
Затем вы можете объявить подпись пакета:
CREATE OR REPLACE PACKAGE P_trdelclvr01 AS
FUNCTION fn_trdelclvr_QADJ(
P_CLAIM varchar2,
P_CIW varchar2,
P_PP varchar2,
P_PAPER varchar2,
P_MBR varchar2,
P_EDI varchar2,
P_MBR_NatApp varchar2,
P_CDAnet_DialUp varchar2,
P_CDAnet_IP varchar2,
P_CDAnet_ICA varchar2,
P_START_DATE date,
P_END_DATE date,
P_DENTAL varchar2,
P_IVR varchar2
) return table_trdelclvr_QADJ;
END P_trdelclvr01;
/
и тело пакета:
CREATE OR REPLACE PACKAGE BODY P_trdelclvr01 AS
FUNCTION fn_trdelclvr_QADJ(
P_CLAIM varchar2,
P_CIW varchar2,
P_PP varchar2,
P_PAPER varchar2,
P_MBR varchar2,
P_EDI varchar2,
P_MBR_NatApp varchar2,
P_CDAnet_DialUp varchar2,
P_CDAnet_IP varchar2,
P_CDAnet_ICA varchar2,
P_START_DATE date,
P_END_DATE date,
P_DENTAL varchar2,
P_IVR varchar2
) RETURN table_trdelclvr_QADJ
AS
test_type table_trdelclvr_QADJ;
BEGIN
SELECT type_trdelclvr_QADJ(
count(1),
TO_CHAR(TRUNC(system_date, 'MM'),'YYYY'),
TO_CHAR(TRUNC(system_date, 'MM'),'YYYY-MM'),
sum(decode(document_category, P_CLAIM ,1,0)),
sum(decode(document_category, P_CIW ,1, P_PP ,1,0)),
sum(decode(document_source,P_PAPER,1,0)),
sum(decode(document_source, P_MBR,decode(edi_app_source,P_MBR,1,0),0)
+ decode(document_source, P_EDI, decode(edi_app_source, P_MBR_NatApp, 1,0),0)),
sum(decode(document_source, P_EDI, decode(edi_app_source, P_CDAnet_DialUp, 1,0),0)),
sum(decode(document_source, P_EDI,decode(edi_app_source, P_CDAnet_IP, 1,0),0)
+ decode(document_source, P_EDI, decode(edi_app_source, P_CDAnet_ICA, 1,0),0)),
sum(decode(document_source, P_EDI, 1,0))
)
BULK COLLECT INTO test_type
FROM blu_adj_statistics adj
WHERE system_date >= P_START_DATE
AND system_date < P_END_DATE + 1
AND claim_type = P_DENTAL
AND claim_iteration = 1
AND document_source <> P_IVR
AND hsa_indicator is null
GROUP BY TRUNC(system_date, 'MM')
ORDER BY TRUNC(system_date, 'MM');
RETURN test_type;
END;
END P_trdelclvr01;
/
Учитывая примерные данные:
CREATE TABLE blu_adj_statistics (
system_date DATE,
document_category VARCHAR2(50),
document_source VARCHAR2(50),
claim_type VARCHAR2(50),
claim_iteration NUMBER,
hsa_indicator NUMBER,
edi_app_source VARCHAR2(50)
)
INSERT INTO blu_adj_statistics VALUES (SYSDATE, 'A', 'B', 'C', 1, NULL, 'D');
Затем:
DECLARE
v_data table_trdelclvr_QADJ;
BEGIN
v_data := P_trdelclvr01.fn_trdelclvr_QADJ(
P_CLAIM => 'A',
P_CIW => 'A',
P_PP => 'X',
P_PAPER => 'B',
P_MBR => 'B',
P_EDI => 'D',
P_MBR_NatApp => 'D',
P_CDAnet_DialUp => 'D',
P_CDAnet_IP => 'D',
P_CDAnet_ICA => 'D',
P_START_DATE => TRUNC(SYSDATE),
P_END_DATE => TRUNC(SYSDATE),
P_DENTAL => 'C',
P_IVR => 'A'
);
FOR i IN 1 .. v_data.COUNT LOOP
DBMS_OUTPUT.PUT_LINE(
v_data(i).TOTAL_CLAIMS
||', '||v_data(i).calculated_year
||', '||v_data(i).MTH
||', '||v_data(i).CLAIM
||', '||v_data(i).CIW
||', '||v_data(i).PAPER
||', '||v_data(i).MBRECLAIM
||', '||v_data(i).PRVRDIALUP
||', '||v_data(i).PRVRIP
||', '||v_data(i).ELECTRONIC
);
END LOOP;
END;
/
Выходы:
1, 2024, 2024-08, 1, 1, 1, 0, 0, 0, 0