diff --git a/src/Database/Seeders/BasePermissionSeeder.php b/src/Database/Seeders/BasePermissionSeeder.php index 6db252e..18fbfab 100644 --- a/src/Database/Seeders/BasePermissionSeeder.php +++ b/src/Database/Seeders/BasePermissionSeeder.php @@ -5,12 +5,16 @@ namespace Lloricode\FilamentSpatieLaravelPermissionPlugin\Database\Seeders; use Illuminate\Database\Seeder; -use Illuminate\Support\Collection; use Illuminate\Support\Str; +use Lloricode\FilamentSpatieLaravelPermissionPlugin\Database\Seeders\Support\PermissionSeeder; +use Lloricode\FilamentSpatieLaravelPermissionPlugin\Database\Seeders\Support\ResourceSeeder; use Spatie\Permission\Contracts\Permission as PermissionContract; abstract class BasePermissionSeeder extends Seeder { + /** + * @return array + */ abstract protected function permissionsByGuard(): array; public function run(): void @@ -18,32 +22,40 @@ public function run(): void $permissionClass = app(PermissionContract::class); collect($this->permissionsByGuard()) - ->map(fn (array $permissions) => collect($permissions)) ->each( - function (Collection $permissions, string $guardName) use ($permissionClass) { + function (PermissionSeeder $permissionSeeder, string $guardName) use ($permissionClass) { $output = $this->command->getOutput(); - $output->info('Seeding permissions for guard: ' . $guardName . ' ...'); + $output->title(sprintf('Seeding permissions for guard: [%s] ...', $guardName)); - $output->progressStart($permissions->count()); + $output->text('panels'); + $this->seedPanelsPagesWidgets($permissionSeeder->panels, $guardName); - $permissions->sort()->each( - function (string $permission) use ($permissionClass, $guardName, $output) { - $permissionClass->findOrCreate(name: $permission, guardName: $guardName); - $output->progressAdvance(); - } - ); + $output->text('pages'); + $this->seedPanelsPagesWidgets($permissionSeeder->pages, $guardName); - $output->progressFinish(); + $output->text('widgets'); + $this->seedPanelsPagesWidgets($permissionSeeder->widgets, $guardName); + + $output->text('resources'); + $this->seedResource($permissionSeeder->resources, $guardName); + + $allPermissionNames = $permissionSeeder->allPermissionNames(); + + $output->info(sprintf( + 'Done Seeding permissions for guard: [%s] with total of [%d] permissions.!', + $guardName, + count($allPermissionNames) + )); - $output->info('Done Seeding permissions for guard: ' . $guardName . '!'); $output->newLine(); $permissionClass::whereGuardName($guardName) - ->whereNotIn('name', $permissions) + ->whereNotIn('name', $allPermissionNames) ->delete(); } ); + } /** @param class-string $modelPolicy */ @@ -73,6 +85,55 @@ protected static function generatePermissionGroup(string $resourceName, array $p return collect($permissions) ->map(fn (string $permission) => "{$resourceName}.{$permission}") ->prepend($resourceName) + ->sort() ->toArray(); } + + /** + * @param array $permissionNames + */ + public function seedPanelsPagesWidgets(array $permissionNames, string $guardName): void + { + $permissionClass = app(PermissionContract::class); + + $permissionNames = collect($permissionNames); + + $output = $this->command->getOutput(); + $output->progressStart($permissionNames->count()); + + $permissionNames->sort()->each( + function (string $permission) use ($permissionClass, $guardName, $output) { + $permissionClass->findOrCreate(name: $permission, guardName: $guardName); + $output->progressAdvance(); + } + ); + + $output->progressFinish(); + } + + /** + * @param array $resourcePermissionNames + */ + public function seedResource(array $resourcePermissionNames, string $guardName): void + { + $permissionClass = app(PermissionContract::class); + + $permissionNames = collect(); + + foreach ($resourcePermissionNames as $resourcePermissionName) { + $permissionNames = $permissionNames->merge($resourcePermissionName->permissionNames); + } + + $output = $this->command->getOutput(); + $output->progressStart($permissionNames->count()); + + $permissionNames->sort()->each( + function (string $permission) use ($permissionClass, $guardName, $output) { + $permissionClass->findOrCreate(name: $permission, guardName: $guardName); + $output->progressAdvance(); + } + ); + + $output->progressFinish(); + } } diff --git a/src/Database/Seeders/DefaultPermissionSeeder.php b/src/Database/Seeders/DefaultPermissionSeeder.php index 61fab8c..b448f1c 100644 --- a/src/Database/Seeders/DefaultPermissionSeeder.php +++ b/src/Database/Seeders/DefaultPermissionSeeder.php @@ -7,39 +7,47 @@ use Exception; use Filament\Facades\Filament; use Filament\Panel; -use Illuminate\Support\Collection; use Illuminate\Support\Facades\Config; use Illuminate\Support\Facades\Gate; use Lloricode\FilamentSpatieLaravelPermissionPlugin\Contracts\HasPermissionPage; use Lloricode\FilamentSpatieLaravelPermissionPlugin\Contracts\HasPermissionWidgets; +use Lloricode\FilamentSpatieLaravelPermissionPlugin\Database\Seeders\Support\PermissionSeeder; +use Lloricode\FilamentSpatieLaravelPermissionPlugin\Database\Seeders\Support\ResourceSeeder; use Lloricode\FilamentSpatieLaravelPermissionPlugin\FilamentPermissionGenerateName; class DefaultPermissionSeeder extends BasePermissionSeeder { - /** @throws Exception */ + /** + * {@inheritdoc} + * + * @throws Exception + */ #[\Override] protected function permissionsByGuard(): array { return [ - Config::string('filament-permission.guard') => self::getPermissionsFromPanels() - ->merge(self::getPermissionsFromResourceModelPolicies()) - ->merge(self::getPermissionsFromWidgets()) - ->merge(self::getPermissionsFromPages()) - ->toArray(), + Config::string('filament-permission.guard') => new PermissionSeeder( + panels: self::getPermissionsFromPanels(), + pages: self::getPermissionsFromPages(), + widgets: self::getPermissionsFromWidgets(), + resources: self::getPermissionsFromResourceModelPolicies() + ), ]; } - /** @return \Illuminate\Support\Collection */ - private static function getPermissionsFromPanels(): Collection + /** @return array */ + private static function getPermissionsFromPanels(): array { return collect(Filament::getPanels()) ->map(fn (Panel $panel) => FilamentPermissionGenerateName::getPanelPermissionName($panel)) ->prepend(FilamentPermissionGenerateName::PANELS) - ->values(); + ->values() + ->sort() + ->toArray(); } - /** @return \Illuminate\Support\Collection */ - private static function getPermissionsFromResourceModelPolicies(): Collection + /** @return array */ + private static function getPermissionsFromResourceModelPolicies(): array { $permissionsByPolicy = collect(); @@ -47,16 +55,20 @@ private static function getPermissionsFromResourceModelPolicies(): Collection $modelPolicy = Gate::getPolicyFor($filamentResource::getModel()); - $permissionsByPolicy = $permissionsByPolicy->merge( - self::generateFilamentResourcePermissions($modelPolicy::class) - ); + $permissionsByPolicy->push(new ResourceSeeder( + resource: $filamentResource, + model: $filamentResource::getModel(), + modelPolicy: $modelPolicy::class, + permissionNames: self::generateFilamentResourcePermissions($modelPolicy::class) + )); + } - return $permissionsByPolicy; + return $permissionsByPolicy->sort()->toArray(); } - /** @return \Illuminate\Support\Collection */ - private static function getPermissionsFromWidgets(): Collection + /** @return array */ + private static function getPermissionsFromWidgets(): array { $permissionNames = collect(); @@ -67,16 +79,16 @@ private static function getPermissionsFromWidgets(): Collection } if ($permissionNames->isEmpty()) { - return $permissionNames; + return []; } $permissionNames->prepend(FilamentPermissionGenerateName::WIDGETS); - return $permissionNames; + return $permissionNames->sort()->toArray(); } - /** @return \Illuminate\Support\Collection */ - private static function getPermissionsFromPages(): Collection + /** @return array */ + private static function getPermissionsFromPages(): array { $permissionNames = collect(); @@ -87,11 +99,11 @@ private static function getPermissionsFromPages(): Collection } if ($permissionNames->isEmpty()) { - return $permissionNames; + return []; } $permissionNames->prepend(FilamentPermissionGenerateName::PAGES); - return $permissionNames; + return $permissionNames->sort()->toArray(); } } diff --git a/src/Database/Seeders/Support/PermissionSeeder.php b/src/Database/Seeders/Support/PermissionSeeder.php new file mode 100644 index 0000000..a60a0ad --- /dev/null +++ b/src/Database/Seeders/Support/PermissionSeeder.php @@ -0,0 +1,34 @@ + $resources + */ + public function __construct( + public array $panels, + public array $pages, + public array $widgets, + public array $resources, + ) {} + + /** + * @return array + */ + public function allPermissionNames(): array + { + $collect = collect($this->panels) + ->merge($this->pages) + ->merge($this->widgets); + + foreach ($this->resources as $resource) { + $collect = $collect->merge($resource->permissionNames); + } + + return $collect->toArray(); + } +} diff --git a/src/Database/Seeders/Support/ResourceSeeder.php b/src/Database/Seeders/Support/ResourceSeeder.php new file mode 100644 index 0000000..92164e9 --- /dev/null +++ b/src/Database/Seeders/Support/ResourceSeeder.php @@ -0,0 +1,18 @@ + $permissionNames + */ + public function __construct( + public string $resource, + public string $model, + public string $modelPolicy, + public array $permissionNames + ) {} +}