Spatie Permissions with Laravel
In this tutorial, we will implement Spatie Permissions with Laravel application. We will make multiple roles with their permissions in our application and assign these roles to users.
The prerequisite of this tutorial is that our application should have Laravel Auth in our application.
Getting Started
Let's install this package via composer in our app
composer require spatie/laravel-permission
After that Register the PermissionServiceProvider in config/app.php in the provider's array:
Spatie\Permission\PermissionServiceProvider::class,
Then publish the package migration file and config/permission.php file from this command:
php artisan vendor:publish — provider=”Spatie\Permission\PermissionServiceProvider”
Run this command to clear cache because this package requires to the permissions from configuration:
php artisan optimize:clear
or
php artisan config:clear
Run the migration command:
php artisan migrate
If you want to make your own Permission and Role Models then copy the respective path from models array in config/permissions.php and paste it in these models and replace the Permission and Role Models path in config/permissions.php from your own models path.
In config/permission.php file:
‘models’ => [
‘permission’ => \App\Models\Permission::class,
‘role’ => \App\Models\Role::class,
],
Permision Model file:
<?php
namespace App\Models;
use Spatie\Permission\Models\Permission as SpatiePermission;
class Permission extends SpatiePermission
{
protected $fillable = [‘name’, ‘guard_name’];
}
Role Model file:
<?php
namespace App\Models;
use Spatie\Permission\Models\Role as SpatieRole;
class Role extends SpatieRole
{
protected $fillable = [‘name’, ‘guard_name’];
}
Add Spatie\Permission\Traits\HasRoles
trait to your User
model:
<?php
namespace App\Models;
use Illuminate\Foundation\Auth\User as Authenticatable;
use Spatie\Permission\Traits\HasRoles;
class User extends Authenticatable
{
use HasRoles;
// …
}
Now make a seerder file to write Roles and Permissions for user!
php artisan make:seeder RolesAndPermissionsSeeder
Add the Role and Permission model in seed file:
use Spatie\Permission\Models\Role;
use Spatie\Permission\Models\Permission;
Again if you define your own model then instead of this add your own model path i.e.
use App\Models\Permission;
use App\Models\Role;
In the run funtion of seed file:
// Reset cached roles and permissions
app()[\Spatie\Permission\PermissionRegistrar::class]->forgetCachedPermissions();
//truncate tables
DB::statement(‘SET FOREIGN_KEY_CHECKS=0;’);
DB::table(‘roles’)->truncate();
DB::table(‘permissions’)->truncate();
DB::table(‘model_has_permissions’)->truncate();
DB::table(‘model_has_roles’)->truncate();
DB::table(‘role_has_permissions’)->truncate();
DB::statement(‘SET FOREIGN_KEY_CHECKS=1;’);
// create permissions
Permission::create([‘name’ => ‘owner’, ‘guard_name’ => ‘admin’]);
Permission::create([‘name’ => ‘branch-manager’, ‘guard_name’ => ‘admin’]);
Permission::create([‘name’ => ‘data-entry-operator’, ‘guard_name’ => ‘admin’]);
// create roles and assign created permissions
// this can be done as separate statements
$role = Role::create([
‘name’ => ‘owner’,
‘guard_name’ => ‘admin’,
]);
$role->givePermissionTo(Permission::all());
$role = Role::create([
‘name’ => ‘branch-manager’,
‘guard_name’ => ‘admin’,
]);
$role->givePermissionTo(‘branch-manager’);
$role = Role::create([
‘name’ => ‘data-entry-operator’,
‘guard_name’ => ‘admin’,
]);
$role->givePermissionTo(‘data-entry-operator’);
If you do not define guard_name in the create method of permission and role then package will get the default guard_name from config/auth.php from defaults array.
If you want to work with multiple guard or other than default guard then these guards should be in the guards array in config/auth.php i.e. admin,api etc.
After that assign a role to the user:
$owner = User::find(1);
$owner->assignRole(‘owner’);
$branch-manger= User::find(2);
$branch-manger->assignRole(‘branch-manger’);
From this you can assign role dynamically to the new login user accounding to their type.
We can direct assign the permission to the user without creating role from this:
$user->givePermissionTo(‘branch-manger’);
In the last we check the permissions against the loggedIn user:
@if(Auth::guard(‘admin’)->user()->hasPermissionTo(‘branch-manager’))//can perform branch manager task
//perform
@endif
@if(Auth::guard(‘admin’)->user()->hasPermissionTo(‘data-entry-operator’))//can perform data-entry-operator task
//perform
@endif
I hope it will help you! If you have some questions or suggestion then feel free to comment. Thanks for reading this tutorial.