Привилегии Muti-схемы для запуска таблиц в базе данных Oracle - PullRequest
3 голосов
/ 17 апреля 2010

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

Error: ORA-00942: table or view does not exist

при попытке запроса таблиц вне моей схемы.

EDIT

Приношу свои извинения за то, что не предоставил как можно больше информации в первый раз. У меня сложилось впечатление, что этот вопрос был более простым.

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

У учетной записи пользователя, которую я использую для создания триггера, есть разрешения на независимый запуск запросов. На самом деле мой триггер распечатал запрос, который я пытаюсь выполнить, и смог выполнить его самостоятельно.

Следует также отметить, что я строю запрос динамически с помощью оператора EXECUTE IMMEDIATE. Вот пример:

CREATE OR REPLACE TRIGGER MAIN_SCHEMA.EVENTS
BEFORE INSERT
ON MAIN_SCHEMA.EVENTS REFERENCING OLD AS OLD NEW AS NEW
FOR EACH ROW
DECLARE 
    rtn_count NUMBER := 0;
    table_name VARCHAR2(17) := :NEW.SOME_FIELD;
    key_field VARCHAR2(20) := :NEW.ANOTHER_FIELD;
BEGIN
    CASE
        WHEN (key_field = 'condition_a') THEN
            EXECUTE IMMEDIATE 'select count(*) from OTHER_SCHEMA_A.'||table_name||' where KEY_FIELD='''||key_field||'''' INTO rtn_count;
        WHEN (key_field = 'condition_b') THEN
            EXECUTE IMMEDIATE 'select count(*) from OTHER_SCHEMA_B.'||table_name||' where KEY_FIELD='''||key_field||'''' INTO rtn_count;
        WHEN (key_field = 'condition_c') THEN
            EXECUTE IMMEDIATE 'select count(*) from OTHER_SCHEMA_C.'||table_name||' where KEY_FIELD='''||key_field||'''' INTO rtn_count;
    END CASE;

    IF (rtn_count > 0) THEN
        -- change some fields that are to be inserted
    END IF; 
END;

Сбои шва триггера на ИСПОЛНИТЕЛЬНО НЕМЕДЛЕННО с ранее упомянутой ошибкой.

EDIT

Я провел еще несколько исследований и могу предложить больше разъяснений.

Учетная запись пользователя, которую я использую для создания этого триггера, не MAIN_SCHEMA или какая-либо из OTHER_SCHEMA_Xs. Используемая мной учетная запись (ME) получает права доступа к соответствующим таблицам через самих пользователей схемы. Например (USER_TAB_PRIVS):

GRANTOR        GRANTEE TABLE_SCHEMA    TABLE_NAME PRIVILEGE GRANTABLE HIERARCHY
MAIN_SCHEMA    ME       MAIN_SCHEMA    EVENTS     DELETE    NO        NO
MAIN_SCHEMA    ME       MAIN_SCHEMA    EVENTS     INSERT    NO        NO
MAIN_SCHEMA    ME       MAIN_SCHEMA    EVENTS     SELECT    NO        NO
MAIN_SCHEMA    ME       MAIN_SCHEMA    EVENTS     UPDATE    NO        NO
OTHER_SCHEMA_X ME       OTHER_SCHEMA_X TARGET_TBL SELECT    NO          NO

И у меня есть следующие системные привилегии (USER_SYS_PRIVS):

USERNAME   PRIVILEGE            ADMIN_OPTION
ME         ALTER ANY TRIGGER    NO
ME         CREATE ANY TRIGGER   NO
ME         UNLIMITED TABLESPACE NO

И это то, что я нашел в документации Oracle:

Для создания триггера у другого пользователя Схема или ссылаться на таблицу в другая схема из триггера в вашем схема, вы должны иметь СОЗДАТЬ ЛЮБОЙ Системная привилегия TRIGGER. С этим привилегия, триггер может быть создан в любой схеме и может быть связан с любым столом пользователя. К тому же, пользователь, создающий триггер, должен также имеют привилегию EXECUTE на упомянутые процедуры, функции или пакеты.

Здесь: Oracle Doc

Так что мне кажется, что это должно сработать, но я не уверен насчет "привилегии EXECUTE", на которую она ссылается в документе.

Ответы [ 3 ]

5 голосов
/ 17 апреля 2010

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

Синтаксис довольно прост: выдает схему владельца

grant select, insert on my_table to you
/

В качестве альтернативы учетная запись с привилегией GRANT ANY (например, администратор баз данных) может передавать привилегии объектам любого пользователя.

grant select, insert on apc.my_table to you
/

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

Итак, если вы попросите другого владельца схемы предоставить вам необходимые привилегии, вы сможете создать свой триггер.

редактировать

При ссылке на объект в другой схеме нам нужно квалифицировать объект с именем схемы ....

insert into apc.whatever_table  values ...

или же нам нужно создать для него синоним

create synonym whatever for apc.whatever_table;
2 голосов
/ 17 апреля 2010

Мне кажется, что кто-то должен добавить очевидное - в таблице другой схемы должно быть указано имя схемы или необходим частный / публичный синоним. Интересно, если исходная проблема была просто проблемой разрешения имени. Если нет, ответ APC является хорошим объяснением модели безопасности Oracle.

0 голосов
/ 20 апреля 2010

Вы должны выполнить это для каждой таблицы и схемы:

grant select on OTHER_SCHEMA_%.table_name to MAIN_SCHEMA;
...