2012-01-26 1 views
1

これは、Oracleの行レベルのセキュリティ機能についての古い質問へのフォローアップですが、もともと、元のコードが複数の結果の場合を返しますので、私は変更する場合は、必要に応じhereOracleのRLS/VPD

を議論しましたユーザーは複数のプロジェクトにアタッチされていました。だから今私は、複数の場所(すなわち、project = project_1またはproject = project_2)がセキュリティポリシーに渡されて、動作するようにする必要があります。私は、forループを使用して、それが動作していないことにより、コードを変更しようとしたこれを行うには...

--create function 
create or replace function 
    table_access_policy 
    (obj_schema varchar2, obj_name varchar2) return varchar2 

is     

v_project_temp varchar2(9000); 

begin    

v_project_temp:= 'declare v_project varchar2(9000); 

begin 
v_project:= ''project = ''; 

for c in (select admin.access_list.project from admin.access_list where upper(admin.access_list.user_id) = SYS_CONTEXT (''USERENV'', ''SESSION_USER'')) 

loop 

v_project := v_project || c.project_sn || '' or project = '' ; 

end loop; 

v_project := rtrim(v_project, '' or project = ''); 

end;'; 

return v_project_temp; 

end; 

機能はセーブ/エラーなしで実行されますが、それは呼ばれていたときに政策自体がエラーをスローします。これを行うより良い方法はありますか?

答えて

2

PL/SQLを文字列に入れるのではなく、それを実行してv_project文字列を作成して戻す必要があります。以下のような:

--create function 
create or replace function 
    table_access_policy 
    (obj_schema varchar2, obj_name varchar2) return varchar2  
is 
    v_project varchar2(9000); 
begin    
    v_project:= 'project = '; 
    for c in (select admin.access_list.project from admin.access_list where upper(admin.access_list.user_id) = SYS_CONTEXT ('USERENV', 'SESSION_USER')) 
    loop 
    v_project := v_project ||''''|| c.project_sn ||''''|||| ' or project = ' ; 
    end loop;  
    v_project := rtrim(v_project, ' or project = ');  
    return v_project;  
end; 

のようなSQL文でwhere後に最終的にv_projectに表示される値は、直進します:

select * from data; 

はその

select * from date where <v_project>; 

だけそうなものになるだろうwhereに従うと、v_ projectに入るはずです。

+0

お返事ありがとうございます。私はそれをセキュリティポリシーに伝えることができないことを知りませんでした。私は、クエリを渡さなければならないと仮定し、ポリシーはクエリをリアルタイムで実行しなければなりませんでした。 残念ながら、私はまだ "ポリシー述語にはエラーがあります"というメッセージが表示されます。 "Create function ..."を使わずにコードを手動で実行しようとしましたが、期待通りの結果が返されました。何か案は? – AFJ

+0

私は 'USERENV'と' SESSION_USER'の周りに余分な引用符を残していました。私はそれらを削除する答えを編集しました。それが動作するかどうかを確認します。 –

+0

私はあなたの応答に余分な引用符をつかんで、早く削除しました。まだ運がない – AFJ