PHPackages                             nowakadmin/nova-role-manager - PHPackages - PHPackages  [Skip to content](#main-content)[PHPackages](/)[Directory](/)[Categories](/categories)[Trending](/trending)[Leaderboard](/leaderboard)[Changelog](/changelog)[Analyze](/analyze)[Collections](/collections)[Log in](/login)[Sign up](/register)

1. [Directory](/)
2. /
3. [Authentication &amp; Authorization](/categories/authentication)
4. /
5. nowakadmin/nova-role-manager

ActiveLibrary[Authentication &amp; Authorization](/categories/authentication)

nowakadmin/nova-role-manager
============================

Complete role-based access control (RBAC) system for Laravel Nova with multi-tenancy support, policies, and permissions

01PHP

Since Jan 29Pushed 1mo agoCompare

[ Source](https://github.com/NowakAdmin/NovaRoleManager)[ Packagist](https://packagist.org/packages/nowakadmin/nova-role-manager)[ RSS](/packages/nowakadmin-nova-role-manager/feed)WikiDiscussions main Synced today

READMEChangelogDependenciesVersions (2)Used By (0)

Nova Role Manager
=================

[](#nova-role-manager)

A complete, reusable role-based access control (RBAC) system for Laravel Nova with multi-tenancy support, policies, and permissions.

Built on top of **[spatie/laravel-permission](https://github.com/spatie/laravel-permission)** with Nova admin UI layer and multi-tenancy integration.

Features
--------

[](#features)

- 🔐 **Role-Based Access Control (RBAC)** - Manage user roles and permissions via spatie/laravel-permission
- 🏢 **Multi-Tenancy Support** - Full tenant isolation using Spatie Multitenancy
- 📋 **Nova Integration** - Manage roles and permissions directly from Nova admin panel
- 🔑 **Policies** - Built-in Laravel policies for model authorization
- 🎯 **Flexible Permissions** - Resource-based permission system (view, create, update, delete, manage)
- 🔄 **Trait-Based** - Easy integration with existing User model via Authorizable trait
- ⚡ **Industry Standard** - Built on battle-tested spatie/laravel-permission package
- 🌍 **Multi-Language** - English and Polish translations included

Installation
------------

[](#installation)

### 1. Install via Composer

[](#1-install-via-composer)

```
composer require nowakadmin/nova-role-manager
```

### 2. Add Authorizable Trait to User Model

[](#2-add-authorizable-trait-to-user-model)

In your `app/Models/User.php`:

```
use NowakAdmin\NovaRoleManager\Traits\Authorizable;
class User extends Authenticatable
{
    use Authorizable; // Add this
    // ... rest of model
}
```

### 3. Publish Files

[](#3-publish-files)

```
# Publish migrations
php artisan vendor:publish --provider="NowakAdmin\NovaRoleManager\Providers\NovaRoleManagerServiceProvider" --tag=nova-role-manager-migrations

# Publish config
php artisan vendor:publish --provider="NowakAdmin\NovaRoleManager\Providers\NovaRoleManagerServiceProvider" --tag=nova-role-manager-config

# Publish translations
php artisan vendor:publish --provider="NowakAdmin\NovaRoleManager\Providers\NovaRoleManagerServiceProvider" --tag=nova-role-manager-translations

# Or publish all at once
php artisan vendor:publish --provider="NowakAdmin\NovaRoleManager\Providers\NovaRoleManagerServiceProvider" --force
```

### 4. Run Migrations

[](#4-run-migrations)

**For multi-tenant projects:**

```
php artisan tenants:artisan "migrate --path=database/migrations/tenant --database=tenant"
```

**For single-tenant projects:**

```
php artisan migrate
```

### 5. Register Policies (Optional but Recommended)

[](#5-register-policies-optional-but-recommended)

In `app/Providers/AuthServiceProvider.php`:

```
use Illuminate\Support\Facades\Gate;
use NowakAdmin\NovaRoleManager\Policies\BasePolicy;

protected $policies = [
    // Your models here
    YourModel::class => YourPolicy::class, // extends BasePolicy
];

public function boot(): void
{
    $this->registerPolicies();

    Gate::define('is-superadmin', fn($user) => $user->isSuperAdmin());
    Gate::define('manage-roles', fn($user) => $user->hasPermission('manage.role'));
}
```

Configuration
-------------

[](#configuration)

Edit `config/nova-role-manager.php`:

```
return [
    'user_model' => \App\Models\User::class,

    'resources' => [
        'user' => 'User',
        'role' => 'Role',
        'permission' => 'Permission',
        // Add your application resources
    ],

    'actions' => [
        'view' => 'View',
        'create' => 'Create',
        'update' => 'Update',
        'delete' => 'Delete',
        'restore' => 'Restore',
        'force_delete' => 'Force Delete',
        'manage' => 'Manage',
    ],
];
```

Usage
-----

[](#usage)

### User Methods

[](#user-methods)

```
$user = auth()->user();

// Check roles
$user->hasRole('admin');
$user->isSuperAdmin();

// Check permissions
$user->hasPermission('view.user');
$user->hasPermission('create.role');
$user->hasAnyPermission(['view.user', 'view.role']);
$user->hasAllPermissions(['create.user', 'update.user']);

// Assign/Remove roles
$user->assignRole('admin');
$user->assignRole($roleModel);
$user->removeRole('admin');
$user->syncRoles(['admin', 'moderator']);
```

### Role Methods

[](#role-methods)

```
$role = Role::first();

// Check/grant/revoke permissions
$role->hasPermission('view.user');
$role->grantPermission('create.user');
$role->revokePermission('delete.user');
$role->revokeAllPermissions();

// Access relationships
$role->permissions;
$role->users;
```

### Nova Authorization

[](#nova-authorization)

Use `canSee()` in Nova resources:

```
public function fields(NovaRequest $request)
{
    return [
        // Only visible to superadmin
        Boolean::make('is_superadmin')
            ->canSee(fn() => auth()->user()->isSuperAdmin()),

        // Only if user has permission
        Text::make('Sensitive Field')
            ->canSee(fn() => auth()->user()->hasPermission('manage.sensitive')),
    ];
}
```

### Creating Custom Policies

[](#creating-custom-policies)

Create a policy extending `BasePolicy`:

```
namespace App\Policies;

use NowakAdmin\NovaRoleManager\Policies\BasePolicy;;

class ArticlePolicy extends BasePolicy
{
    protected function getResourceName(): string
    {
        return 'article';
    }

    // Optional: Override specific methods
    public function update($user, Article $article)
    {
        // Custom logic
        return $user->id === $article->author_id
            && parent::update($user, $article);
    }
}
```

Register in `AuthServiceProvider`:

```
protected $policies = [
    Article::class => ArticlePolicy::class,
];
```

Permission Format
-----------------

[](#permission-format)

Permissions follow a `action.resource` naming convention:

- `view.user` - View users
- `create.user` - Create users
- `update.user` - Update users
- `delete.user` - Delete users
- `manage.role` - Manage roles
- `manage.permission` - Manage permissions

Default Roles
-------------

[](#default-roles)

The package creates these default roles (optional via configuration):

- **superadmin** - Full access to everything
- **manager** - Can view, create, update, delete (except manage)
- **technician** - Limited access to specific resources
- **viewer** - Read-only access

Multi-Tenancy
-------------

[](#multi-tenancy)

The package is fully compatible with Spatie Multitenancy:

```
// All models use tenant connection automatically
$role = Role::create(...); // Scoped to current tenant
$permission = Permission::create(...); // Scoped to current tenant

// First user in each tenant automatically becomes superadmin
```

Seeding Permissions
-------------------

[](#seeding-permissions)

Create a seeder to populate permissions:

```
use NowakAdmin\NovaRoleManager\Models\Permission;
use NowakAdmin\NovaRoleManager\Models\Role;

public function run()
{
    // Create permissions
    Permission::firstOrCreate(
        ['name' => 'view.article'],
        ['resource' => 'article', 'action' => 'view', 'description' => 'View articles']
    );

    // Grant to role
    $role = Role::firstOrCreate(['name' => 'editor']);
    $role->grantPermission('view.article');
}
```

API Integration
---------------

[](#api-integration)

Check permissions in your API:

```
class ArticleController extends Controller
{
    public function store(Request $request)
    {
        $this->authorize('create', Article::class);

        // Or manually:
        if (!auth()->user()->hasPermission('create.article')) {
            abort(403);
        }

        // ... create article
    }
}
```

Testing
-------

[](#testing)

```
public function testUserCanViewArticles()
{
    $user = User::factory()->create();
    $permission = Permission::firstOrCreate(
        ['name' => 'view.article'],
        ['resource' => 'article', 'action' => 'view']
    );

    $user->assignRole(
        Role::firstOrCreate(
            ['name' => 'viewer'],
            ['is_superadmin' => false]
        )
    );

    // Grant permission
    $user->roles->first()->grantPermission($permission);

    $this->assertTrue($user->hasPermission('view.article'));
}
```

Database Schema
---------------

[](#database-schema)

### Roles Table (`roles`)

[](#roles-table-roles)

- `id` - Primary key
- `tenant_id` - Tenant identifier (multi-tenancy, nullable for landlord)
- `name` - Unique role name
- `guard_name` - Guard type (default: 'web')
- `description` - Role description (optional)
- `created_at`, `updated_at`
- Unique constraint: `[name, guard_name, tenant_id]`

### Permissions Table (`permissions`)

[](#permissions-table-permissions)

- `id` - Primary key
- `tenant_id` - Tenant identifier (nullable for landlord)
- `name` - Unique permission name
- `guard_name` - Guard type (default: 'web')
- `resource` - Resource type (user, role, article, etc.)
- `action` - Action (view, create, update, delete, restore, force\_delete, manage)
- `description` - Permission description (optional)
- `created_at`, `updated_at`
- Unique constraint: `[name, guard_name, tenant_id]`

### Pivot Tables

[](#pivot-tables)

- `role_has_permissions` - Maps roles to permissions
- `model_has_roles` - Maps users to roles (polymorphic)

Events &amp; Observers
----------------------

[](#events--observers)

The package includes:

- `UserObserver` - Automatically assigns superadmin role to first user in tenant

Troubleshooting
---------------

[](#troubleshooting)

### First user not becoming superadmin

[](#first-user-not-becoming-superadmin)

- Ensure `Authorizable` trait is added to User model
- Check that `UsesTenantConnection` is on User model for multi-tenancy
- Run migrations for the tenant

### Permissions not working

[](#permissions-not-working)

- Verify policies are registered in `AuthServiceProvider`
- Check permission names follow `action.resource` format
- Ensure user has required role before checking permission

### Nova resources not appearing

[](#nova-resources-not-appearing)

- Publish package with `--tag=config` and `--tag=translations`
- Clear Nova cache: `php artisan nova:publish && php artisan optimize:clear`
- Check user has `manage.role` and `manage.permission` permissions

License
-------

[](#license)

MIT License. See LICENSE file for details.

Support
-------

[](#support)

For issues and questions, please open an issue on GitHub:

Contributing
------------

[](#contributing)

Contributions are welcome! Please feel free to submit a Pull Request.

###  Health Score

21

—

LowBetter than 18% of packages

Maintenance61

Regular maintenance activity

Popularity1

Limited adoption so far

Community6

Small or concentrated contributor base

Maturity14

Early-stage or recently created project

 Bus Factor1

Top contributor holds 100% of commits — single point of failure

How is this calculated?**Maintenance (25%)** — Last commit recency, latest release date, and issue-to-star ratio. Uses a 2-year decay window.

**Popularity (30%)** — Total and monthly downloads, GitHub stars, and forks. Logarithmic scaling prevents top-heavy scores.

**Community (15%)** — Contributors, dependents, forks, watchers, and maintainers. Measures real ecosystem engagement.

**Maturity (30%)** — Project age, version count, PHP version support, and release stability.

### Community

Maintainers

![](https://avatars.githubusercontent.com/u/71527799?v=4)[Adam Nowak](/maintainers/NowakAdmin)[@NowakAdmin](https://github.com/NowakAdmin)

---

Top Contributors

[![NowakAdmin](https://avatars.githubusercontent.com/u/71527799?v=4)](https://github.com/NowakAdmin "NowakAdmin (49 commits)")

### Embed Badge

![Health badge](/badges/nowakadmin-nova-role-manager/health.svg)

```
[![Health](https://phpackages.com/badges/nowakadmin-nova-role-manager/health.svg)](https://phpackages.com/packages/nowakadmin-nova-role-manager)
```

###  Alternatives

[vitalybaev/laravel5-dkim

Laravel 5/6 package for signing outgoing messages with DKIM.

3163.1k](/packages/vitalybaev-laravel5-dkim)

PHPackages © 2026

[Directory](/)[Categories](/categories)[Trending](/trending)[Changelog](/changelog)[Analyze](/analyze)
