Гость
Форумы / Oracle [игнор отключен] [закрыт для гостей] / Вопрос по секьюрити / 7 сообщений из 7, страница 1 из 1
05.12.2002, 14:44
    #32076152
johnRSDN
Участник
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Вопрос по секьюрити
Господа здравствуйте.

Есть потребность в реализации секьюрити такого характера:

Пусть у нас существует таблица и несколько пользователей. В этой одной таблице хранятся данные всех пользователей. Непосредственно права на операции с ней имеет _только_ админ и создается она админом, и данные туда тоже заносятся только им, и селект гонять может только он.

Необходимо предоставить пользователям механизм , который бы позволял, например, выбирать(возможно добавлять, удалять, модифицировать) информацию из этой таблицы. НО сделать это надо так, чтобы пользователь, работающий с таблицей видел только свои данные и не видел чужих. И при этом не просто не видел, но и не имел физической возможности доступа к ним отказавшись, скажем от приложения, которое работает с данной базой, а получив доступ туда просто ручками через СКЛ консольку. Соотв. для этого в таблице будут естественно поля типа ИД_ЮЗЕР.
Я вот что думаю. Если бы это было возможно, то организовать сей механизм так:

Админ создает таблицу. Когда требуется дать юзеру права на выборку данных из неё, то Админ создает ХранимуюПроцедуру (ХП), которая по ИД Юзера осуществляет в выражении WHERE контроль выбираемых значений, чтобы в конечную выборку попадали только те значения, которые принадлежат пользователю.
Далее.. Пользователь работает с этой таблицей только с помощью ХП, права на выполнение которой дает ему Админ, потому что прямых грантов на выборку данных ему не дано. И эта ХП единственный способ получить доступ к данным. Таким образом он никак не сможет при всем желании увидеть данные др. юзера.

В данном примере ХП я представил в виде объекта посредника, который может запускаться юзером, которому даны права на его выполнение, однако этот объект (в данном случае ХП) запустившись работает в контексте своего создателя, т.е. админа, а потому имеет доступ к таблице. Т.е. в этом случае ХП выступает в роли некоторого секьюрити-моста.

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

Если понятен смысл подобных объяснений, то подскажите как можно было бы реализовать подобных механизм секьюрити. Т.е. с помощью чего-либо ( например в описанном выше примере это ХП) эмулировать для юзеров работающих физически с одной таблицей различную её "область видимости" , создавая тем самым эффект, что у каждого юзера своя таблица.

Спасибо.
...
Рейтинг: 0 / 0
05.12.2002, 15:30
    #32076194
Denis Popov
Участник
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Вопрос по секьюрити
Функция, процедура, пакет по умолчанию имеют права создателя, а не вызывающего. Для того. чтобы они работали с правами вызывающего, требуется указать authid current_user:

http://download-west.oracle.com/docs/cd/A97630_01/server.920/a96540/statements_110a.htm#2068964

Представления- второй способ row-level security:
http://www.interface.ru/fset.asp?Url=/oracle/ks.htm

Еще посмотри на Fine Granted Access Control:
http://www.interface.ru/fset.asp?Url=/oracle/ks_1.htm
http://www.oracle.com/ru/oramag/august2001/index.html?dev_tkyte.html
...
Рейтинг: 0 / 0
05.12.2002, 15:40
    #32076204
AIR
AIR
Гость
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Вопрос по секьюрити
В Oracle 8i мы осуществляем это через детальный контроль доступа. Не знаю только есть такакя возможность в предыдущих версиях.
Таблица:
CREATE TABLE PRIMER(
OBJ_ID NUMBER(18) PRIMARY KEY,
ID_USER VARCHAR2(32),
USER_DATA VARCHAR2(32))
В нее след- данные:
OBJ_ID ID_USER USER_DATA
---------------------------------------
1 FORTMETA 1111
2 FORTMETA 22222
3 SCOTT 333

Для осуществления того чтоб FORTMETA видел только данные FORTMETA, если он залогинился под ним надо создать пакет:
CREATE OR REPLACE PACKAGE PRIMER_PKG IS
FUNCTION Get_Data_From_Primer (p_schema in varchar2,p_object in varchar2) return varchar2;
END PRIMER_PKG;
/
CREATE OR REPLACE PACKAGE BODY PRIMER_PKG IS
FUNCTION Get_Data_From_Primer (p_schema in varchar2,p_object in varchar2) return varchar2 IS
BEGIN
IF USER='ADMIN' THEN
RETURN '';
ELSE
RETURN 'ID_USER=USER';
END IF;
END;
END PRIMER_PKG;
/

Далее создать Policy для таблицы PRIMER, связанный с указанной пакетной функцией:
BEGIN
dbms_rls.ADD_POLICY(
object_schema=>'ADMIN',
object_name=>'PRIMER',
policy_name=>'primer_plc',
function_schema=>'ADMIN',
policy_function=>'PRIMER_PKG.Get_Data_From_Primer',
statement_types=>'select,insert,update,delete',
update_check=>TRUE);
END;

После этого при логине под FORTMETA мы получим след. результат
OBJ_ID ID_USER USER_DATA
---------------------------------------
1 FORTMETA 1111
2 FORTMETA 22222

с помощью какого бы мы инструмента не обращались к данным.
А под пользователем ADMIN мы увидим все данные.
Причем данное ограничение действует и на обновление и вставку данных
statement_types=>'select,insert,update,delete',

В случае если оракл не поддерживает данной возможности то работа только через представления и навешенные на них INSTEAD OFF триггера.
С уважением Ильяс.
...
Рейтинг: 0 / 0
05.12.2002, 16:21
    #32076237
softy
Участник
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Вопрос по секьюрити
Для того что-бы из таблицы пользователь смог выбирать только свои данные, для этого в таблицу вводится столбец, определяющий пользователя, каким угодно образом: именем, его UID или через отдельную таблицу пользователей - не важно. Главное есть идетификатор пользователя, который определяет его однозначно.
Таблица должна быть помещена в схему, которая не является собственной не для одного из пользователей, иначе у него будут в любом случае права к таблице. Для этого создаётся отдельная схема:
Код: plaintext
1.
2.
create user work identified by work default tablespace usr temporary tablespace temp;
grant connect, resource to work


От имени work создаём таблицу:
Код: plaintext
1.
2.
3.
4.
5.
create table test_work
( id_user VARCHAR2( 100 ),
  num_order VARCHAR2( 50 ),
  pay_order NUMBER( 32 , 4 ),
  date_order DATE)

Допустим юзера заполняет таблицу ордеров, в которой есть номер,сумма,дата ордера. Поле id_user означает какой пользователь вносит данные.
Замечание: прав у пользователей на таблицу нет никаких, поэтому они не могут ничего сделать.

Создадим двух рабочих юзера(от имени SYS):
Код: plaintext
1.
2.
3.
4.
create user user1 identified by user1 default tablespace usr temporary tablespace temp;
create user user2 identified by user1 default tablespace usr temporary tablespace temp;

grant connect to user1, user2;


Создадим пакет для регистрации юзеров(от имени work):
Код: plaintext
1.
2.
3.
4.
5.
6.
7.
8.
9.
10.
11.
12.
13.
14.
15.
16.
17.
18.
19.
 create or replace package ses_mod as
  UserId VARCHAR2( 100 ):='';
  procedure setUserId;
  function getUserId return varchar2;
 end ses_mod;

 create or replace package body ses_mod as
  procedure setUserId as
   user_v VARCHAR2( 100 );
  begin
    select user into user_v from dual;
    UserId:=user_v;
  end;

  function getUserId return  varchar2 as
  begin
   return UserId;
  end getUserId;
 end ses_mod;


Гранты на пакет:
Код: plaintext
1.
GRANT EXECUTE ON work.ses_mod TO user1,user2;


Создадим вью(от имени work):
Код: plaintext
1.
2.
3.
4.
5.
6.
7.
8.
9.
create or replace view test_work_v as
select
  num_order,
  pay_order,
  date_order
 from
  test_work
 where
  id_user = ses_mod.getUserId();


дадим право прсомотра вью(от имени work):
Код: plaintext
1.
grant select on test_work_v to user1, user2;


Теперь запрос для получения данных:
Код: plaintext
1.
2.
3.
4.
select 
 * 
from
 work.test_work_v



Смысл в следующем: Пользователи смогут получить данные, если они зарегистрируются. Для регистрации используется пакет ses_mod и процедура setUserId. Вью возвратит данные только для текущего юзера, так как идёт проверка id_user через функцию getUserId(). Добавим в ручную для понимания идеи данные в таблицу, как-будто юзера уже их туда занесли:
Код: plaintext
1.
2.
3.
4.
5.
6.
insert into test_work values('USER1', 1 , 2000 ,sysdate);
insert into test_work values('USER1', 2 , 2500 ,sysdate);
insert into test_work values('USER1', 3 , 1200 ,sysdate);
insert into test_work values('USER2', 4 , 3000 ,sysdate);
insert into test_work values('USER2', 5 , 4500 ,sysdate);
commit;


Теперь проверим как работает вью:
Код: plaintext
1.
2.
3.
4.
5.
6.
7.
8.
9.
10.
11.
connect user1/user1@test;
SQLWKS> connect work@test
Связь установлена.

select * from work.test_work_v;
SQLWKS> select * from work.test_work_v;
NUM_ORDER                                          PAY_ORDER  DATE_ORDER          
 -------------------------------------------------- ---------- --------------------
 
Выбрано  0  строк.
SQLWKS> 


Видим что данные не получены. Теперь зарегистрирем пользьвателя:
Код: plaintext
1.
2.
3.
execute work.ses_mod.setUserId();
SQLWKS> execute work.ses_mod.setUserId();
Предложение обработано.


Попробуем получит данные еще раз:
Код: plaintext
1.
2.
3.
4.
5.
6.
7.
8.
9.
10.
select * from work.test_work_v;

SQLWKS> select * from work.test_work_v;
NUM_ORDER                                          PAY_ORDER  DATE_ORDER          
 -------------------------------------------------- ---------- --------------------
 
 1                                                          2000   05 . 12 . 02             
 2                                                          2500   05 . 12 . 02             
 3                                                          1200   05 . 12 . 02             
Выбрано  3  строк.


Данные есть. Примерно делается так. Это в общих чертах.
...
Рейтинг: 0 / 0
05.12.2002, 22:39
    #32076436
vskv
Участник
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Вопрос по секьюрити
А после добавления в определиние вьюшки "WITH CHECK OPTION", то юзвери смогут апдейтить вьюшку, но не смогут выползти за этот самый CHECK OPTION.
...
Рейтинг: 0 / 0
06.12.2002, 05:09
    #32076470
Виктор
Участник
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Вопрос по секьюрити
Я бы посоветовал для данной задачи использовать Fine Granted Access Control (Детальный контроль доступа). Поразбираться, конечно придется, но , как мне кажется, дело того стоит. Во всяком случае, у меня задача, похожая на твою, решается именно так.
...
Рейтинг: 0 / 0
06.12.2002, 10:32
    #32076563
Славик
Участник
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Вопрос по секьюрити
...
Рейтинг: 0 / 0
Форумы / Oracle [игнор отключен] [закрыт для гостей] / Вопрос по секьюрити / 7 сообщений из 7, страница 1 из 1
Целевая тема:
Создать новую тему:
Автор:
Найденые пользователи ...
Разблокировать пользователей ...
Читали форум (0):
Пользователи онлайн (0):
x
x
Закрыть


Просмотр
0 / 0
Close
Debug Console [Select Text]