---
title: "How to Manage Role in Laravel using Spatie Laravel Permission?"
url: "https://magecomp.com/blog/manage-role-in-laravel-using-spatie-laravel-permission/"
date: "2025-04-16T11:05:25+00:00"
modified: "2025-04-16T11:05:26+00:00"
author:
  name: "Bharat Desai"
  url: "https://magecomp.com"
categories:
  - "Laravel"
word_count: 2125
reading_time: "11 min read"
summary: "When building modern web applications, managing user roles and permissions is a critical aspect of ensuring security and proper access control. Laravel, one of the most popular PHP frameworks, does..."
description: "Learn how to manage user roles and permissions in Laravel using the Spatie Laravel Permission package. Step-by-step guide"
keywords: "Laravel"
language: "en"
schema_type: "Article"
related_posts:
  - title: "How to Upload Image in Laravel?"
    url: "https://magecomp.com/blog/upload-image-laravel/"
  - title: "Laravel 10 Authentication using Jetstream"
    url: "https://magecomp.com/blog/laravel-10-authentication-using-jetstream/"
  - title: "How to Push a Laravel Docker Image to DockerHub (Step-by-Step Guide)"
    url: "https://magecomp.com/blog/push-laravel-docker-image-to-dockerhub/"
---

# How to Manage Role in Laravel using Spatie Laravel Permission?

_Published: April 16, 2025_  
_Author: Bharat Desai_  

![How to Manage Role in Laravel using Spatie Laravel Permission](https://magecomp.com/blog/wp-content/uploads/2025/04/How-to-Manage-Role-in-Laravel-using-Spatie-Laravel-Permission-1024x512.webp)

When building modern web applications, managing user roles and permissions is a critical aspect of ensuring security and proper access control. Laravel, one of the most popular PHP frameworks, doesn’t come with role management out-of-the-box, but thanks to the Spatie Laravel Permission package, implementing it becomes seamless and elegant.

[![Hire laravel Developer](https://magecomp.com/blog/wp-content/uploads/2024/12/Hire-Laravel-Expert-Now-3-1024x284.webp)](https://magecomp.com/services/hire-laravel-developer/)In this blog, we’ll walk you through how to install, configure, and manage roles and permissions in Laravel using the Spatie package.

## What is Spatie Laravel Permission?
Spatie Laravel Permission is a powerful Laravel package that allows you to manage user roles and permissions with ease. It supports roles, permissions, multiple guards, and even blade directives to control access in views.

[![Laravel Development Services](https://magecomp.com/blog/wp-content/uploads/2024/12/Laravel-Development-Services-4-1024x284.webp)](https://magecomp.com/services/laravel-development-services/)

## Steps to Manage Role in Laravel using Spatie Laravel Permission:
### Step 1: Install Laravel
Run the below command to install Laravel

```
composer create-project laravel/laravel role-permission
```

### Step 2: Install spatie/laravel-permission Package
Open your terminal and run the following commands

```
composer require spatie/laravel-permission

php artisan vendor:publish –provider="SpatiePermissionPermissionServiceProvider"

php artisan migrate
```

### Step 3: Create Product Migration
In this step, we have to create three migrations for the products table using the following command:

```
php artisan make:migration create_products_table
```

Add code as follows

```
<?php

use IlluminateDatabaseMigrationsMigration;
use IlluminateDatabaseSchemaBlueprint;
use IlluminateSupportFacadesSchema;

return new class extends Migration
{
    /**
     * Run the migrations.
     *
     * @return void
     */
    public function up(): void
    {
        Schema::create('products', function (Blueprint $table) {
            $table->id();
            $table->string('name');
            $table->text('detail');
            $table->timestamps();
        });
    }

    /**
     * Reverse the migrations.
     *
     * @return void
     */
    public function down(): void
    {
        Schema::dropIfExists('products');
    }
};
```

After this, run the migration command

```
php artisan migrate
```

### Step 4: Create Models
 Add the following code

**app/Models/User.php**

```
<?php

namespace AppModels;

use IlluminateDatabaseEloquentFactoriesHasFactory;
use IlluminateFoundationAuthUser as Authenticatable;
use IlluminateNotificationsNotifiable;
use SpatiePermissionTraitsHasRoles;

class User extends Authenticatable
{
    use HasFactory, Notifiable, HasRoles;

    /**
     * The attributes that are mass assignable.
     *
     * @var array
     */
    protected $fillable = [
        'name',
        'email',
        'password',
    ];

    /**
     * The attributes that should be hidden for serialization.
     *
     * @var array
     */
    protected $hidden = [
        'password',
        'remember_token',
    ];

    /**
     * Get the attributes that should be cast.
     *
     * @return array
     */
    protected function casts(): array
    {
        return [
            'email_verified_at' => 'datetime',
            'password' => 'hashed',
        ];
    }
}
```

**app/Models/Product.php**

```
<?php

namespace AppModels;

use IlluminateDatabaseEloquentFactoriesHasFactory;
use IlluminateDatabaseEloquentModel;

class Product extends Model
{
    use HasFactory;

    /**
     * The attributes that are mass assignable.
     *
     * @var array
     */
    protected $fillable = [
        'name', 'detail'
    ];
}
```

### Step 5: Add Middleware
So, we have to add middleware in the app.php file this way:

**bootstrap/app.php**

```
<?php

use IlluminateFoundationApplication;
use IlluminateFoundationConfigurationExceptions;
use IlluminateFoundationConfigurationMiddleware;

return Application::configure(basePath: dirname(__DIR__))
    ->withRouting(
        web: __DIR__.'/../routes/web.php',
        commands: __DIR__.'/../routes/console.php',
        health: '/up',
    )
    ->withMiddleware(function (Middleware $middleware) {
        $middleware->alias([
            'role' => SpatiePermissionMiddlewareRoleMiddleware::class,
            'permission' => SpatiePermissionMiddlewarePermissionMiddleware::class,
            'role_or_permission' => SpatiePermissionMiddlewareRoleOrPermissionMiddleware::class
        ]);
    })
    ->withExceptions(function (Exceptions $exceptions) {
        //
    })->create();
```

### Step 6: Create Authentication
First, you need to install the laravel/ui package as shown below:

```
composer require laravel/ui
```

Here, we need to generate auth scaffolding in Laravel 11 using the Laravel UI command. So, let’s generate it with the below command:

```
php artisan ui bootstrap –auth
```

Now you need to run the npm command; otherwise, you cannot see the better layout of the login and register page.

```
npm install

npm run build
```

### Step 7: Create Routes
We need to add a number of routes for the users module, products module, and roles module. In these routes, also use middleware with permissions for the roles and products routes, so add routes this way:

**routes/web.php**

```
<?php

use IlluminateSupportFacadesRoute;

use AppHttpControllersHomeController;
use AppHttpControllersRoleController;
use AppHttpControllersUserController;
use AppHttpControllersProductController;

Route::get('/', function () {
    return view('welcome');
});

Auth::routes();

Route::get('/home', [HomeController::class, 'index'])->name('home');

Route::group(['middleware' => ['auth']], function() {
    Route::resource('roles', RoleController::class);
    Route::resource('users', UserController::class);
    Route::resource('products', ProductController::class);
});
```

### Step 8: Add Controllers
**app/Http/Controllers/UserController.php**

```
<?php

namespace AppHttpControllers;

use IlluminateHttpRequest;
use AppHttpControllersController;
use AppModelsUser;
use SpatiePermissionModelsRole;
use DB;
use Hash;
use IlluminateSupportArr;
use IlluminateViewView;
use IlluminateHttpRedirectResponse;

class UserController extends Controller
{
    /**
     * Display a listing of the resource.
     *
     * @return IlluminateHttpResponse
     */
    public function index(Request $request): View
    {
        $data = User::latest()->paginate(5);

        return view('users.index',compact('data'))
            ->with('i', ($request->input('page', 1) - 1) * 5);
    }

    /**
     * Show the form for creating a new resource.
     *
     * @return IlluminateHttpResponse
     */
    public function create(): View
    {
        $roles = Role::pluck('name','name')->all();

        return view('users.create',compact('roles'));
    }

    /**
     * Store a newly created resource in storage.
     *
     * @param  IlluminateHttpRequest  $request
     * @return IlluminateHttpResponse
     */
    public function store(Request $request): RedirectResponse
    {
        $this->validate($request, [
            'name' => 'required',
            'email' => 'required|email|unique:users,email',
            'password' => 'required|same:confirm-password',
            'roles' => 'required'
        ]);

        $input = $request->all();
        $input['password'] = Hash::make($input['password']);

        $user = User::create($input);
        $user->assignRole($request->input('roles'));

        return redirect()->route('users.index')
                        ->with('success','User created successfully');
    }

    /**
     * Display the specified resource.
     *
     * @param  int  $id
     * @return IlluminateHttpResponse
     */
    public function show($id): View
    {
        $user = User::find($id);

        return view('users.show',compact('user'));
    }

    /**
     * Show the form for editing the specified resource.
     *
     * @param  int  $id
     * @return IlluminateHttpResponse
     */
    public function edit($id): View
    {
        $user = User::find($id);
        $roles = Role::pluck('name','name')->all();
        $userRole = $user->roles->pluck('name','name')->all();

        return view('users.edit',compact('user','roles','userRole'));
    }

    /**
     * Update the specified resource in storage.
     *
     * @param  IlluminateHttpRequest  $request
     * @param  int  $id
     * @return IlluminateHttpResponse
     */
    public function update(Request $request, $id): RedirectResponse
    {
        $this->validate($request, [
            'name' => 'required',
            'email' => 'required|email|unique:users,email,'.$id,
            'password' => 'same:confirm-password',
            'roles' => 'required'
        ]);

        $input = $request->all();
        if(!empty($input['password'])){
            $input['password'] = Hash::make($input['password']);
        }else{
            $input = Arr::except($input,array('password'));
        }

        $user = User::find($id);
        $user->update($input);
        DB::table('model_has_roles')->where('model_id',$id)->delete();

        $user->assignRole($request->input('roles'));

        return redirect()->route('users.index')
                        ->with('success','User updated successfully');
    }

    /**
     * Remove the specified resource from storage.
     *
     * @param  int  $id
     * @return IlluminateHttpResponse
     */
    public function destroy($id): RedirectResponse
    {
        User::find($id)->delete();
        return redirect()->route('users.index')
                        ->with('success','User deleted successfully');
    }
}
```

**app/Http/Controllers/ProductController.php**

```
<?php

namespace AppHttpControllers;

use AppModelsProduct;
use IlluminateHttpRequest;
use IlluminateViewView;
use IlluminateHttpRedirectResponse;

class ProductController extends Controller
{
    /**
     * Display a listing of the resource.
     *
     * @return IlluminateHttpResponse
     */
    function __construct()
    {
         $this->middleware('permission:product-list|product-create|product-edit|product-delete', ['only' => ['index','show']]);
         $this->middleware('permission:product-create', ['only' => ['create','store']]);
         $this->middleware('permission:product-edit', ['only' => ['edit','update']]);
         $this->middleware('permission:product-delete', ['only' => ['destroy']]);
    }
    /**
     * Display a listing of the resource.
     *
     * @return IlluminateHttpResponse
     */
    public function index(): View
    {
        $products = Product::latest()->paginate(5);

        return view('products.index',compact('products'))
            ->with('i', (request()->input('page', 1) - 1) * 5);
    }

    /**
     * Show the form for creating a new resource.
     *
     * @return IlluminateHttpResponse
     */
    public function create(): View
    {
        return view('products.create');
    }

    /**
     * Store a newly created resource in storage.
     *
     * @param  IlluminateHttpRequest  $request
     * @return IlluminateHttpResponse
     */
    public function store(Request $request): RedirectResponse
    {
        request()->validate([
            'name' => 'required',
            'detail' => 'required',
        ]);

        Product::create($request->all());

        return redirect()->route('products.index')
                        ->with('success','Product created successfully.');
    }

    /**
     * Display the specified resource.
     *
     * @param  AppProduct  $product
     * @return IlluminateHttpResponse
     */
    public function show(Product $product): View
    {
        return view('products.show',compact('product'));
    }

    /**
     * Show the form for editing the specified resource.
     *
     * @param  AppProduct  $product
     * @return IlluminateHttpResponse
     */
    public function edit(Product $product): View
    {
        return view('products.edit',compact('product'));
    }

    /**
     * Update the specified resource in storage.
     *
     * @param  IlluminateHttpRequest  $request
     * @param  AppProduct  $product
     * @return IlluminateHttpResponse
     */
    public function update(Request $request, Product $product): RedirectResponse
    {
         request()->validate([
            'name' => 'required',
            'detail' => 'required',
        ]);

        $product->update($request->all());

        return redirect()->route('products.index')
                        ->with('success','Product updated successfully');
    }

    /**
     * Remove the specified resource from storage.
     *
     * @param  AppProduct  $product
     * @return IlluminateHttpResponse
     */
    public function destroy(Product $product): RedirectResponse
    {
        $product->delete();

        return redirect()->route('products.index')
                        ->with('success','Product deleted successfully');
    }
}
```

**app/Http/Controllers/RoleController.php**

```
<?php

namespace AppHttpControllers;

use IlluminateHttpRequest;
use AppHttpControllersController;
use SpatiePermissionModelsRole;
use SpatiePermissionModelsPermission;
use DB;
use IlluminateViewView;
use IlluminateHttpRedirectResponse;

class RoleController extends Controller
{
    /**
     * Display a listing of the resource.
     *
     * @return IlluminateHttpResponse
     */
    function __construct()
    {
         $this->middleware('permission:role-list|role-create|role-edit|role-delete', ['only' => ['index','store']]);
         $this->middleware('permission:role-create', ['only' => ['create','store']]);
         $this->middleware('permission:role-edit', ['only' => ['edit','update']]);
         $this->middleware('permission:role-delete', ['only' => ['destroy']]);
    }

    /**
     * Display a listing of the resource.
     *
     * @return IlluminateHttpResponse
     */
    public function index(Request $request): View
    {
        $roles = Role::orderBy('id','DESC')->paginate(5);
        return view('roles.index',compact('roles'))
            ->with('i', ($request->input('page', 1) - 1) * 5);
    }

    /**
     * Show the form for creating a new resource.
     *
     * @return IlluminateHttpResponse
     */
    public function create(): View
    {
        $permission = Permission::get();
        return view('roles.create',compact('permission'));
    }

    /**
     * Store a newly created resource in storage.
     *
     * @param  IlluminateHttpRequest  $request
     * @return IlluminateHttpResponse
     */
    public function store(Request $request): RedirectResponse
    {
        $this->validate($request, [
            'name' => 'required|unique:roles,name',
            'permission' => 'required',
        ]);

        $permissionsID = array_map(
            function($value) { return (int)$value; },
            $request->input('permission')
        );

        $role = Role::create(['name' => $request->input('name')]);
        $role->syncPermissions($permissionsID);

        return redirect()->route('roles.index')
                        ->with('success','Role created successfully');
    }
    /**
     * Display the specified resource.
     *
     * @param  int  $id
     * @return IlluminateHttpResponse
     */
    public function show($id): View
    {
        $role = Role::find($id);
        $rolePermissions = Permission::join("role_has_permissions","role_has_permissions.permission_id","=","permissions.id")
            ->where("role_has_permissions.role_id",$id)
            ->get();

        return view('roles.show',compact('role','rolePermissions'));
    }

    /**
     * Show the form for editing the specified resource.
     *
     * @param  int  $id
     * @return IlluminateHttpResponse
     */
    public function edit($id): View
    {
        $role = Role::find($id);
        $permission = Permission::get();
        $rolePermissions = DB::table("role_has_permissions")->where("role_has_permissions.role_id",$id)
            ->pluck('role_has_permissions.permission_id','role_has_permissions.permission_id')
            ->all();

        return view('roles.edit',compact('role','permission','rolePermissions'));
    }

    /**
     * Update the specified resource in storage.
     *
     * @param  IlluminateHttpRequest  $request
     * @param  int  $id
     * @return IlluminateHttpResponse
     */
    public function update(Request $request, $id): RedirectResponse
    {
        $this->validate($request, [
            'name' => 'required',
            'permission' => 'required',
        ]);

        $role = Role::find($id);
        $role->name = $request->input('name');
        $role->save();

        $permissionsID = array_map(
            function($value) { return (int)$value; },
            $request->input('permission')
        );

        $role->syncPermissions($permissionsID);

        return redirect()->route('roles.index')
                        ->with('success','Role updated successfully');
    }
    /**
     * Remove the specified resource from storage.
     *
     * @param  int  $id
     * @return IlluminateHttpResponse
     */
    public function destroy($id): RedirectResponse
    {
        DB::table("roles")->where('id',$id)->delete();
        return redirect()->route('roles.index')
                        ->with('success','Role deleted successfully');
    }
}
```

### Step 9: Create Seeder For Permissions and AdminUser
In this step, we will create a seeder for permissions. Right now, we have fixed permissions, so we’ll create them using a seeder as listed below. However, if you want, you can add more permissions as you wish.

1. role-list
2. role-create
3. role-edit
4. role-delete
5. product-list
6. product-create
7. product-edit
8. product-delete

```
php artisan make:seeder PermissionTableSeeder
```

And put the below code in the PermissionTableSeeder seeder this way:

**database/seeders/PermissionTableSeeder.php**

```
<?php

namespace DatabaseSeeders;

use IlluminateDatabaseConsoleSeedsWithoutModelEvents;
use IlluminateDatabaseSeeder;
use SpatiePermissionModelsPermission;

class PermissionTableSeeder extends Seeder
{
    /**
     * Run the database seeds.
     */
    public function run(): void
    {
        $permissions = [
           'role-list',
           'role-create',
           'role-edit',
           'role-delete',
           'product-list',
           'product-create',
           'product-edit',
           'product-delete'
        ];

        foreach ($permissions as $permission) {
             Permission::create(['name' => $permission]);
        }
    }
}
```

After this, we have to run the below command to execute the PermissionTableSeeder seeder:

```
php artisan db:seed –class=PermissionTableSeeder
```

Now let’s create a new seeder for creating an admin user

```
php artisan make:seeder CreateAdminUserSeeder
```

**database/seeders/CreateAdminUserSeeder.php**

```
<?php

namespace DatabaseSeeders;

use IlluminateDatabaseConsoleSeedsWithoutModelEvents;
use IlluminateDatabaseSeeder;
use AppModelsUser;
use SpatiePermissionModelsRole;
use SpatiePermissionModelsPermission;

class CreateAdminUserSeeder extends Seeder
{
    /**
     * Run the database seeds.
     */
    public function run(): void
    {
        $user = User::create([
            'name' => 'Hardik Savani',
            'email' => 'admin@gmail.com',
            'password' => bcrypt('123456')
        ]);

        $role = Role::create(['name' => 'Admin']);

        $permissions = Permission::pluck('id','id')->all();

        $role->syncPermissions($permissions);

        $user->assignRole([$role->id]);
    }
}
```

Then, run the seeder using the following command:

```
php artisan db:seed –class=CreateAdminUserSeeder
```

All the required steps have been done, now you have to type the command below and hit enter to run the Laravel app:

```
php artisan serve
```

## Conclusion:
Using Spatie Laravel Permission makes managing roles and permissions in your Laravel application incredibly efficient and developer-friendly.

Need help implementing Spatie Laravel Permission in your Laravel app? Feel free to reach out in the comments or contact us—we’re here to help!

[![Contact Us](https://magecomp.com/blog/wp-content/uploads/2024/12/Contact-Us-3-1024x284.webp)](https://magecomp.com/contact)


---

_View the original post at: [https://magecomp.com/blog/manage-role-in-laravel-using-spatie-laravel-permission/](https://magecomp.com/blog/manage-role-in-laravel-using-spatie-laravel-permission/)_  
_Served as markdown by [Third Audience](https://github.com/third-audience) v3.5.3_  
_Generated: 2026-10-13 17:38:43 UTC_  
