Oracle: регулирование доступа к отдельным строкам таблиц - Заводим метки доступа
ОГЛАВЛЕНИЕ
Заводим метки доступа
Заданные в рамках политики EMPSEC_POLICY уровни секретности используем для формирования меток доступа. Именно метки и будут регламентировать доступ к строкам таблицы. В нашем простейшем случае каждая метка соответствуют попросту уровню секретности:
BEGIN
SA_LABEL_ADMIN.CREATE_LABEL
(POLICY_NAME => 'EMPSEC_POLICY'
, LABEL_TAG => 10000
, LABEL_VALUE => 'OPEN'
, DATA_LABEL => TRUE);
SA_LABEL_ADMIN.CREATE_LABEL
(POLICY_NAME => 'EMPSEC_POLICY'
, LABEL_TAG => 20000
, LABEL_VALUE => 'LIMITED'
, DATA_LABEL => TRUE);
END;
/
Номер метки LABEL_TAG имеет технический смысл, выбирается произвольно и безотносительно к номерам уровней. Его даже можно порождать автоматически специальной функцией TO_DATA_LABEL. Значение TRUE для DATA_LABEL указывает, что меткой можно будет помечать строки таблиц.
Приписываем метки доступа пользователям
Пользователю EMPLOYEE дадим право доступа только к «открытым» строкам, а пользователю HEAD – к «открытым» и «ограниченного пользования»:
BEGIN
SA_USER_ADMIN.SET_USER_LABELS
(POLICY_NAME => 'EMPSEC_POLICY'
, USER_NAME => 'EMPLOYEE'
, MAX_READ_LABEL => 'OPEN');
SA_USER_ADMIN.SET_USER_LABELS
(POLICY_NAME => 'EMPSEC_POLICY'
, USER_NAME => 'HEAD'
, MAX_READ_LABEL => 'LIMITED');
END;
/
Приписываем метки доступа строкам
Для этого сначала «применим политику доступа» к таблице PHONE в целом:
BEGIN
SA_POLICY_ADMIN.APPLY_TABLE_POLICY
(POLICY_NAME => 'EMPSEC_POLICY'
, SCHEMA_NAME => 'SCOTT'
, TABLE_NAME => 'PHONE'
, TABLE_OPTIONS => 'LABEL_DEFAULT,
READ_CONTROL, WRITE_CONTROL');
END;
/
В результате она автоматически окажется пополнена столбцом EMP_DATA_LABEL, указанным в самом начале для нашей политики EMPSEC_POLICY. Его можно легко наблюдать командой SQL*Plus DESCRIBE. Если же в параметре TABLE_OPTIONS в число свойств через запятую включить HIDE, новый служебный столбец обычным пользователям виден не будет. В этом же параметре свойство WRITE_CONTROL можно для нашего случая спокойно опустить.
Теперь появилась возможность разметить конкретными метками конкретные строки:
UPDATE scott.phone
SET emp_data_label = CHAR_TO_LABEL('EMPSEC_POLICY',
'OPEN');
UPDATE scott.phone
SET emp_data_label = CHAR_TO_LABEL('EMPSEC_POLICY',
'LIMITED')
WHERE empno IN (SELECT empno
FROM scott.emp
WHERE job IN ('MANAGER', 'PRESIDENT'));
Вместо обращения к функции
CHAR_TO_LABEL('EMPSEC_POLICY', 'OPEN')
можно было сразу указать число 10000, номер метки, так как именно число будет храниться в поле метки фактически; аналогично же и во второй команде UPDATE. Однако для содержательной ясности удобнее воспользоваться функцией.