A super lightweight library for handling role based permissions in Laravel.
This library is in early release and is pending unit tests.
There are some great existing role based authorization libraries out there, so why another one?
For our internal systems, we wanted something which is:
- simple to use
- does not contain all the bells and whistles
- works with the framework's existing authorization library
- focuses on performance first
- elegantly modeled without a plethora of pivot tables - json type works fine!
We've managed to keep things simple and efficient by:
- creating just 2 tables, a
roles
table and arole_user
table mapping users to roles - storing assigned permissions in a json column on the
roles
table - performing just a single database query to retrieve all users, assigned roles & permissions
- keeping an in-object mapping cache of user -> permissions
- decorating this mapping cache with an external cache of your choice (memcached, redis, etc)
composer require balfour/laravel-custodian
The package works out the box without any configuration, however if you'd like to publish the config file, you can do so using:
php artisan vendor:publish --provider="Balfour\LaravelCustodian\ServiceProvider"
Custom User Model
The library will try to detect the path of your user model from the auth config's default guard.
If you'd like to use a custom model such as \App\User::class
, you can specify a class path
in the user_model
config value.
An alternative way to set the user model on the fly is via the
Balfour\LaravelCustodian\UserModelResolver::setModel(\App\User::class)
function.
Super Admins
The admins
config value takes an array of email addresses which should be given super admin
access on the custodian. This means that these users will automatically pass all gate (permission)
checks.
We do not recommend using this outside of testing. You should rather make use of Laravel's
Gate::before
or Gate::after
hooks to accomplish this.
Add the HasRoles
trait to your user model.
namespace App;
use Balfour\LaravelCustodian\HasRoles;
use Illuminate\Notifications\Notifiable;
use Illuminate\Contracts\Auth\MustVerifyEmail;
use Illuminate\Foundation\Auth\User as Authenticatable;
class User extends Authenticatable
{
use HasRoles;
}
This will establish a relationship between users and roles; and also give you the following utility methods:
/**
* @param mixed $role
*/
public function assignRole($role)
/**
* @param mixed $role
*/
public function revokeRole($role)
/**
* @param array $ids
*/
public function syncRoles(array $ids)
use Balfour\LaravelCustodian\Models\Role;
$admin = Role::create(['name' => 'admin']);
$support = Role::create(['name' => 'customer-support']);
You must register permissions before they can be assigned to roles.
The package does not store available permissions in the database, but instead, registers
them against a PermissionRegistrar
. This means that permissions must be registered
upon bootstrap, such as in your app's AppServiceProvider
, or a module/package's
ServiceProvider
.
use Balfour\LaravelCustodian\Custodian;
$custodian = app(Custodian::class);
$custodian->register('create-user');
$custodian->register('view-user');
$custodian->register('view-user-support-tickets');
use Balfour\LaravelCustodian\Custodian;
$custodian = app(Custodian::class);
$permissions = $custodian->getAvailablePermissions();
// you could use this to generate a permission matrix for a user, or display a checkbox list
// of permissions on an edit user type of page
use Balfour\LaravelCustodian\Models\Role;
$admin = Role::where('name', 'admin')->first();
$admin->give('create-user');
$admin->give('view-user');
use Balfour\LaravelCustodian\Models\Role;
$admin = Role::where('name', 'admin')->first();
$admin->revoke('create-user');
use App\User;
use Balfour\LaravelCustodian\Models\Role;
$user = User::find(1);
$user->assignRole('admin');
// you can also assign using a model
$admin = Role::where('name', 'admin')->first();
$user->assignRole($admin);
// or by id
$user->assignRole(1);
use App\User;
$user = User::find(1);
$user->syncRoles([
1,
2,
]);
use App\User;
use Balfour\LaravelCustodian\Models\Role;
$user = User::find(1);
$user->revokeRole('admin');
// you can also revoke using a model
$admin = Role::where('name', 'admin')->first();
$user->revokeRole($admin);
// or by id
$user->revokeRole(1);
use App\User;
$user = User::find(1);
$roles = $user->roles;
use App\User;
use Balfour\LaravelCustodian\Custodian;
$custodian = app(Custodian::class);
$user = User::find(1);
$permissions = $custodian->getUserPermissions();
The library does not add any special functionality for checking if a user can perform a specific permission (or ability).
Please see the Laravel Authorization documentation for more info on this subject.
use App\User;
$user = User::find(1);
var_dump($user->can('create-user'));
// via middleware
Route::put('/users/{user}', function (User $user) {
})->middleware('can:view-user');
// via blade
@can('view-user)
// ....
@endcan