## Summary - complete Spec 136 canonical admin tenant rollout across admin-visible and shared Filament surfaces - add the shared panel-aware tenant resolver helper, persisted filter-state synchronization, and admin navigation segregation for tenant-sensitive resources - expand regression, guard, and parity coverage for admin-path tenant resolution, stale filters, workspace-wide tenant-default surfaces, and panel split behavior ## Validation - `vendor/bin/sail artisan test --compact tests/Feature/Guards/AdminTenantResolverGuardTest.php` - `vendor/bin/sail artisan test --compact tests/Feature/Filament/TableStatePersistenceTest.php` - `vendor/bin/sail artisan test --compact --filter='CanonicalAdminTenantFilterState|PolicyResource|BackupSchedule|BackupSet|FindingResource|BaselineCompareLanding|RestoreRunResource|InventoryItemResource|PolicyVersionResource|ProviderConnectionResource|TenantDiagnostics|InventoryCoverage|InventoryKpiHeader|AuditLog|EntraGroup'` - `vendor/bin/sail bin pint --dirty --format agent` ## Notes - Livewire v4.0+ compliance is preserved with Filament v5. - Provider registration remains unchanged in `bootstrap/providers.php`. - `PolicyResource` and `PolicyVersionResource` have admin global search disabled explicitly; `EntraGroupResource` keeps admin-aware scoped search with a View page. - Destructive and governance-sensitive actions retain existing confirmation and authorization behavior while using canonical tenant parity. - No new assets were introduced, so deployment asset strategy is unchanged and does not add new `filament:assets` work. Co-authored-by: Ahmed Darrazi <ahmed.darrazi@live.de> Reviewed-on: #165
6.3 KiB
Admin Canonical Tenant Rollout
Purpose
Spec 136 completes the workspace-admin canonical tenant rule across admin-visible and admin-reachable shared surfaces. Workspace-admin requests under /admin/... resolve tenant context through App\Support\OperateHub\OperateHubShell::activeEntitledTenant(request()). Tenant-panel requests under /admin/t/{tenant}/... keep panel-native tenant semantics.
Rollout Manifest
Type A: Hard tenant-sensitive
app/Filament/Resources/PolicyResource.phpapp/Filament/Resources/BackupScheduleResource.phpapp/Filament/Resources/BackupSetResource.phpapp/Filament/Resources/FindingResource.phpapp/Filament/Pages/BaselineCompareLanding.phpapp/Filament/Resources/RestoreRunResource.phpapp/Filament/Resources/InventoryItemResource.phpapp/Filament/Resources/PolicyVersionResource.phpapp/Filament/Pages/TenantDiagnostics.phpapp/Filament/Pages/InventoryCoverage.phpapp/Filament/Widgets/Inventory/InventoryKpiHeader.php
Type B: Workspace-wide with tenant-default behavior
app/Filament/Resources/ProviderConnectionResource.phpapp/Filament/Pages/Monitoring/AuditLog.phpapp/Filament/Resources/EntraGroupResource.phpapp/Filament/Resources/AlertDeliveryResource.php
Type C: Workspace-only non-regression references
app/Filament/Resources/AlertRuleResource.phpapp/Filament/Resources/BaselineProfileResource.phpapp/Filament/Resources/BaselineSnapshotResource.phpapp/Filament/Resources/TenantResource.php
Persisted Filter Sync
Apply App\Support\Filament\CanonicalAdminTenantFilterState::sync() on admin list surfaces that persist filters in session.
app/Filament/Resources/AlertDeliveryResource/Pages/ListAlertDeliveries.phpapp/Filament/Pages/Monitoring/AuditLog.phpapp/Filament/Resources/BackupScheduleResource/Pages/ListBackupSchedules.phpapp/Filament/Resources/BackupSetResource/Pages/ListBackupSets.phpapp/Filament/Resources/FindingResource/Pages/ListFindings.phpapp/Filament/Resources/InventoryItemResource/Pages/ListInventoryItems.phpapp/Filament/Resources/PolicyVersionResource/Pages/ListPolicyVersions.phpapp/Filament/Resources/ProviderConnectionResource/Pages/ListProviderConnections.phpapp/Filament/Resources/EntraGroupResource/Pages/ListEntraGroups.php
Guarded Files
These files must not introduce raw admin-path Tenant::current() or Filament::getTenant() reads:
app/Filament/Pages/BaselineCompareLanding.phpapp/Filament/Pages/TenantDiagnostics.phpapp/Filament/Pages/InventoryCoverage.phpapp/Filament/Widgets/Inventory/InventoryKpiHeader.phpapp/Filament/Resources/PolicyResource.phpapp/Filament/Resources/BackupScheduleResource.phpapp/Filament/Resources/InventoryItemResource.phpapp/Filament/Resources/PolicyVersionResource.phpapp/Filament/Resources/ProviderConnectionResource.phpapp/Filament/Resources/AlertDeliveryResource.phpapp/Filament/Resources/AlertDeliveryResource/Pages/ListAlertDeliveries.phpapp/Filament/Pages/Monitoring/AuditLog.phpapp/Filament/Resources/ProviderConnectionResource/Pages/ListProviderConnections.php
Exception Inventory
Approved tenant-panel-native or bootstrapping exceptions:
app/Filament/Pages/ChooseTenant.phpapp/Http/Controllers/SelectTenantController.phpapp/Support/Middleware/EnsureFilamentTenantSelected.phpapp/Filament/Resources/EntraGroupResource.phpapp/Filament/Concerns/ResolvesPanelTenantContext.php
app/Filament/Concerns/ResolvesPanelTenantContext.php is the only shared internal delegation wrapper allowed for this rollout. It is not a new public resolver. Admin semantics still come from OperateHubShell.
Global Search
PolicyResource: global search disabled explicitly.PolicyVersionResource: global search disabled explicitly.EntraGroupResource: global search remains enabled and uses admin-aware scoping with a View page.
Future-Surface Rule
Any new admin-visible or admin-reachable tenant-sensitive Filament surface must:
- resolve workspace-admin tenant context through
OperateHubShellor the internalResolvesPanelTenantContexthelper - keep tenant-panel requests panel-native
- synchronize persisted tenant-derived filters before render when
persistFiltersInSession()is used - disable global search unless list, detail, and search parity are explicitly tenant-safe
- keep destructive actions on
->action(...)with->requiresConfirmation()and server-side authorization
Verification Log
Wave 1
- 2026-03-11: automated parity coverage added for representative tenant-sensitive resources and admin list scoping.
- 2026-03-12: manual tenant-switch verification completed on
/admin/findingswithPhoenicon (DEV)andYPTW2 (DEV). - 2026-03-12: the admin shell changed visible finding rows and row-action tenant IDs together after switching tenants, confirming header context, list queries, and deep links stayed aligned.
Wave 2
- 2026-03-11: automated stale-filter and tenant-default coverage added for persisted filter surfaces.
- 2026-03-12: manual verification completed on
/admin/inventory/inventory-coverageafter fixing remembered-canonical-tenant handling inEnsureFilamentTenantSelected. - 2026-03-12: switching from
YPTW2 (DEV)toPhoenicon (DEV)changed tenant-driven KPI values while the shared support-matrix table remained available, confirming page-widget parity and the expected safe no-data state. - 2026-03-12: tenant-panel navigation under
/admin/t/{tenant}/...remained route-bound and required explicit tenant switching through the chooser flow instead of reusing remembered admin context.
Wave 3
- 2026-03-11: guard inventory and shared-surface panel-split coverage updated for the canonical rollout.
- 2026-03-12: manual verification completed on
/admin/provider-connectionsand confirmed the base dataset stays workspace-wide while the default tenant filter follows the active canonical admin tenant. - 2026-03-12: clearing the tenant filter exposed workspace-wide provider connections, while switching back to another tenant reseeded the tenant-default pill and
tenant_iddeep links for the newly selected tenant. - 2026-03-12: admin search safety remained unchanged from the rollout contract:
PolicyResourceandPolicyVersionResourcestay disabled for global search, andEntraGroupResourcekeeps admin-aware global search with a View page.