表に述語関数を実装しようとしています。パッケージと述語関数は問題なくコンパイルされますが、テーブルを選択するとこのエラーが発生します。VPD述語関数の実装 - ORA-28110:ポリシー関数またはパッケージにエラーがあります
SELECT * FROM MSGG_GUIDES;
ORA-28110: policy function or package VPD674.MSGG_SECURITY_POLICY has error
ここに定義した関数です。以下のコードは、その関数が一部であるパッケージ本体からのスニペットです。私の最終目標は、この関数がifステートメントで見る4つのテーブルのポリシーを定義することです。
function MSGG_SECURITY_POLICY (schema_in varchar2, NAME_IN varchar2)
return varchar2
IS
where_stmt varchar2(5000);
BEGIN
if schema_in='VPD674' and NAME_IN='MSGG_GUIDES' THEN
where_stmt := 'PERSON_ID = MSGG_SESSION.get_user_id';
elsif schema_in='VPD674' and NAME_IN='MSGG_ORDERS' THEN
where_stmt := 'ORDERING_PERSON = MSGG_SESSION.get_user_id';
elsif schema_in='VPD674' and NAME_IN='MSGG_SIGHTING_REPORTS' THEN
where_stmt := 'PERSON_ID = MSGG_SESSION.get_user_id';
elsif schema_in='VPD674' and NAME_IN='MSGG_TRIP_HISTORY' THEN
where_stmt := 'GUIDE_ID = MSGG_SESSION.get_user_id';
end if;
return (where_stmt);
これは、問題のテーブル(選択しているもの)に適用されます。
BEGIN
DBMS_RLS.ADD_POLICY(
object_schema => 'VPD674',
object_name => 'MSGG_GUIDES',
policy_name => 'MSGG_SECURITY_POLICY1',
function_schema => 'VPD674',
policy_function => 'MSGG_SECURITY_POLICY',
statement_types => 'SELECT');
END;
/
なぜ選択がエラーになるのでしょうか?関数は問題なくコンパイルされます。パッケージ、関数、またはポリシーの "show errors"コマンドは、 "no errors"を返します。トラブルシューティングの手順としてget_user_id関数を使用しないハードコードされたバージョンの関数を試しましたが、同じエラーが表示されます。私はまた、パッケージの外で関数を作成してポリシーに適用しようとしましたが、同じエラーが発生しました。
完全な開示のために、以下はパッケージ仕様書および本文作成スクリプト全体です。上記のハードコーディングされた関数のバージョンが表示されます(MSGG_SECURITY_POLICY_G)。
CREATE OR REPLACE PACKAGE MSGG_SESSION AS
PROCEDURE authenticate (current_username varchar2, current_password varchar2);
function get_user_id
RETURN NUMBER;
function MSGG_SECURITY_POLICY (schema_in varchar2, NAME_IN varchar2)
RETURN VARCHAR2;
function MSGG_SECURITY_POLICY_G (schema_var IN VARCHAR2, table_var IN VARCHAR2)
RETURN VARCHAR2;
end MSGG_SESSION;
/
CREATE OR REPLACE PACKAGE BODY MSGG_SESSION AS
person_id_var NUMBER;
function get_user_id
return NUMBER IS BEGIN
return(person_id_var);
end get_user_id;
PROCEDURE authenticate (current_username varchar2, current_password varchar2) IS BEGIN
SELECT personID
INTO person_id_var
FROM MSGG_USER
WHERE (current_username=username and current_password=password);
DBMS_OUTPUT.put_line(person_id_var);
END authenticate;
function MSGG_SECURITY_POLICY (schema_in varchar2, NAME_IN varchar2)
return varchar2
IS
where_stmt varchar2(5000);
BEGIN
if schema_in='VPD674' and NAME_IN='MSGG_GUIDES' THEN
where_stmt := 'PERSON_ID = MSGG_SESSION.get_user_id';
elsif schema_in='VPD674' and NAME_IN='MSGG_ORDERS' THEN
where_stmt := 'ORDERING_PERSON = MSGG_SESSION.get_user_id';
elsif schema_in='VPD674' and NAME_IN='MSGG_SIGHTING_REPORTS' THEN
where_stmt := 'PERSON_ID = MSGG_SESSION.get_user_id';
elsif schema_in='VPD674' and NAME_IN='MSGG_TRIP_HISTORY' THEN
where_stmt := 'GUIDE_ID = MSGG_SESSION.get_user_id';
end if;
return (where_stmt);
end MSGG_SECURITY_POLICY;
FUNCTION MSGG_SECURITY_POLICY_G(
schema_var IN VARCHAR2,
table_var IN VARCHAR2
)
RETURN VARCHAR2
IS
return_val VARCHAR2 (400);
BEGIN
return_val := 'PERSON_ID = ''14''';
RETURN return_val;
END MSGG_SECURITY_POLICY_G;
end MSGG_SESSION;
/