DeepEdit!

Программирование баз данных на Oracle, техническая документация, литература, статьи и публикации

  • Увеличить размер шрифта
  • Размер шрифта по умолчанию
  • Уменьшить размер шрифта

Определение динамической политики

В предыдущем разделе мы говорили о политике, которая возвращает строку предиката, являющуюся константой, например SAL <= 1500.
В реальной жизни такие сценарии используются не слишком часто, за исключением некоторых специализированных приложений, таких как склады. В большинстве случаев необходима фильтрация пользователей, выдающих запросы. Например, в приложении управления персоналом может потребоваться, чтобы пользователь видел только свои собственные записи, а не все записи таблицы. Это динамическое требование, так как оно должно проверяться для каждого пользователя, входящего в систему. Функцию политики можно переписать следующим образом:

В строке 9 предикат сравнивает значение столбца ENAME со значением USER, то есть с именем текущего зарегистрированного пользователя. Если пользователь Martin (если помните, Martin - это имя одного из служащих в таблице EMP) входит в систему и выполняет выборку из таблицы, он видит всего одну строку - свою собственную.

Давайте теперь несколько расширим задачу: пусть Martin видит не только собственную запись, но и записи для всего своего отдела. В этом случае функция политики будет такой:


Необходимо сделать еще один шаг. В предыдущем фрагменте кода функция осуществляла выборку из таблицы EMP (строки 10-13). Однако таблица защищена политикой RLS, функция которой принадлежит пользователю HR. Будучи выполненной с привилегиями пользователя HR, она не найдет ни одной строки, так как сотрудника с именем HR не существует, что делает предикат некорректным. Существуют два способа решения этой проблемы:
Выдать пользователю HR специальную привилегию, с тем чтобы к нему не применялись политики RLS, или
Внутри функции политики указать, что если вызывающий ее пользователь является владельцем схемы, то для него проверку проводить не следует.
При использовании первого подхода нет необходимости в изменении функции политики. От имени администратора базы данных выдаем специальную привилегию пользователю HR:

Тем самым для пользователя HR из приложения будут удалены все политики. Этот подход следует использовать с большой осторожностью, так как будут отменены все политики - для всех таблиц. Осознавая, какую брешь это создает в модели безопасности, мы бы порекомендовали не применять данный подход для обычных владельцев схем.
Второй подход заключается в создании специальной схемы, например RLSOWNER, в которой будут созданы все политики RLS, и которой будут принадлежать все функции политики безопасности. Только этот пользователь, и никакие другие, получает системную привилегию EXEMPT ACCESS POLICY. Функция политики принадлежит RLSOWNER, поэтому PL/ SQL-блок создания политики будет выглядеть следующим образом (его сможет запускать любой пользователь, имеющий привилегии EXECUTE на пакет DBMS_RLS):


Если используется второй подход, то логика обхода фильтра для владельца схемы должна быть реализована в функции политики. Этот блок кода также может быть запущен любым пользователем, имеющим привилегии EXECUTE на пакет DBMS_RLS.

Эта версия функции очень похожа на предыдущие. Новые строки выделены жирным шрифтом (строка 10). Здесь проверяется, является ли вызывающий пользователь владельцем таблицы. Если это так, возвращается NULL (строка 12). Значение NULL в предикате, возвращенном функцией, эквивалентно полному отсутствию политики, то есть строки не фильтруются.
Пользователь Martin выполняет тот же запрос, что и раньше:


EMPNO
ENAME
JOB
MGR
HIREDATE
SAL
COMM
DEPTNO
7499
ALLEN
SALESMAN
7698
20-FEB-81
1,600
300
30
7521
WARD
SALESMAN
7698
22-FEB-81
1,250
500
30
7654
MARTIN
SALESMAN
7698
28-SEP-81
1,250
1,400
30
7698
BLAKE
MANAGER
7839
01-MAY-81
2,850

30
4 4 8 7
TURNER
SALESMAN
7698
08-SEP-81
1,500
0
30
7900
JAMES
CLERK
7698
03-DEC-81
950

30
6 rows selected.

Обратите внимание, что все возвращенные строки относятся к отделу пользователя Martin - 30.
Как видите, функция политики является важнейшим элементом создания политики RLS. Политика будет применять к строкам фильтры на основании значения любого предиката, возвращенного функцией, необходима лишь синтаксическая корректность. При помощи функций политики безопасности вы можете создавать весьма замысловатые и сложные предикаты.
Точно так же можно применять фильтры RLS для любой таблицы базы данных. Например, можно создать политику для таблицы DEPT:

Та же самая функция, AUTHORIZED_EMPS, используется в качестве функции политики. Функция возвращает предикат DEPTNO = deptno, поэтому она может использоваться в таблице DEPT, как и в любой другой таблице, содержащей столбец DEPTNO.
Таблица, в которой нет столбца DEPTNO, может содержать другой столбец, являющийся внешним ключом для таблицы EMP. Например, в таблице BONUS есть столбец ENAME, который связан с таблицей EMP. Перепишем нашу функцию политики следующим образом:


Определяем политику для таблицы BONUS посредством следующей функции политики; тем самым политика RLS будет введена в действие и для нее:

Так можно определить политики RLS для всех связанных таблиц базы данных, находящихся в зависимости от данной. В связи с тем, что описанная функциональность обеспечивает персональное представление таблиц базы данных на основании характеристик пользователя или каких-то других параметров (например, времени дня или IP-адреса), ее называют виртуальной частной базой данных (Virtual Private Database (VPD)).
 









jAntivirus