Skip to content

Latest commit

 

History

History
100 lines (72 loc) · 2.82 KB

authorization-gates.md

File metadata and controls

100 lines (72 loc) · 2.82 KB

Authorization Gates

See Laravel docs about gates.

You do not need a complex RBAC to restrict access for particular application area. For the most cases a simple role and permissions system is enough.

Open App\Enums\AdminPermissionEnum - see a list of segregated admin permissions Open App\Enums\AdminRoleEnum - see the list of possible admin roles. Note that each role defines a list of permissions available for it.

Open App\Gates\AdminPermission - see permissions check implementation. Open App\Providers\AuthServiceProvider - see a new gate defined per each admin permission.

Open App\Http\Controllers\Admin\AdminController - see permission check at constructor.

Additional Gate Context

We could rewrite our gate definition in the way it accepts permission as argument. For example

<?php

use App\Gates\AdminPermission;
use Illuminate\Foundation\Support\Providers\AuthServiceProvider as ServiceProvider;
use Illuminate\Support\Facades\Gate;

class AuthServiceProvider extends ServiceProvider
{
    public function boot()
    {
        $this->registerPolicies();

        Gate::define('admin-permission', function (object $admin, $permission) {
            return AdminPermission::check($admin, $permission);
        });
    }
}

In this case our controller will look like following:

<?php

use App\Enums\AdminPermissionEnum;
use App\Http\Controllers\Controller;

class AdminController extends Controller
{
    public function __construct()
    {
        $this->authorize('admin-permission', [AdminPermissionEnum::ADMINS]);
    }
    
    // ...
}

In the first example a multiple gates were defined to simplify the code. Also, it allows permission checks via middleware. For example:

<?php

use App\Enums\AdminPermissionEnum;

Route::middleware('can:' . AdminPermissionEnum::ADMINS()->ability())->get('admins', AdminController::class . '@index');

The most common case for extra context in gate check is passing an Eloquent model instance. For example:

<?php

use App\Models\Article;
use Illuminate\Foundation\Support\Providers\AuthServiceProvider as ServiceProvider;
use Illuminate\Support\Facades\Gate;

class AuthServiceProvider extends ServiceProvider
{
    public function boot()
    {
        $this->registerPolicies();

        Gate::define('article-edit', function (object $user, Article $article) {
            if ($article->author_id === $user->id) {
                return true;
            }
            
            return false;
        });
    }
}

For the permission checks over entire CRUD policies are used.