Skip to content
Pro Analyzer — Available with ShieldCI Pro

Filament Custom Pages Analyzer

Analyzer IDCategorySeverityTime To Fix
filament-custom-pages🛡️ SecurityMedium10 minutes

What This Checks

Validates that custom Filament pages have proper authorization. Checks for:

  • Custom pages have canAccess() or authorize() method
  • Pages with sensitive operations (database writes, config changes) have authorization
  • Pages with forms have authorization to prevent unauthorized data submission
  • Weak canAccess() patterns: returning true literally, or only checking auth()->check() (login-only, no role/permission check)
  • Pages extending SettingsPage (from filament/spatie-laravel-settings-plugin) without authorization - reported at High severity because the parent class writes settings automatically
  • Dashboard pages are skipped entirely (panel-level auth typically covers them), including when the parent class is imported under an alias (use Filament\Pages\Dashboard as BasePage)
  • Accepts abort_unless(), $this->authorize(), or Gate::authorize() inside mount() as valid authorization patterns

Why It Matters

  • Unauthorized Access: Custom pages without authorization are accessible to all panel users
  • Data Modification: Pages with forms can be used to submit unauthorized data changes
  • Privilege Escalation: Sensitive operations (user management, settings) may be accessible to low-privilege users
  • Audit Trail: Without access control, there's no way to track who accessed what

How to Fix

Quick Fix (5 minutes)

Add canAccess() to your custom page:

php
// app/Filament/Pages/SystemSettings.php
class SystemSettings extends Page
{
    public static function canAccess(): bool
    {
        return auth()->user()?->hasRole('admin');
    }
}

Proper Fix (10 minutes)

1. Add authorization to pages with sensitive operations:

php
class ImportUsers extends Page
{
    public static function canAccess(): bool
    {
        return auth()->user()?->can('import', User::class);
    }

    public function import(): void
    {
        $this->authorize('import', User::class);

        // Import logic...
    }
}

2. Protect pages with forms:

php
class EditSettings extends Page implements HasForms
{
    public static function canAccess(): bool
    {
        return auth()->user()?->can('manage-settings');
    }

    public function save(): void
    {
        $this->authorize('manage-settings');

        // Save settings...
    }
}

References