Implements workspace-scoped managed tenant onboarding wizard (Filament v5 / Livewire v4) with strict RBAC (404/403 semantics), resumable sessions, provider connection selection/creation, verification OperationRun, and optional bootstrap. Removes legacy onboarding entrypoints and adds Pest coverage + spec artifacts (073). ## Summary <!-- Kurz: Was ändert sich und warum? --> ## Spec-Driven Development (SDD) - [ ] Es gibt eine Spec unter `specs/<NNN>-<feature>/` - [ ] Enthaltene Dateien: `plan.md`, `tasks.md`, `spec.md` - [ ] Spec beschreibt Verhalten/Acceptance Criteria (nicht nur Implementation) - [ ] Wenn sich Anforderungen während der Umsetzung geändert haben: Spec/Plan/Tasks wurden aktualisiert ## Implementation - [ ] Implementierung entspricht der Spec - [ ] Edge cases / Fehlerfälle berücksichtigt - [ ] Keine unbeabsichtigten Änderungen außerhalb des Scopes ## Tests - [ ] Tests ergänzt/aktualisiert (Pest/PHPUnit) - [ ] Relevante Tests lokal ausgeführt (`./vendor/bin/sail artisan test` oder `php artisan test`) ## Migration / Config / Ops (falls relevant) - [ ] Migration(en) enthalten und getestet - [ ] Rollback bedacht (rückwärts kompatibel, sichere Migration) - [ ] Neue Env Vars dokumentiert (`.env.example` / Doku) - [ ] Queue/cron/storage Auswirkungen geprüft ## UI (Filament/Livewire) (falls relevant) - [ ] UI-Flows geprüft - [ ] Screenshots/Notizen hinzugefügt ## Notes <!-- Links, Screenshots, Follow-ups, offene Punkte --> Co-authored-by: Ahmed Darrazi <ahmeddarrazi@adsmac.fritz.box> Reviewed-on: #88
160 lines
12 KiB
Markdown
160 lines
12 KiB
Markdown
---
|
||
|
||
description: "Tasks for Unified Managed Tenant Onboarding Wizard (073)"
|
||
---
|
||
|
||
# Tasks: Unified Managed Tenant Onboarding Wizard (073)
|
||
|
||
**Input**: Design documents from `specs/073-unified-managed-tenant-onboarding-wizard/`
|
||
|
||
**Tests**: Required (Pest). Use `vendor/bin/sail artisan test --compact ...`.
|
||
|
||
## Phase 1: Setup
|
||
|
||
- [X] T001 Confirm Sail is running and DB is reachable using docker-compose.yml (command: `vendor/bin/sail up -d`)
|
||
- [X] T002 Confirm baseline tests pass for the branch using phpunit.xml and tests/ (command: `vendor/bin/sail artisan test --compact`)
|
||
|
||
---
|
||
|
||
## Phase 2: Foundational (Blocking Prerequisites)
|
||
|
||
**Purpose**: Shared primitives required by all user stories (authz, data model, safety semantics).
|
||
|
||
- [X] T003 Add onboarding capability constant in app/Support/Auth/Capabilities.php
|
||
- [X] T004 Add onboarding capability mapping for Owner+Manager in app/Services/Auth/WorkspaceRoleCapabilityMap.php
|
||
- [X] T005 Implement Gate/Policy for onboarding authorization in app/Providers/AuthServiceProvider.php (enforce capabilities; no role-string checks)
|
||
- [X] T006 [P] Create TenantOnboardingSession model in app/Models/TenantOnboardingSession.php
|
||
- [X] T007 Create onboarding sessions migration in database/migrations/*_create_tenant_onboarding_sessions_table.php (unique workspace_id + tenant_id)
|
||
- [X] T008 Create tenant workspace binding migration in database/migrations/*_enforce_tenant_workspace_binding.php (ensure tenants.workspace_id is NOT NULL + FK; ensure tenants.tenant_id remains globally unique; deny cross-workspace duplicates)
|
||
- [X] T009 Verify tenant routing key strategy for v1: keep existing Filament tenant route-key stable (do NOT change external_id strategy in this feature); add a regression test that /admin/t/{tenant} continues to resolve the intended managed tenant
|
||
- [X] T010 [P] Add foundational authorization + data-model tests in tests/Feature/ManagedTenantOnboardingWizardTest.php (capability known, mapping correct, migrations applied)
|
||
|
||
**Checkpoint**: Foundational complete — user story work can begin.
|
||
|
||
---
|
||
|
||
## Phase 3: User Story 1 — Start Managed Tenant onboarding (Priority: P1) 🎯 MVP
|
||
|
||
**Goal**: Start or resume a workspace-scoped onboarding wizard and create exactly one Managed Tenant per global-unique `tenant_id` (Entra tenant ID), bound to exactly one workspace.
|
||
|
||
**Independent Test**: Start onboarding in an empty workspace and complete “Identify Managed Tenant”; assert exactly one tenant exists and a session is created/resumed.
|
||
|
||
- [X] T011 [P] [US1] Add wizard page class in app/Filament/Pages/Workspaces/ManagedTenantOnboardingWizard.php (Filament v5 / Livewire v4)
|
||
- [X] T012 [P] [US1] Add wizard view in resources/views/filament/pages/workspaces/managed-tenant-onboarding-wizard.blade.php
|
||
- [X] T013 [US1] Register wizard route in routes/web.php at `/admin/w/{workspace}/managed-tenants/onboarding` with `ensure-workspace-member` middleware and 404 semantics for non-members
|
||
- [X] T014 [US1] Implement wizard mount + workspace loading in app/Filament/Pages/Workspaces/ManagedTenantOnboardingWizard.php (abort 404 for non-member, 403 for missing onboarding capability)
|
||
- [X] T015 [US1] Implement Step 1 “Identify Managed Tenant” upsert in app/Filament/Pages/Workspaces/ManagedTenantOnboardingWizard.php (transactional; idempotent by workspace_id + tenant_id; tenant status `pending`)
|
||
- [X] T015b [US1] Enforce cross-workspace uniqueness in Step 1: if a tenant with the same tenant_id exists in a different workspace, deny-as-not-found (404) and do not create/update anything
|
||
- [X] T015c [US1] Membership bootstrap: after tenant upsert, ensure the initiating user has a Managed Tenant membership of role owner (create if missing); never allow tenant to end up with zero owners
|
||
- [X] T016 [US1] Persist/resume onboarding session in app/Models/TenantOnboardingSession.php (no secrets in state)
|
||
- [X] T017 [US1] Add audit events for onboarding start/resume in app/Services/Audit/WorkspaceAuditLogger.php (or existing audit service) and call from wizard actions
|
||
- [X] T018 [P] [US1] Add happy-path tests in tests/Feature/ManagedTenantOnboardingWizardTest.php (owner/manager can start; tenant created; session created)
|
||
- [X] T019 [P] [US1] Add negative auth tests in tests/Feature/ManagedTenantOnboardingWizardTest.php (non-member gets 404; member without capability gets 403)
|
||
- [X] T020 [P] [US1] Add idempotency tests in tests/Feature/ManagedTenantOnboardingWizardTest.php (repeat step does not create duplicates)
|
||
- [X] T020b [P] [US1] Add tests asserting membership bootstrap: newly created tenant has exactly one owner membership for the initiator; attempting to remove/demote the last owner is blocked (can be a minimal service/policy-level assertion)
|
||
- [X] T020c [P] [US1] Add tests asserting cross-workspace protection: if tenant_id exists under another workspace, the wizard returns 404 and does not reveal the existence of that tenant
|
||
|
||
### Remove legacy entry points (required by FR-001)
|
||
|
||
- [X] T021 [US1] Remove tenant registration from app/Providers/Filament/AdminPanelProvider.php (drop `->tenantRegistration(...)`)
|
||
- [X] T022 [US1] Remove `/admin/register-tenant` route from routes/web.php (must behave as not found)
|
||
- [X] T023 [US1] Replace legacy onboarding redirects with 404 in routes/web.php (`/admin/managed-tenants`, `/admin/managed-tenants/onboarding`, `/admin/new`, workspace onboarding redirect stub)
|
||
- [X] T024 [US1] Remove RegisterTenant references in app/Filament/Pages/ChooseTenant.php and app/Filament/Pages/Workspaces/ManagedTenantsLanding.php
|
||
- [X] T025 [P] [US1] Add regression tests in tests/Feature/ManagedTenantOnboardingWizardTest.php asserting legacy endpoints return 404 (no redirects)
|
||
|
||
|
||
**Checkpoint**: US1 complete — wizard is the only entry point; onboarding start is safe + idempotent.
|
||
|
||
---
|
||
|
||
## Phase 4: User Story 2 — Configure a connection and verify access (Priority: P2)
|
||
|
||
**Goal**: Attach or create a Provider Connection and start verification as an `OperationRun` without leaking secrets.
|
||
|
||
**Independent Test**: Select/create connection, start verification, assert an OperationRun is created and job is dispatched; assert no secret material is returned.
|
||
|
||
- [X] T026 [US2] Implement Step 2 connection selection in app/Filament/Pages/Workspaces/ManagedTenantOnboardingWizard.php (auto-select default connection; allow switching)
|
||
- [X] T027 [US2] Implement connection creation path in app/Filament/Pages/Workspaces/ManagedTenantOnboardingWizard.php using app/Models/ProviderConnection.php and app/Services/Providers/CredentialManager.php (never display stored secrets)
|
||
- [X] T028 [US2] Persist selected connection id in app/Models/TenantOnboardingSession.php `state` (non-secret)
|
||
- [X] T029 [US2] Implement “Start verification” action using app/Services/Providers/ProviderOperationStartGate.php with operation type `provider.connection.check`
|
||
- [X] T029b [US2] Enforce/verify dedupe: clicking “Start verification” twice while an active run exists must return the active OperationRun (no second run created); add a focused test (Bus::fake + assert single run)
|
||
- [X] T030 [US2] Ensure verification enqueues app/Jobs/ProviderConnectionHealthCheckJob.php and stores `operation_run_id` in onboarding session state
|
||
- [X] T031 [US2] Add “View run” navigation to app/Filament/Resources/OperationRunResource.php (link from wizard action notification)
|
||
- [X] T032 [P] [US2] Add tests in tests/Feature/ManagedTenantOnboardingWizardTest.php for connection default selection + switching
|
||
- [X] T033 [P] [US2] Add tests in tests/Feature/ManagedTenantOnboardingWizardTest.php for verification run creation + job dispatch (Bus::fake)
|
||
- [X] T034 [P] [US2] Add secret-safety tests in tests/Feature/ManagedTenantOnboardingWizardTest.php (no secret fields appear in response/session/run failure summary)
|
||
|
||
**Checkpoint**: US2 complete — verification is observable via OperationRun and secrets are safe.
|
||
|
||
---
|
||
|
||
## Phase 5: User Story 3 — Resume and complete onboarding (Priority: P3)
|
||
|
||
**Goal**: Resume an onboarding session, run optional bootstrap actions, and complete onboarding to activate the tenant.
|
||
|
||
**Independent Test**: Start onboarding, leave incomplete, resume as a different authorized owner/manager, complete verification + bootstrap, then mark tenant active.
|
||
|
||
- [X] T035 [US3] Implement session resume logic in app/Filament/Pages/Workspaces/ManagedTenantOnboardingWizard.php (load by workspace_id + tenant_id; shared resumability)
|
||
- [X] T036 [US3] Implement Step gating in app/Filament/Pages/Workspaces/ManagedTenantOnboardingWizard.php (cannot complete until verification succeeded)
|
||
- [X] T037 [US3] Implement optional bootstrap actions in app/Filament/Pages/Workspaces/ManagedTenantOnboardingWizard.php (start operations listed in app/Services/Providers/ProviderOperationRegistry.php)
|
||
- [X] T038 [US3] Persist bootstrap `operation_run_id`s in app/Models/TenantOnboardingSession.php `state`
|
||
- [X] T039 [US3] Implement completion: set tenant status `active`, set onboarding session `completed_at`, redirect to tenant dashboard (app/Filament/Pages/TenantDashboard.php)
|
||
- [X] T040 [P] [US3] Add tests in tests/Feature/ManagedTenantOnboardingWizardTest.php for resume by different authorized actor
|
||
- [X] T041 [P] [US3] Add tests in tests/Feature/ManagedTenantOnboardingWizardTest.php for completion and tenant status transition `pending` → `active`
|
||
- [X] T042 [P] [US3] Add tests in tests/Feature/ManagedTenantOnboardingWizardTest.php for bootstrap run creation (one OperationRun per selected action)
|
||
|
||
**Checkpoint**: US3 complete — onboarding is resumable and completes safely.
|
||
|
||
---
|
||
|
||
## Phase 6: Polish & Cross-Cutting Concerns
|
||
|
||
- [X] T043 Add Managed Tenant status badge mapping via BadgeCatalog/BadgeRenderer in app/Support/Badges/* (BADGE-001) and add mapping test in tests/Feature/Badges/TenantStatusBadgeTest.php
|
||
- [X] T044 Verify/extend audit coverage for FR-016: use stable audit action IDs (enum/registry), ensure redaction, and add at least one concrete feature test asserting audit rows for onboarding start + verification start (no secrets in payload)
|
||
- [X] T045 Verify last-owner protections cover both workspace + tenant memberships; extend policies if needed in app/Policies/* and add regression tests in tests/Feature/Rbac/*
|
||
- [X] T046 Run formatter on touched files (command: `vendor/bin/sail bin pint --dirty`)
|
||
- [X] T047 Run targeted test suite for onboarding (command: `vendor/bin/sail artisan test --compact tests/Feature/ManagedTenantOnboardingWizardTest.php`)
|
||
|
||
### Post-spec hardening (Filament-native UX)
|
||
|
||
- [X] T048 Refactor onboarding page to a Filament-native Wizard schema (replace header-action modals + step cards; persist per-step progress; keep strict RBAC and existing action methods)
|
||
- [X] T049 Fix tenant identify UX: entering an existing tenant GUID must not surface a raw 404 modal; bind legacy unscoped tenants to the current workspace when safely inferable and add a regression test
|
||
|
||
|
||
---
|
||
|
||
## Dependencies & Execution Order
|
||
|
||
### User Story completion order
|
||
|
||
1. US1 (P1) depends on Phase 2 only.
|
||
2. US2 (P2) depends on US1 (tenant/session + wizard scaffold).
|
||
3. US3 (P3) depends on US2 (verification state + run linking).
|
||
|
||
### Dependency graph
|
||
|
||
- Phase 1 → Phase 2 → US1 → US2 → US3 → Polish
|
||
|
||
---
|
||
|
||
## Parallel execution examples
|
||
|
||
### US1 parallel work
|
||
|
||
- [P] T011 and T012 can be implemented in parallel (page class vs blade view).
|
||
- [P] T018–T020 can be written in parallel (distinct test cases).
|
||
|
||
### US2 parallel work
|
||
|
||
- [P] T032–T034 can be written in parallel (selection tests vs run tests vs secret-safety tests).
|
||
|
||
### US3 parallel work
|
||
|
||
- [P] T040–T042 can be written in parallel (resume tests vs completion tests vs bootstrap tests).
|
||
|
||
---
|
||
|
||
## Implementation Strategy (MVP)
|
||
|
||
- MVP scope is US1 only: wizard-only entry point + idempotent tenant identification + resumable session skeleton + required authorization semantics + tests.
|