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

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

В моей голове я рисую 3 таблицы (пользователи, роли и разрешения). Я могу дать каждому пользователю идентификатор роли, который присоединяется к таблице ролей, я просто не знаю, как я могу связать роли с несколькими правами.

Ответы

Ответ 1

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

Вы используете таблицу соединений: role_id и permission_id для определения того, какие разрешения связаны с какими ролями

EDIT:

Примеры таблиц

Таблица ROLE

Role_ID Role_Name
1       Standard User
2       Super User
3       Guest

Таблица PERMISSION

Permission_ID Permission_Name
1             View User List
2             Update Own User Account
3             Update Any User Account

Таблица ROLE_PERMISSION

Role_ID Permission_ID
1       1    // Role 1 (Standard User) grants View User List
1       2    //        and Update Own User Account
2       1    // Role 2 (Super User) grants View User List,
2       2    //        Update Own User Account,
2       3    //        and Update Any User Account
3       1    // Role 3 (Guest) grants View User List

Список разрешений для указанного Role_ID

select R.role_id,
       P.permission_id,
       P.permission_name
  from role R,
       permission P,
       role_permission RP
 where RP.permission_id = P.permission_id
   and RP.role_id = R.role_id
   and R.role_id = 1 

Ответ 2

Вот как обычно я делаю:

Вы определяете набор разрешений, значение которых изменяется от целевого объекта к целевому объекту, но общий смысл которого тот же. Например:

  • прочитать
  • записи
  • Append
  • удалить
  • удалить содержимое
  • права на чтение
  • изменить права доступа

Затем вы назначаете бит каждому из них:

class Perms {
    const read           = 1;
    const write          = 2;
    const append         = 4;
    const delete         = 8;
    const deleteContents = 16;
    const readPerm       = 32;
    const changePerm     = 64;
    /* shortcuts */
    const fullControl    = 127; 
    const noControl      = 0;
}

Затем для каждого типа объекта у вас есть таблица, в которую вы вставляете пары (user, perms), (group, perms), (role, perms) или все, что вы хотите связать с разрешениями.

Вы можете запросить разрешения пользователя (который может иметь несколько ролей) следующим образом:

//this will depend on the database
//you could also use whatever bitwise OR aggregate your database has
//to avoid the foreach loop below
$query = new Query(
    "select perm from objects_permissions as P ".
    "where P.id_object = \$1 and " .
    "   (P.role = any(\$2));",
    $obj->getId(), $user->getRoles()
);

$perms = 0;
foreach ($query as $row) {
    $perms |= $row['perm']; 
}

Вы также можете добавить разрешения запрета с небольшими трудностями.

Ответ 3

Я считаю, что побитовый оператор - лучший способ реализовать пользовательское разрешение. Здесь я показываю, как мы можем реализовать его с помощью Mysql.

Ниже приведены примеры таблиц с некоторыми примерами данных:

Таблица 1: таблица разрешений для хранения имени разрешения вместе с ним бит, например, 1,2,4,8..etc(несколько из 2)

CREATE TABLE IF NOT EXISTS `permission` (
  `bit` int(11) NOT NULL,
  `name` varchar(50) NOT NULL,
  PRIMARY KEY (`bit`)
) ENGINE=InnoDB DEFAULT CHARSET=latin1;

Вставьте некоторые примеры данных в таблицу.

INSERT INTO `permission` (`bit`, `name`) VALUES
(1, 'User-Add'),
(2, 'User-Edit'),
(4, 'User-Delete'),
(8, 'User-View'),
(16, 'Blog-Add'),
(32, 'Blog-Edit'),
(64, 'Blog-Delete'),
(128, 'Blog-View');

Таблица 2. Таблица пользователей для хранения идентификатора пользователя, имени и роли. Роль будет рассчитываться как сумма разрешений.
Пример:
Если пользователь "Ketan" имеет разрешение "User-Add" (бит = 1) и "Blog-Delete" (бит-64), эта роль будет равна 65 (1 + 64).
Если пользователь "Mehata" имеет разрешение "Blog-View" (бит = 128) и "User-Delete" (бит-4), то роль будет равна 132 (128 + 4).

CREATE TABLE IF NOT EXISTS `user` (
  `id` int(11) NOT NULL AUTO_INCREMENT,
  `name` varchar(50) NOT NULL,
  `role` int(11) NOT NULL,
  `created_date` datetime NOT NULL
  PRIMARY KEY (`id`)
) ENGINE=InnoDB  DEFAULT CHARSET=latin1;

Пример данных -

INSERT INTO `user` (`id`, `name`, `role`, `created_date`)
   VALUES (NULL, 'Ketan', '65', '2013-01-09 00:00:00'),
   (NULL, 'Mehata', '132', '2013-01-09 00:00:00');

Разрешение пользователя Loding После входа в систему, если мы хотим загрузить пользовательское разрешение, мы можем запросить ниже, чтобы получить разрешения:

SELECT permission.bit,permission.name  
   FROM user LEFT JOIN permission ON user.role & permission.bit
 WHERE user.id = 1

Здесь user.role "&" permission.bit - биттонный оператор, который будет выдавать результат как -

User-Add - 1
Blog-Delete - 64

Если мы хотим проверить погоду, у определенного пользователя есть разрешение на редактирование пользователя или нет -

  SELECT * FROM `user` 
     WHERE role & (select bit from permission where name='user-edit')

Вывод = Нет строк.

Вы также можете увидеть: http://goo.gl/ATnj6j

Ответ 4

Если вы хотите пройти маршрут из трех таблиц, вы можете создать свои таблицы следующим образом:

Table       | Rows
User        | id ; name ; dob ; permission_id ; etc...  
Roles       | id ; add_post ; edit_post ; delete_post ; add_user ; etc...
Permissions | id ; user_id ; role_id