- Added `priority`-based access logic to restrict role and user management actions. - Introduced `Permission Manager` UI and routes for permission access control. - Updated `RoleService` and `AppRoleService` to include `visible` scope for priority filtering. - Enhanced seeding to assign priorities to default roles and ensure proper hierarchy. - Updated sidebar, routes, and data structure to handle new permission enums and resource segmentation. - Improved UI components to dynamically restrict visibility and actions based on role priority.
65 lines
1.8 KiB
PHP
65 lines
1.8 KiB
PHP
<?php
|
|
|
|
declare(strict_types=1);
|
|
|
|
namespace App\Services;
|
|
|
|
use App\Data\Permissions\PermissionData;
|
|
use App\Data\Role\RoleData;
|
|
use App\Helpers\AppPermission;
|
|
use App\Models\Role;
|
|
use NoDiscard;
|
|
use Spatie\LaravelData\{DataCollection, PaginatedDataCollection};
|
|
use Spatie\Permission\Models\Permission;
|
|
|
|
final class PermissionManagerService
|
|
{
|
|
/**
|
|
* Returns a Paginated Collection of roles with their permissions and users DTO.
|
|
*
|
|
* @return PaginatedDataCollection<int, RoleData>
|
|
*/
|
|
#[NoDiscard]
|
|
public function getRolesWithPermissionsAndUsers(): PaginatedDataCollection
|
|
{
|
|
$roles = Role::query()
|
|
->visible()
|
|
->with(['permissions:id,name', 'users:id,name'])
|
|
->orderBy('priority', 'asc')
|
|
->paginate();
|
|
|
|
return RoleData::collect($roles, PaginatedDataCollection::class);
|
|
}
|
|
|
|
/**
|
|
* Get all non-app system permissions mapped to the PermissionData DTO.
|
|
*
|
|
* @return DataCollection<int, PermissionData>
|
|
*/
|
|
#[NoDiscard]
|
|
public function getNonAppPermissions(): DataCollection
|
|
{
|
|
$permissions = Permission::all()
|
|
->filter(fn ($p) => null === AppPermission::type($p->name));
|
|
|
|
return PermissionData::collect($permissions, DataCollection::class);
|
|
}
|
|
|
|
/**
|
|
* Get a role by its ID, ensuring it has a priority strictly greater than the logged in user's priority.
|
|
*
|
|
* @throws \Symfony\Component\HttpKernel\Exception\HttpException
|
|
*/
|
|
public function getRoleForEditing(int $roleId): Role
|
|
{
|
|
$role = Role::query()->findOrFail($roleId);
|
|
|
|
$userPriority = auth()->user()?->roles()->min('priority') ?? 999999;
|
|
if ($role->priority <= $userPriority) {
|
|
abort(403, 'Unauthorized to manage permissions for this role.');
|
|
}
|
|
|
|
return $role;
|
|
}
|
|
}
|