2013-02-09 4 views
2

Вот что я читал:PostgreSQL ВЫБРАТЬ-ПРАВИЛ, права наследования, на уровне строк

http://www.postgresql.org/docs/9.2/static/rules-views.html 
http://www.postgresql.org/docs/9.2/static/rules-privileges.html 

Моя цель состоит в том, чтобы позволить Войти, чтобы видеть только те строки, что «владеет», так сказать.

Допустим, каждая таблица в базе данных наследует из этой таблицы:

create table WHOAMI 
    ( 
     tenant varchar(25) not null default current_user 
    ); 

, например:

create table FOO 
    (
    id int primary key, 
    invoicedate date 
    ) inherits (WHOAMI); 

    insert into FOO(id, invoicedate) values(1,now()::date); 

    select * from FOO; 

    --abclogin|1|2013-02-01 

Есть ли такая вещь в PostgreSQL как выбрать правило уровня схемы, влияя на все таблицы и представления в схеме, которая добавляет к каждому запросу, вставке, обновлению или удалению условие, которое говорит, по сути, ..AND WHERE TENANT = current_user? Если такого глобального правила нет, можно ли это сделать по таблице за таблицей? У меня нет никаких успехов в моих попытках, и я, вероятно, неправильно понимаю некоторые вещи о том, как создаются правила. Вот то, что я пытался сделать:

Я пытаюсь создать избранную-правило:

CREATE RULE "_RETURN" AS ON SELECT TO FOO DO INSTEAD 
    SELECT * FROM FOO where tenant = current_user; 

но получаю эту ошибку: ERROR: could not convert table "foo" to a view because it has indexes

Я пытаюсь создать представление с безопасности- барьер:

 CREATE VIEW TENANTFOO WITH (security_barrier) AS 
     SELECT * FROM FOO WHERE tenant=current_user; 

, а затем попытаться вставки:

 insert into TENANTFOO(id,invoicedate) 
     values(2,(now()::date); 

но получаю эту ошибку:

 `ERROR: cannot insert into view "tenantfoo" 
     HINT: You need an unconditional ON INSERT DO INSTEAD rule 
     or an INSTEAD OF INSERT trigger.` 

Какие шаги необходимы для реализации барьеров безопасности на уровне строк на столах?

ответ

2

В вашем последнем примере, вам нужно запустить INSERTк таблице или создать еще одно правило: ON INSERT TO TENANTFOO DO INSTEAD.

1

То, что вы ищете, является Row-Level Security, он еще не доступен, хотя some work had been done on this thing. Я надеюсь, что этот патч внесет его в предстоящий выпуск 9.3.

Между тем, я работал со следующим дизайном некоторое время назад.

Требования были схожими, виды должны были поставлять только те ряды, которые предназначены для CURRENT_USER.В нашем доступе случае было сделано довольно просто: таблица, в которой указано, имеет ли данный пользователь доступ к данному отношению и данный ключ, чему-л, как:

CREATE TABLE user_grants (
    user_id  integer, 
    entity_name text, -- should exist in pg_class 
    entity_id integer 
); 

Тогда, скажем, для tasks, был создан следующий вид :

CREATE VIEW tasks_v AS 
SELECT t.* 
    FROM tasks t 
    JOIN user_grants ug ON t.user_id = ug.user_id 
    AND ug.entity_name='TASKS' AND ug.entity_id = t.task_id; 

Конечно, установка не является полной без ряда вспомогательных функций, триггеров и правил. Также необходимо было убедиться, что всегда предоставляются разумные привилегии по умолчанию.

 Смежные вопросы

  • Нет связанных вопросов^_^