14

I am using Laravel 5.6 with spatie/laravel-permission version 2.9 also using Laravel Passport as auth driver with $guard = 'api'.

When I am trying to assign an array of permission like ['edit_project', 'add_project' 'delete_project'] to a role with help of this function

public function assignPermissions($role, $permissions)
    {

        $role = Role::findByName($role);

        $role->givePermissionTo($permissions);

        return $role;
    }

but getting the error There is no permission namededit_projectfor guardapi`.

Also I have at config/auth.php

return [

/*
|--------------------------------------------------------------------------
| Authentication Defaults
|--------------------------------------------------------------------------
|
| This option controls the default authentication "guard" and password
| reset options for your application. You may change these defaults
| as required, but they're a perfect start for most applications.
|
*/

'defaults' => [
    'guard' => 'web',
    'passwords' => 'users',
],

/*
|--------------------------------------------------------------------------
| Authentication Guards
|--------------------------------------------------------------------------
|
| Next, you may define every authentication guard for your application.
| Of course, a great default configuration has been defined for you
| here which uses session storage and the Eloquent user provider.
|
| All authentication drivers have a user provider. This defines how the
| users are actually retrieved out of your database or other storage
| mechanisms used by this application to persist your user's data.
|
| Supported: "session", "token"
|
*/

'guards' => [
    'web' => [
        'driver' => 'session',
        'provider' => 'users',
    ],

    'api' => [
        'driver' => 'passport',
        'provider' => 'users',
    ],
],

/*
|--------------------------------------------------------------------------
| User Providers
|--------------------------------------------------------------------------
|
| All authentication drivers have a user provider. This defines how the
| users are actually retrieved out of your database or other storage
| mechanisms used by this application to persist your user's data.
|
| If you have multiple user tables or models you may configure multiple
| sources which represent each model / table. These sources may then
| be assigned to any extra authentication guards you have defined.
|
| Supported: "database", "eloquent"
|
*/

'providers' => [
    'users' => [
        'driver' => 'eloquent',
        'model' => App\User::class,
    ],

    // 'users' => [
    //     'driver' => 'database',
    //     'table' => 'users',
    // ],
],

/*
|--------------------------------------------------------------------------
| Resetting Passwords
|--------------------------------------------------------------------------
|
| You may specify multiple password reset configurations if you have more
| than one user table or model in the application and you want to have
| separate password reset settings based on the specific user types.
|
| The expire time is the number of minutes that the reset token should be
| considered valid. This security feature keeps tokens short-lived so
| they have less time to be guessed. You may change this as needed.
|
*/

'passwords' => [
    'users' => [
        'provider' => 'users',
        'table' => 'password_resets',
        'expire' => 60,
    ],
],

];

if there is any solution please help me with it thanks.

as well I am seeding the permission table by help of Larvel seeder which my permission table looks at the first time like below which the guard_name is web.

enter image description here

but manually I am changing the guard_name field to "api" which my permission table became like this.

enter image description here

apokryfos
  • 38,771
  • 9
  • 70
  • 114
Barakzai
  • 351
  • 1
  • 3
  • 10

11 Answers11

55

After creating permissions, running the following commands should work as it worked for me.

php artisan cache:forget spatie.permission.cache 

then

php artisan cache:clear

Note: In Ubuntu you may need to run these commands as sudo...

AnasSafi
  • 5,353
  • 1
  • 35
  • 38
Qasim Ali
  • 787
  • 6
  • 17
9

Clear your cache php artisan cache:clear

if this does not work use sudo php artisan cache:clear it worked for me once i use sudo

beatusfk
  • 451
  • 6
  • 4
6

The package uses the default guard unless instructed otherwise. The way to instruct it otherwise is to add the following to the Role class public $guard_name = 'api';. Of course adding that to the class in the vendor directory is a bad idea so you'd want to extend it and specify the guard like this

use Spatie\Permission\Models\Role as OriginalRole;

class Role extends OriginalRole
{
    public $guard_name = 'api';
}

Then if you haven't done so already, generate the config file with php artisan vendor:publish --provider="Spatie\Permission\PermissionServiceProvider" --tag="config"

Lastly you'll want to register your Role in config/permissions.php by changing 'role' => Spatie\Permission\Models\Role::class, to 'role' => \App\Models\Role::class, (of course this will vary based on where your Role class is)

Also the example from your question mentions add_project but the database shows create_project so make sure you're using the same names everywhere.

joelrosenthal
  • 471
  • 4
  • 10
4

Move the web and api places from

'guards' => [
    'web' => [
        'driver' => 'session',
        'provider' => 'users',
    ],

    'api' => [
        'driver' => 'passport',
        'provider' => 'users',
    ],
],

To

'guards' => [

        'api' => [
            'driver' => 'passport',
            'provider' => 'users',
        ],

        'web' => [
            'driver' => 'session',
            'provider' => 'users',
        ],
    ]

run php artisan cache:clear

Barakzai
  • 351
  • 1
  • 3
  • 10
  • 1
    Not quite, changing the order of the guards won't fix the problem. What could be done, although I would recommend against it is to change the default guard but that's set in the `defaults` in `config/auth.php`. If the default is being relied on anywhere in the application there would be side effects. – joelrosenthal Mar 04 '18 at 18:29
  • In my case the driver i was using under API guard was 'token' , so I changed my /config/auth.php to looks like this ` 'guards' => [ 'api' => [ 'driver' => 'token', 'provider' => 'users', ], 'web' => [ 'driver' => 'session', 'provider' => 'users', ], ], ` – macleash Jun 12 '21 at 14:05
2

You need to specify the guard when creating a role or permission failure of which spatie will take on the first guard that appears in the config/auth in this case "web"

'defaults' => [
'guard' => 'web',
'passwords' => 'users',
   ],

You need to approach as follows:

// Create a manager role for users authenticating with the api guard:
$role = Role::create(['guard_name' => 'api', 'name' => 'manager']);

// Define a `edit_project` permission for the admin users belonging to the api guard
$permission = Permission::create(['guard_name' => 'api', 'name' => 'edit_project']);
  • I was facing issues for different guard then I check this work for me permission was not set to new guard so if there will be no permission to this error will occur .. This work for me – kantsverma Oct 29 '21 at 12:39
2

It might be a permissions issue. run below command.

sudo php artisan permission:cache-reset
Dharmesh Rakholia
  • 1,210
  • 9
  • 22
1

In your user model add protected $guard_name = 'api'; This will override the default guard which is web.

GotaloveCode
  • 994
  • 1
  • 13
  • 30
1

If you want to do this from your code you can clear the cache straight from your code.

\DB::table('permissions')->insert([['name' => 'create Stuff', 'guard_name' => 'web']]);
\Artisan::call('cache:clear');
$role = Role::findByName('admin');
$role->givePermissionTo('create Stuff');
Jean-Roch B.
  • 486
  • 4
  • 10
0

Sometimes it happens if you override model events; such as create, created, and updated, ... I experienced this problem in my test cases when I used the Event::fake() to mock Events.

  • This does not provide an answer to the question. Once you have sufficient [reputation](https://stackoverflow.com/help/whats-reputation) you will be able to [comment on any post](https://stackoverflow.com/help/privileges/comment); instead, [provide answers that don't require clarification from the asker](https://meta.stackexchange.com/questions/214173/why-do-i-need-50-reputation-to-comment-what-can-i-do-instead). - [From Review](/review/late-answers/34125697) – Eyad Mohammed Osama Apr 04 '23 at 11:32
0

After a lot of research, I had to delete cache data manually. Laravel stores it on /storage/framework/cache/data. After that the new permission worked perfectly

Juan Joya
  • 120
  • 5
-2

Empty the role and permission tables in the database and then fill in the tables again. I had this error and I fixed it this way