Пользователи Laravel с разными наборами разрешений на основе клиента

#laravel #permissions #multi-tenant

#laravel #разрешения #многопользовательский

Вопрос:

В настоящее время я работаю над проектом Laravel, который в некоторой степени является многопользовательским. Администратор будет создавать компании, которые по сути являются клиентами, но пользователь может быть частью нескольких компаний, каждая из которых имеет определенную роль или назначенные индивидуальные разрешения.

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

Пользователь сможет видеть все свои данные, к которым он привязан, на одном портале, поэтому переключение клиентов не происходит.

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

пользователь:

  • ID

user_role (используется для назначения пользователей-администраторов):

  • user_id
  • role_id

Компания:

  • ID

пользователь_company:

  • ID
  • user_id
  • company_id
  • role_id

пользователь_компания_перемещение:

  • ID
  • user_company_id
  • permission_id

разрешение:

  • ID
  • Имя

Роль:

  • ID
  • Имя

permission_role:

  • ID
  • permission_id
  • role_id

project: — id — (другая информация, связанная с проектом)

project_user: — id — project_id — user_id — role_id

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

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

Комментарии:

1. Должны ли разрешения роли быть динамическими (т. Е. В базе данных) или это может быть жестко запрограммировано? Я только что создал нечто подобное (но не такое сложное), и способ, которым я это сделал, заключался в том, чтобы сохранить a role в сводной таблице и проверить разрешения в политиках.

2. Сами роли могут быть жестко запрограммированы, но пользователям для компании необходимо иметь возможность назначать индивидуальные разрешения или назначать роли.

Ответ №1:

Если разрешения каждой роли не обязательно должны быть динамическими, вы можете заменить role таблицы permission и политиками. Просто добавьте role поле в user_company таблицу (я бы лично сделал его строкой, чтобы его было легче читать).

Затем в CompanyPolicy вы можете запускать проверки следующим образом:

 
    /**
     * Determine whether the user can view the object.
     *
     * @param  AppUser  $user
     * @param  AppCompany  $company
     * @return mixed
     */
    public function view(User $user, Company $company)
    {
        $allowedRoles = ['admin', 'someotherrole'];
        return $user->companies()->wherePivotIn('role', $allowedRoles)->count() > 0;
    }
  

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

Комментарии:

1. Итак, с таким решением, как это, как я мог бы по-прежнему использовать директиву «@can» в моих блейдах, которая проверяла бы все разрешения пользователей, компаний или проектов? Я полагаю, я мог бы написать свою собственную директиву, которая сделала это и позволила мне перейти в конкретную компанию или проект. Что вы думаете?

2. @can вызывает соответствующий метод политики и передает текущего пользователя и объект, для которого вы проверяете разрешения, так что вы можете поместить туда всю логику. Вы также можете передать несколько параметров @can('view', [$obj1, $obj2]) .

3. Приятно знать, я совсем новичок в laravel, поэтому я этого не знал. Мне придется попробовать. Спасибо!