## Summary - add conditional polling support for the tenantless operation run viewer and tenant review pack card - add focused Pest coverage for active vs terminal polling behavior and related review pack access regressions - add the full Spec Kit artifacts for Spec 123, including spec, plan, research, data model, contracts, quickstart, tasks, and checklist ## Testing - `vendor/bin/sail artisan test --compact tests/Feature/OpsUx/RunDetailPollingStopsOnTerminalTest.php tests/Feature/Operations/TenantlessOperationRunViewerTest.php tests/Feature/ReviewPack/ReviewPackWidgetTest.php tests/Feature/ReviewPack/ReviewPackGenerationTest.php tests/Feature/ReviewPack/ReviewPackRbacTest.php` - `vendor/bin/sail bin pint --dirty --format agent` ## Notes - Manual QA task `T014` in the Spec Kit checklist remains to be completed outside this automated flow. - Livewire v4.0+ compliance is unchanged. - No panel provider changes were made; provider registration remains in `bootstrap/providers.php`. - No global-search behavior was changed. - No destructive actions were added or modified. - No new Filament assets were introduced; existing deployment expectations for `php artisan filament:assets` remain unchanged. Co-authored-by: Ahmed Darrazi <ahmed.darrazi@live.de> Reviewed-on: #149
200 lines
12 KiB
Markdown
200 lines
12 KiB
Markdown
# Tasks: Operations Auto-Refresh Pass
|
||
|
||
**Input**: Design documents from `/specs/123-operations-auto-refresh/`
|
||
**Prerequisites**: plan.md, spec.md, research.md, data-model.md, contracts/polling-contracts.yaml, quickstart.md
|
||
|
||
**Tests**: Tests are REQUIRED for this runtime behavior change. Use Pest feature tests via Sail.
|
||
**Operations**: No new `OperationRun` type or lifecycle work is required for this feature; tasks must reuse existing `OperationRun` observability semantics and preserve the existing tenantless Monitoring route.
|
||
**RBAC**: No authorization model changes are planned; tasks must preserve existing workspace membership checks for the tenantless run viewer and existing tenant capability checks for every tenant-scoped host surface that renders the review pack card.
|
||
**Filament UI Action Surfaces**: The affected Filament surfaces change passive refresh behavior only; no new actions, destructive flows, or action-matrix rows are introduced beyond the approved spec exemption.
|
||
**Filament UI UX-001**: No Create/Edit/View layout changes are required; tasks must preserve existing viewer and card layouts while adding non-noisy auto-refresh behavior.
|
||
|
||
**Organization**: Tasks are grouped by user story so each story remains independently testable.
|
||
|
||
## Phase 1: Setup (Shared Context)
|
||
|
||
**Purpose**: Align implementation with the approved polling contract and current codebase patterns before editing runtime code.
|
||
|
||
- [X] T001 [P] Review the approved polling behavior in specs/123-operations-auto-refresh/spec.md, specs/123-operations-auto-refresh/research.md, specs/123-operations-auto-refresh/contracts/polling-contracts.yaml, and specs/123-operations-auto-refresh/quickstart.md
|
||
- [X] T002 [P] Inspect the current shared polling implementations in app/Support/OpsUx/RunDetailPolling.php, app/Filament/Resources/OperationRunResource.php, app/Filament/Widgets/Dashboard/NeedsAttention.php, and resources/views/filament/widgets/dashboard/needs-attention.blade.php
|
||
|
||
---
|
||
|
||
## Phase 2: Foundational (Blocking Prerequisites)
|
||
|
||
**Purpose**: Confirm the active-vs-terminal state sources that both polling surfaces depend on.
|
||
|
||
**⚠️ CRITICAL**: No user story work should begin until this phase is complete.
|
||
|
||
- [X] T003 Confirm polling state ownership in app/Support/OpsUx/OperationStatusNormalizer.php, app/Support/ReviewPackStatus.php, app/Models/ReviewPack.php, app/Services/ReviewPackService.php, and app/Jobs/GenerateReviewPackJob.php so active and terminal semantics stay consistent across both surfaces
|
||
|
||
**Checkpoint**: Shared polling semantics are confirmed and user-story implementation can begin.
|
||
|
||
---
|
||
|
||
## Phase 3: User Story 1 - Watch an active operation complete (Priority: P1) 🎯 MVP
|
||
|
||
**Goal**: Make the tenantless operation run viewer update automatically while a run remains active.
|
||
|
||
**Independent Test**: Open `/admin/operations/{run}` for queued and running runs and verify the page emits auto-refresh behavior; open the same page for a completed run and verify it does not rely on manual refresh for active monitoring.
|
||
|
||
### Tests for User Story 1 ⚠️
|
||
|
||
> **NOTE**: Add or update these tests first and ensure they fail before implementation.
|
||
|
||
- [X] T004 [P] [US1] Extend tests/Feature/OpsUx/RunDetailPollingStopsOnTerminalTest.php to cover the shared queued/running polling contract and age-based interval expectations in app/Support/OpsUx/RunDetailPolling.php
|
||
- [X] T005 [P] [US1] Extend tests/Feature/Operations/TenantlessOperationRunViewerTest.php to assert queued and running runs render polling markup on the `/admin/operations/{run}` viewer while preserving the existing workspace-membership and tenant-entitlement access semantics on that canonical route
|
||
|
||
### Implementation for User Story 1
|
||
|
||
- [X] T006 [US1] Ensure app/Filament/Pages/Operations/TenantlessOperationRunViewer.php and resources/views/filament/pages/operations/tenantless-operation-run-viewer.blade.php surface the shared polling contract from app/Filament/Resources/OperationRunResource.php without breaking the existing hidden-tab and mounted-action guards in app/Support/OpsUx/RunDetailPolling.php
|
||
|
||
**Checkpoint**: User Story 1 should now allow operators to watch active tenantless runs update automatically.
|
||
|
||
---
|
||
|
||
## Phase 4: User Story 2 - Monitor review pack generation from the card (Priority: P2)
|
||
|
||
**Goal**: Make the tenant review pack card refresh itself while generation is queued or in progress.
|
||
|
||
**Independent Test**: Open any tenant-scoped host surface that renders `TenantReviewPackCard`, trigger review-pack generation, and verify the card refreshes itself until the pack finishes.
|
||
|
||
### Tests for User Story 2 ⚠️
|
||
|
||
- [X] T007 [P] [US2] Extend tests/Feature/ReviewPack/ReviewPackWidgetTest.php to assert queued and generating review pack states render `wire:poll.10s` on the card while preserving the widget’s existing tenant membership and review-pack capability behavior
|
||
- [X] T008 [P] [US2] Extend tests/Feature/ReviewPack/ReviewPackGenerationTest.php to keep `queued` and `generating` aligned as the only active lifecycle states that should drive card polling
|
||
|
||
### Implementation for User Story 2
|
||
|
||
- [X] T009 [US2] Add a review-pack polling interval resolver in app/Filament/Widgets/Tenant/TenantReviewPackCard.php that returns `10s` only when the latest pack status is `queued` or `generating`
|
||
- [X] T010 [US2] Apply conditional root-level polling markup in resources/views/filament/widgets/tenant/tenant-review-pack-card.blade.php using the interval exposed by app/Filament/Widgets/Tenant/TenantReviewPackCard.php
|
||
|
||
**Checkpoint**: User Story 2 should now let users observe review pack generation without manual refresh.
|
||
|
||
---
|
||
|
||
## Phase 5: User Story 3 - Avoid noisy refresh behavior on completed work (Priority: P3)
|
||
|
||
**Goal**: Stop polling cleanly for terminal or unknown states so completed surfaces remain stable.
|
||
|
||
**Independent Test**: Open completed/failed tenantless runs plus ready/failed/expired/no-pack review card states and confirm none of them emit polling markup or restart refresh loops.
|
||
|
||
### Tests for User Story 3 ⚠️
|
||
|
||
- [X] T011 [P] [US3] Extend tests/Feature/Operations/TenantlessOperationRunViewerTest.php to assert completed and failed tenantless runs render without polling markup when loaded directly in a terminal state, without regressing the route’s existing 404 and 403 behavior
|
||
- [X] T012 [P] [US3] Extend tests/Feature/ReviewPack/ReviewPackWidgetTest.php to assert ready, failed, expired, and no-pack card states render without polling markup
|
||
|
||
### Implementation for User Story 3
|
||
|
||
- [X] T013 [US3] Harden non-active fallback logic in app/Support/OpsUx/RunDetailPolling.php and app/Filament/Widgets/Tenant/TenantReviewPackCard.php so terminal or unrecognized states always resolve to `null` polling without visible UI churn
|
||
|
||
**Checkpoint**: User Story 3 should now guarantee stable terminal states across both surfaces.
|
||
|
||
---
|
||
|
||
## Phase 6: Polish & Cross-Cutting Concerns
|
||
|
||
**Purpose**: Final verification, manual QA, and formatting across all stories.
|
||
|
||
- [ ] T014 Perform the manual QA flow from specs/123-operations-auto-refresh/quickstart.md for one active and one terminal tenantless run plus one active and one terminal review pack generation lifecycle
|
||
- [X] T015 Run focused Pest coverage with `vendor/bin/sail artisan test --compact` for tests/Feature/OpsUx/RunDetailPollingStopsOnTerminalTest.php, tests/Feature/Operations/TenantlessOperationRunViewerTest.php, tests/Feature/ReviewPack/ReviewPackWidgetTest.php, and tests/Feature/ReviewPack/ReviewPackGenerationTest.php
|
||
- [X] T016 Run `vendor/bin/sail bin pint --dirty --format agent`
|
||
- [X] T017 Run existing non-regression authorization coverage with `vendor/bin/sail artisan test --compact` for tests/Feature/Operations/TenantlessOperationRunViewerTest.php and tests/Feature/ReviewPack/ReviewPackRbacTest.php to confirm routes, ownership semantics, and access rules remain unchanged
|
||
|
||
---
|
||
|
||
## Dependencies & Execution Order
|
||
|
||
### Phase Dependencies
|
||
|
||
- **Setup (Phase 1)**: No dependencies; can start immediately.
|
||
- **Foundational (Phase 2)**: Depends on Setup completion; blocks all user stories.
|
||
- **User Story 1 (Phase 3)**: Depends on Foundational completion; this is the MVP.
|
||
- **User Story 2 (Phase 4)**: Depends on Foundational completion; can proceed after US1 or in parallel once shared polling semantics are confirmed.
|
||
- **User Story 3 (Phase 5)**: Depends on Foundational completion and benefits from US1/US2 polling hooks being in place.
|
||
- **Polish (Phase 6)**: Depends on completion of the desired user stories.
|
||
|
||
### User Story Dependencies
|
||
|
||
- **US1**: No dependency on other stories; delivers the primary operator-facing value.
|
||
- **US2**: No dependency on US1; it depends only on the shared polling semantics confirmed in Phase 2.
|
||
- **US3**: Depends on the active-polling implementation paths from US1 and US2 so terminal-state behavior can be finalized and verified.
|
||
|
||
### Within Each User Story
|
||
|
||
- Tests should be added or updated first and observed failing before implementation.
|
||
- Shared helper or resolver changes should land before Blade markup changes that consume them.
|
||
- Story-specific verification should complete before moving to the next priority.
|
||
|
||
### Parallel Opportunities
|
||
|
||
- T001 and T002 can run in parallel.
|
||
- T004 and T005 can run in parallel.
|
||
- T007 and T008 can run in parallel.
|
||
- T011 and T012 can run in parallel.
|
||
- After Phase 2, US1 and US2 can be implemented in parallel if different contributors own the run viewer and review pack card.
|
||
|
||
---
|
||
|
||
## Parallel Example: User Story 1
|
||
|
||
```bash
|
||
Task: "Extend tests/Feature/OpsUx/RunDetailPollingStopsOnTerminalTest.php to cover the shared queued/running polling contract and age-based interval expectations"
|
||
Task: "Extend tests/Feature/Operations/TenantlessOperationRunViewerTest.php to assert queued and running runs render polling markup on the /admin/operations/{run} viewer"
|
||
```
|
||
|
||
---
|
||
|
||
## Parallel Example: User Story 2
|
||
|
||
```bash
|
||
Task: "Extend tests/Feature/ReviewPack/ReviewPackWidgetTest.php to assert queued and generating review pack states render wire:poll.10s on the card"
|
||
Task: "Extend tests/Feature/ReviewPack/ReviewPackGenerationTest.php to keep queued and generating aligned as the only active lifecycle states that should drive card polling"
|
||
```
|
||
|
||
---
|
||
|
||
## Parallel Example: User Story 3
|
||
|
||
```bash
|
||
Task: "Extend tests/Feature/Operations/TenantlessOperationRunViewerTest.php to assert completed and failed tenantless runs render without polling markup"
|
||
Task: "Extend tests/Feature/ReviewPack/ReviewPackWidgetTest.php to assert ready, failed, expired, and no-pack card states render without polling markup"
|
||
```
|
||
|
||
---
|
||
|
||
## Implementation Strategy
|
||
|
||
### MVP First (User Story 1 Only)
|
||
|
||
1. Complete Phase 1: Setup
|
||
2. Complete Phase 2: Foundational
|
||
3. Complete Phase 3: User Story 1
|
||
4. Validate queued and running tenantless operation runs auto-refresh correctly
|
||
5. Stop and review before broadening the change to the tenant review pack card if needed
|
||
|
||
### Incremental Delivery
|
||
|
||
1. Ship the tenantless run viewer polling improvement in US1
|
||
2. Add review pack card polling in US2
|
||
3. Harden terminal-state stability and non-active fallback behavior in US3
|
||
4. Finish with focused Sail tests, manual QA, and Pint
|
||
|
||
### Parallel Team Strategy
|
||
|
||
With multiple contributors:
|
||
|
||
1. One contributor owns tenantless run viewer tests and implementation (US1)
|
||
2. One contributor owns review pack card tests and implementation (US2)
|
||
3. One contributor validates terminal/noisy-state regression coverage (US3)
|
||
4. Recombine for focused Sail test execution and formatting
|
||
|
||
---
|
||
|
||
## Notes
|
||
|
||
- [P] tasks touch different files and can be executed in parallel.
|
||
- User story labels map each task to the corresponding story in spec.md.
|
||
- No migrations, no new routes, and no dependency changes are expected.
|
||
- Manual QA evidence belongs in review artifacts, not committed files.
|