test(redesign): accept Phase 4 foundations with migration gates

This commit is contained in:
cesnimda
2026-09-13 19:18:33 +02:00
parent c99f4fb7dd
commit 2a2f9e4805
42 changed files with 17820 additions and 4 deletions
+3 -1
View File
@@ -8,5 +8,7 @@ Phase 4 starts from `f696f23` on `codex/ui-redesign-phase4`. The 57 preservation
- [P4-03 builder preview keyboard boundary](p4-03/README.md)
- [P4-04 page layout and typography primitives](p4-04/README.md)
- [P4-05 table/list density contract](p4-05/README.md)
- [P4-06 shared validation and Phase 5 gates](p4-06/README.md)
- [Phase 4 preservation acceptance — all 57 contracts](p4-06/PRESERVATION_ACCEPTANCE.md)
P4-02 is locally validated after `115441a` and the separate documentation restructure `682a302` on the same Phase 4 branch. P4-03 follows the P4-02 checkpoint `ebd4a3e`, adding preview keyboard access and preserving focused panes through viewport transitions. P4-04 follows `806eee4e`, introducing opt-in shared page/section typography and layout with Settings as the sole consumer. P4-05 follows `2cdcab9e`, adding opt-in Comfortable/Compact spacing to the existing Jobs/Trash table and phone cards. Its baseline is 916 backend / 354 frontend / 51 actual browser passes plus unchanged P2-D01 expected failure. P4-06 remains unstarted. No broader page migration, CV margin/template rendering correction, B07, backend/schema behaviour change or production deployment is included. F04 remains open pending actual production ingress evidence.
P4-02 is locally validated after `115441a` and the separate documentation restructure `682a302` on the same Phase 4 branch. P4-03 follows the P4-02 checkpoint `ebd4a3e`, adding preview keyboard access and preserving focused panes through viewport transitions. P4-04 follows `806eee4e`, introducing opt-in shared page/section typography and layout with Settings as the sole consumer. P4-05 follows `2cdcab9e`, adding opt-in Comfortable/Compact spacing to the existing Jobs/Trash table and phone cards. Its baseline is 916 backend / 354 frontend / 51 actual browser passes plus unchanged P2-D01 expected failure. P4-06 reviews that combined foundation at `c99f4fb7`, with all 57 contracts reconciled and explicit migration gates. Its conditional readiness verdict is not blanket permission for broad migration. No Phase 5 implementation, CV margin/template rendering correction, B07, backend/schema behaviour change or production deployment is included. F04 remains open pending actual production ingress evidence.
@@ -0,0 +1,217 @@
# Phase 4 preservation acceptance matrix
Scope: `c99f4fb7` application, validated at P4-06. All **57/57** original groups are reconciled; this is mapping completeness, **not exhaustive behavioral coverage or a 100% acceptance score**. Each row keeps every sub-capability, route and owner in its [Phase 2 source contract](../../phase-2/PRESERVATION_MATRIX.md) and [Phase 3 impact](../../phase-3/PRESERVATION_IMPACT_MATRIX.md).
Touch classification: **Direct** = a consumer/presentation owner changed; **Shared** = existing modal/notice/editor caller receives the change; **Theme only** = no domain owner change, but shared MUI styling reaches the surface. E09 is an unchanged security regression dependency. Documentation-comment changes caused by the earlier docs restructure are not feature changes. Original assertions marked NEW below refer to their Phase 2 addition, not new P4-06 tests; P4-06 adds no test cases.
**Scoped acceptance** accepts the bounded Phase 4 change, not untested sub-workflows. **Regression retained** means mapped tests still pass and the domain owner was not restructured. **Conditional** identifies an affected migration gate; passing component/service tests cannot replace missing native/provider/manual evidence. V1–V5/M1 are defined in the [acceptance report](README.md#visual-accessibility-and-responsive-evidence). All inherited gaps below remain unless the extra evidence explicitly narrows one (for example Trash restore and preview keyboard access). F04 remains open for every row's production use.
| PRES ID / capability | Phase 4 touch | P4 slices | Automated evidence (original behavior assertions plus additions) | Visual/UX evidence | Known limitations and migration gate | Acceptance |
|---|---|---|---|---|---|---|
| **PRES-E01** — Public product/plans; honest unavailable billing | Theme only | 01 | [F:landing-page][F:landing-page.test.tsx], [F:planCatalog][F:planCatalog.test.ts], [F:LandingPage.authRedirect][F:LandingPage.authRedirect.test.tsx]; [B:AccountPlans][B:AccountPlansTests]. Free/Pro copy, unavailable checkout and authenticated redirect | Inherited public accessibility/smoke; no new marketing review. | Actual checkout/provider availability; public mobile/keyboard review | Regression retained |
| **PRES-E02** — Local login/register/remember, challenge, reset and verification | Theme only | 01 | [F:login-page][F:login-page.test.tsx], [F:verify-email-page][F:verify-email-page.test.tsx], [F:turnstile-widget][F:turnstile-widget.test.tsx]; [B:LocalAuthIdentity][B:LocalAuthIdentityTests], [B:AuthAndSystemController][B:AuthAndSystemControllerTests]. Configuration gates, two-factor branch, safe redirect, verification outcomes; smoke login | Inherited native login smoke; provider/reset paths not visually certified. | Real reset-email delivery, Turnstile widget/browser configuration, complete reset submit journey | Regression retained |
| **PRES-E03** — Google/Microsoft login, link, legacy relink and popup results | Theme only | 01 | [F:login-page][F:login-page.test.tsx], [F:microsoft-legacy-relink-page][F:microsoft-legacy-relink-page.test.tsx]; [B:GoogleTokenValidator][B:GoogleTokenValidatorTests], [B:MicrosoftTokenValidator][B:MicrosoftTokenValidatorTests], [B:LocalAuthIdentity][B:LocalAuthIdentityTests]. Provider failure/relink presentation and token validation | No new dedicated loaded visual proof; shared-theme exposure only. See original gaps. | Real consent/popups, revoked grants, provider sandbox; callbacks must retain origin/state | Regression retained |
| **PRES-E04** — 2FA challenge/recovery/setup/disable; trusted-device revocation | Theme only | 01 | [F:two-factor-settings][F:two-factor-settings.test.tsx], [F:login-page][F:login-page.test.tsx]; [B:TwoFactorController][B:TwoFactorControllerTests], [B:SessionsController][B:SessionsControllerTests]. Setup/recovery presentation, disable failure/retry; server trusted-device/session checks | No new dedicated loaded visual proof; shared-theme exposure only. See original gaps. | Real mobile authenticator/recovery and trusted-device UI traversal | Regression retained |
| **PRES-E05** — Session list/current device, revoke one/others, logout | Theme only | 01 | [F:session-boundary][F:session-boundary.test.ts], [F:account-scoped-state][F:account-scoped-state.test.tsx]; [B:SessionsController][B:SessionsControllerTests], [B:AuthSessionRevocation][B:AuthSessionRevocationTests]. Own active sessions only, revoke ownership and next-request invalidation; B02 browser logout | No new dedicated loaded visual proof; shared-theme exposure only. See original gaps. | Session-list card UI selection/refresh after remote revoke | Regression retained |
| **PRES-E06** — Avatar, account names/headline, email change and password | Theme only | 01 | [F:profile-page][F:profile-page.test.tsx], [F:verify-email-page][F:verify-email-page.test.tsx]; [B:AvatarStorage][B:AvatarStorageTests], [B:LocalAuthIdentity][B:LocalAuthIdentityTests]. Email change password/confirmation contract; safe avatar storage and identity endpoints | No new dedicated loaded visual proof; shared-theme exposure only. See original gaps. | Avatar upload/remove and password-change browser journeys | Regression retained |
| **PRES-E07** — Desktop collapse/mobile drawer, active nav and command search/actions | Direct | 01, 02, 04 (shell/command presentation only) | [F:sidebar-active-nav][F:sidebar-active-nav.test.ts], [F:app-shell-notifications][F:app-shell-notifications.test.tsx], [F:quick-command-preservation][F:quick-command-preservation.test.tsx]; [B:JobApplicationsAuthorization][B:JobApplicationsAuthorizationTests], [B:CompanyRelationship][B:CompanyRelationshipTests]. Active matching and notification entry; NEW job/company destinations, reviewed add and search reset; NEW browser keyboard navigation Additional: [semantic-foundations](../../../../job-tracker-ui/e2e/semantic-foundations.spec.ts), [named-controls-modal-state](../../../../job-tracker-ui/e2e/named-controls-modal-state.spec.ts), [settings-page-layout](../../../../job-tracker-ui/e2e/settings-page-layout.spec.ts). | V1–V5 plus M1; collapsed/mobile defect recorded. | Drawer focus return and collapse persistence in EN/NB; all command destinations before shell migration **Gate:** P4-02-D01, P4-06-O01/O02 before shell/command migration. | Conditional |
| **PRES-E08** — Theme/system, EN/NB hydration, toast/confirm/prompt and errors | Direct | 01, 02, 04, 05 | [F:theme-state][F:theme-state.test.tsx], [F:i18n-provider][F:i18n-provider.test.tsx], [F:confirm][F:confirm.test.tsx], [F:prompt][F:prompt.test.tsx], [F:dialog-flow][F:dialog-flow.test.tsx]; [B:LocalAuthIdentity][B:LocalAuthIdentityTests]. Hydrated theme/language, confirmation/cancellation and dialog behavior Additional: [semantic-foundations](../../../../job-tracker-ui/e2e/semantic-foundations.spec.ts), [named-controls-modal-state](../../../../job-tracker-ui/e2e/named-controls-modal-state.spec.ts), [settings-page-layout](../../../../job-tracker-ui/e2e/settings-page-layout.spec.ts), [table-density](../../../../job-tracker-ui/e2e/table-density.spec.ts). | V1–V5 plus M1; every theme/locale pair represented, not every route/state. | Not-found/error-boundary retry route; full locale/theme/state cross-product and OS theme changes **Gate:** P4-03-D01 tooltip and P4-04-O01 feedback placement before affected shared-state acceptance. | Conditional |
| **PRES-E09** — Account-switch private-state disposal and stale request rejection | Unchanged identity boundary | 01–05 regression dependency | [F:session-boundary][F:session-boundary.test.ts], [F:account-scoped-state][F:account-scoped-state.test.tsx]; [B:SessionContextMiddleware][B:SessionContextMiddlewareTests], [B:CurrentUserIdLiveEvaluation][B:CurrentUserIdLiveEvaluationTests], [B:OwnershipGuard][B:OwnershipGuardTests]. B02 stale mutation/read abort, account-scoped state; four real-API/two-tab account-isolation browser cases | Four native account-isolation cases; screenshots do not prove privacy. | Real BFCache variations and long offline retry; preserve server precondition even with old bundles | Regression retained |
| **PRES-J01** — NAV discovery/filter/sort/source/deadline/details | Theme only | 01 | [F:job-discovery][F:job-discovery.test.tsx]; [B:JobDiscoveryController][B:JobDiscoveryControllerTests], [B:JobOpportunitySync][B:JobOpportunitySyncTests]. Search/sort/source details, empty versus failure/retry; responsive discovery browser | No new dedicated loaded visual proof; shared-theme exposure only. See original gaps. | Live NAV freshness/API availability; long result keyboard traversal | Regression retained |
| **PRES-J02** — Saved searches, run/delete/alerts, result changes/dismissal | Shared | 02 (confirm) | [F:job-discovery][F:job-discovery.test.tsx]; [B:SavedJobSearchAlert][B:SavedJobSearchAlertTests], [B:JobDiscoveryController][B:JobDiscoveryControllerTests]. Saved search run, pause and dismiss controls; owner-scoped alert results Additional: [named-controls-modal-state](../../../../job-tracker-ui/e2e/named-controls-modal-state.spec.ts). | No new dedicated loaded visual proof; shared-theme exposure only. See original gaps. | Scheduler-to-notification browser journey, delete confirmation on mobile | Regression retained |
| **PRES-J03** — Reviewed manual/URL/paste job create, company/tags/dates, duplicates | Theme only | 01 | [F:quick-capture][F:quick-capture.test.tsx]; [B:JobImportService][B:JobImportServiceTests], [B:JobImportHttpTransport][B:JobImportHttpTransportTests], [B:JobApplicationsController][B:JobApplicationsControllerTests]. Preview before write, URL prefills, manual browser create; B01 real connection boundary | No new dedicated loaded visual proof; shared-theme exposure only. See original gaps. | Duplicate warning and company/date edge UI; creation-intent idempotency remains separate unresolved contract | Regression retained |
| **PRES-J04** — Extension/bookmarklet/share capture; post-create attachment/CV | Direct | 04 (Settings capture section) | [F:captureUrl][F:captureUrl.test.ts], [F:quick-capture][F:quick-capture.test.tsx], [F:quick-command-preservation][F:quick-command-preservation.test.tsx]; [B:JobImportService][B:JobImportServiceTests], [B:CvBuilder][B:CvBuilderTests]. Capture URL encoding/review/no auto-create, post-create CV; extension node tests; NEW keyboard add opens review only Additional: [settings-page-layout](../../../../job-tracker-ui/e2e/settings-page-layout.spec.ts). | V4 Settings capture section; installed extension not exercised. | Installed extension permissions/browser-share flow and optional attachment failure recovery | Scoped acceptance |
| **PRES-J05** — Job filters/sort/page/columns, saved views and row/mobile actions | Direct | 04, 05 | [F:application-workspace-overlay][F:application-workspace-overlay.test.tsx], [F:account-scoped-state][F:account-scoped-state.test.tsx], [F:daily-control-loop][F:daily-control-loop.test.tsx]; [B:JobApplicationsController][B:JobApplicationsControllerTests], [B:JobApplicationsEndpointBehavior][B:JobApplicationsEndpointBehaviorTests]. URL hydration, selection does not open row, list return/focus; browser dirty/full workspace Additional: [settings-page-layout](../../../../job-tracker-ui/e2e/settings-page-layout.spec.ts), [table-density](../../../../job-tracker-ui/e2e/table-density.spec.ts). | V5 both densities, 1440/1024/768 table, 390/320 cards; native row opening. | Saved-view CRUD browser journey, page-size changes with dirty nested state P4-05 narrows selection/sort/page/columns/reflow gaps; saved-view CRUD and dirty nested page-size remain. | Scoped acceptance |
| **PRES-J06** — Bulk status/delete, soft delete/trash/restore and job edit | Direct | 02 (confirm), 05 | [F:application-workspace-overlay][F:application-workspace-overlay.test.tsx], [F:confirm-flow][F:confirm-flow.test.tsx]; [B:JobApplicationsController][B:JobApplicationsControllerTests], [B:JobApplicationsAuthorization][B:JobApplicationsAuthorizationTests], [B:JobLifecycleEvent][B:JobLifecycleEventTests]. Selection and destructive confirmation primitive; server CRUD/ownership/lifecycle behavior Additional: [named-controls-modal-state](../../../../job-tracker-ui/e2e/named-controls-modal-state.spec.ts), [table-density](../../../../job-tracker-ui/e2e/table-density.spec.ts). | V5 select/delete/Trash restore; no bulk partial-failure certification. | Bulk partial failure and trash→restore UI journey; shared confirm tests alone do not prove bulk flow P4-05 now proves native Trash restore; bulk partial failure remains. | Scoped acceptance |
| **PRES-J07** — Kanban grouped statuses, pointer/keyboard move and precise menu | Shared | 02 (notice) | [F:kanban-grouped-board][F:kanban-grouped-board.test.tsx], [F:pipeline][F:pipeline.test.ts]; [B:JobPipeline][B:JobPipelineTests]. Keyboard pickup/drop, failed move keeps card, custom group and precise stages; dark browser test Additional: [named-controls-modal-state](../../../../job-tracker-ui/e2e/named-controls-modal-state.spec.ts). | V1 status semantics and inherited dark Kanban case; no touch device. | Touch drag, keyboard cancel/focus after responsive view switching | Regression retained |
| **PRES-J08** — Company/contact edits, pipeline dates and linked-job history | Shared | 02 (notice/confirm) | [F:companies-relationship][F:companies-relationship.test.tsx], [F:quick-command-preservation][F:quick-command-preservation.test.tsx]; [B:CompanyRelationship][B:CompanyRelationshipTests]. Job history/context and NEW command company destination Additional: [named-controls-modal-state](../../../../job-tracker-ui/e2e/named-controls-modal-state.spec.ts). | V1 loading/error/empty/populated; V2 dialog, error and focus return. | All contact/date edits persisted through browser; source URL safety **Gate:** P4-02-D02 durable accessible modal save error before company-form migration. | Conditional |
| **PRES-J09** — Recorded offers/compensation/deadlines/notes and source links | Theme only | 01 | [F:offer-comparison][F:offer-comparison.test.tsx]; [B:AnalyticsSalary][B:AnalyticsSalaryTests], [B:JobApplicationsEndpointBehavior][B:JobApplicationsEndpointBehaviorTests]. Recorded values/empty states and salary normalization | No new dedicated loaded visual proof; shared-theme exposure only. See original gaps. | Mobile many-offer comparison; localized currency/date visual review | Regression retained |
| **PRES-J10** — CSV/JSON export, JSON import and CSV-to-JSON conversion | Direct | 04 | [F:csv-export][F:csv-export.test.tsx]; [B:CsvExport][B:CsvExportTests], [B:JobApplicationsController][B:JobApplicationsControllerTests]. B05 formula/quotes/UTF-8/typed dates and numeric behavior; CSV browser byte download Additional: [settings-page-layout](../../../../job-tracker-ui/e2e/settings-page-layout.spec.ts). | Inherited native CSV byte download; V4 export placement; no desktop spreadsheet app. | Full browser JSON import/count/roundtrip; Excel/LibreOffice compatibility remains separately bounded | Scoped acceptance |
| **PRES-W01** — Full workspace, sections, legacy links and optional reusable overlay | Shared | 02 (confirm) | [F:application-workspace-overlay][F:application-workspace-overlay.test.tsx], [F:applicationWorkspace][F:applicationWorkspace.test.ts], [F:application-route-contracts][F:application-route-contracts.test.ts]; [B:ApplicationWorkspace][B:ApplicationWorkspaceTests]. Deep links, dirty cancel/discard, missing job and back/filter/focus; NEW actual App command/legacy entry Additional: [named-controls-modal-state](../../../../job-tracker-ui/e2e/named-controls-modal-state.spec.ts). | V5 keyboard entry/back and P2 dirty-route/legacy-link browser. | No active production caller of override/onClose overlay props found; full overlay parity needs a host fixture before adoption **Gate:** P4-02-D03 before mobile workspace migration; P2-D01 before package restructuring. | Conditional |
| **PRES-W02** — Detail/status/progression, recruiter/dates/description/timeline | Theme only | 01 | [F:application-intelligence][F:application-intelligence.test.tsx], [F:workflow-trust-signals][F:workflow-trust-signals.test.tsx], [F:daily-control-loop][F:daily-control-loop.test.tsx]; [B:JobApplicationsWorkflowSignals][B:JobApplicationsWorkflowSignalsTests], [B:JobApplicationsAppliedDateHistory][B:JobApplicationsAppliedDateHistoryTests]. Timeline source labels, next-action routing and applied-date history | V2 populated workspace and V5 status/row entry; mobile progress defect retained. | Edit/status→timeline real-browser sequence across locale/timezone **Gate:** P4-02-D03 before mobile progress/workspace migration. | Conditional |
| **PRES-W03** — Analysis, match/gaps, strategy and reviewed status/workflow suggestions | Theme only | 01 | [F:application-intelligence][F:application-intelligence.test.tsx], [F:application-workflow-assist][F:application-workflow-assist.test.tsx]; [B:ApplicationIntelligence][B:ApplicationIntelligenceTests], [B:StrategySnapshotOperation][B:StrategySnapshotOperationTests], [B:JobApplicationsEndpointBehavior][B:JobApplicationsEndpointBehaviorTests]. Loading/error/empty states, match and explicit suggested action behavior | No new dedicated loaded visual proof; shared-theme exposure only. See original gaps. | Actual model truthfulness/evaluation; source freshness and cancelled generation browser states | Regression retained |
| **PRES-W04** — Checklist create/edit/complete/delete/order and next action | Theme only | 01 | [F:application-checklist][F:application-checklist.test.tsx]; [B:ApplicationChecklist][B:ApplicationChecklistTests]. Persisted item actions and keyboard reorder; localized readiness | No new dedicated loaded visual proof; shared-theme exposure only. See original gaps. | Real-API mobile edit/delete and interruption recovery | Regression retained |
| **PRES-W05** — Attach/select/create/tailor CV and source context | Theme only | 01 | [F:application-assets][F:application-assets.test.tsx], [F:cv-builder-deep-link][F:cv-builder-deep-link.test.tsx]; [B:ApplicationAssets][B:ApplicationAssetsTests], [B:CvBuilder][B:CvBuilderTests]. Attach re-points only, detach keeps variant, foreign owner denied, tailoring never writes source; B02 API browser | P2 linked-CV setup/API assertions; successful SQLite tailoring unavailable. | P2-D01 SQLite tailoring ordering blocks successful real-browser guidance; actual attach→render relationship beyond existing service coverage **Gate:** P2-D01 native tailoring/capture success before relationship restructuring. | Conditional |
| **PRES-W06** — Cover-letter manual/AI review, versions/restore and dirty protection | Direct | 02 (AI option labels) | [F:application-assets][F:application-assets.test.tsx], [F:application-workspace-overlay][F:application-workspace-overlay.test.tsx]; [B:ApplicationAssets][B:ApplicationAssetsTests]. Manual save/discard/restore, linked-CV AI explicit apply then save, version history owner scope Additional: [named-controls-modal-state](../../../../job-tracker-ui/e2e/named-controls-modal-state.spec.ts). | V2 cover-letter options/modal; AI accept/reject are component tests, not real model output. | Whole-browser AI reject/provider success and cover-letter history persistence; no actual model called here **Gate:** P4-02-D04 context interpolation before affected AI UI migration. | Conditional |
| **PRES-W07** — Application drafts and immutable submitted package/archived binaries | Theme only | 01 | [F:application-assets][F:application-assets.test.tsx], [F:application-drafts][F:application-drafts.test.ts]; [B:SubmittedApplicationPackage][B:SubmittedApplicationPackageTests], [B:JobApplicationsApplicationPackage][B:JobApplicationsApplicationPackageTests], [B:JobApplicationsEndpointBehavior][B:JobApplicationsEndpointBehaviorTests]. Drafts keep ordinary notes; service frozen document/hash/copy-failure/tenant assertions; NEW native browser capture oracle | P2-D01 fails at native capture; archive assertions remain unreached. | P2-D01 expected failure: SQLite capture 500. NEW post-capture mutation/archive assertions are NOT reached. Require real storage/provider success before package restructuring **Gate:** P2-D01 native capture/archive success required; this workflow is NOT accepted end to end. | Conditional |
| **PRES-W08** — Attachments upload/category/name/AI consent/preview/download/delete | Direct | 02 (attachment names) | [F:attachments][F:attachments.test.tsx]; [B:AttachmentsController][B:AttachmentsControllerTests], [B:AttachmentConsistency][B:AttachmentConsistencyTests], [B:AttachmentFlagsRecompute][B:AttachmentFlagsRecomputeTests]. Empty/flag controls, storage consistency and owned download; NEW browser fixture uploads real UTF-8 binary Additional: [named-controls-modal-state](../../../../job-tracker-ui/e2e/named-controls-modal-state.spec.ts). | V2 real upload/purpose/name/delete dialog; frozen archive path blocked by P2-D01. | Archived bytes after live delete blocked by W07; drag/drop, rename and download browser journey **Gate:** P2-D01 archived-byte/delete proof required before package/document relationship migration. | Conditional |
| **PRES-W09** — Interview questions/answers/ready/manual removal/AI review | Shared | 02 (confirm) | [F:interview-prep][F:interview-prep.test.tsx]; [B:InterviewPrepPersistence][B:InterviewPrepPersistenceTests], [B:InterviewAiContext][B:InterviewAiContextTests], [B:InterviewPrep][B:InterviewPrepTests]. Explicit AI add, manual/answer readiness, relevant prompt context without invented defaults Additional: [named-controls-modal-state](../../../../job-tracker-ui/e2e/named-controls-modal-state.spec.ts). | No new dedicated loaded visual proof; shared-theme exposure only. See original gaps. | Populated mobile keyboard editing and real reload; actual model quality separate | Regression retained |
| **PRES-W10** — Debrief/follow-up draft/date/readiness | Theme only | 01 | [F:interview-prep][F:interview-prep.test.tsx]; [B:JobApplicationsFollowUpDraft][B:JobApplicationsFollowUpDraftTests], [B:InterviewPrep][B:InterviewPrepTests]. Neutral debrief template and follow-up content handling | No new dedicated loaded visual proof; shared-theme exposure only. See original gaps. | Timezone/reload browser chain; calendar defects remain outside Phase 2 | Regression retained |
| **PRES-W11** — Reminder rules/actions/notifications, ICS and Google/Outlook events | Shared | 02 (notice), 04 (Settings rules) | [F:daily-control-loop][F:daily-control-loop.test.tsx], [F:application-calendar][F:application-calendar.test.tsx], [F:settings-view][F:settings-view.test.tsx]; [B:ApplicationCalendarController][B:ApplicationCalendarControllerTests], [B:RulesEngineProspect][B:RulesEngineProspectTests], [B:NotificationSettingsController][B:NotificationSettingsControllerTests]. Provider write confirmation, ICS and permission; NEW per-scenario rule payload and real saved preference checks Additional: [named-controls-modal-state](../../../../job-tracker-ui/e2e/named-controls-modal-state.spec.ts), [settings-page-layout](../../../../job-tracker-ui/e2e/settings-page-layout.spec.ts). | V4 rule/notification persistence and failure; real calendar providers untested. | DST/date-only correctness and real provider timezone must be resolved separately; initial rules 500 not reproduced | Regression retained |
| **PRES-W12** — Async progress/failure/retry/cancel/notifications | Theme only | 01 | [F:operations-page][F:operations-page.test.tsx], [F:profile-page][F:profile-page.test.tsx]; [B:OperationsController][B:OperationsControllerTests], [B:UserOperationStore][B:UserOperationStoreTests], [B:CvProcessingOperation][B:CvProcessingOperationTests]. Failure retry/cancel, durable operation IDs; extraction polling keeps dirty fields | No new dedicated loaded visual proof; shared-theme exposure only. See original gaps. | Long-lived disconnect/reconnect and worker fault/recovery operational gaps | Regression retained |
| **PRES-C01** — Canonical structured career data and long-tail/custom sections | Theme only | 01 | [F:profile-page][F:profile-page.test.tsx]; [B:CareerProfileController][B:CareerProfileControllerTests], [B:CareerProfileService][B:CareerProfileServiceTests]. Structured field changes propagate to saved singleton, stable child IDs and relational roundtrip; NEW CV edit leaves master unchanged | P2 and V3 canonical/sibling unchanged after variant edits; not all profile sections. | Every long-tail section/mobile keyboard save; concurrent canonical saves outside scope | Regression retained |
| **PRES-C02** — Profile overview/completeness/import guidance/raw copy/history/restore | Theme only | 01 | [F:career-workspace-page][F:career-workspace-page.test.tsx], [F:profile-page][F:profile-page.test.tsx]; [B:CareerProfileService][B:CareerProfileServiceTests]. First/returning state, completeness/errors and non-destructive history restore | No new dedicated loaded visual proof; shared-theme exposure only. See original gaps. | Clipboard/avatar and full browser historical restore; real extraction quality separate | Regression retained |
| **PRES-C03** — Upload/extract/rebuild/reprocess/diff/select/accept/discard/retry/cancel | Theme only | 01 | [F:profile-page][F:profile-page.test.tsx]; [B:ProfileCvController][B:ProfileCvControllerTests], [B:CvProfileDiffService][B:CvProfileDiffServiceTests], [B:CvProcessingOperation][B:CvProcessingOperationTests], [B:CvExtractionCoverage][B:CvExtractionCoverageTests]. Queue/upload, operation retry, pending explicit apply and polling retains edits; extraction/diff service checks | No new dedicated loaded visual proof; shared-theme exposure only. See original gaps. | Manual low-confidence deselection/discard UI; OCR/scanned/unusual real-document quality | Regression retained |
| **PRES-C04** — Evidence bank source/category/tags/add/list/delete | Shared | 02 (confirm) | [F:career-evidence][F:career-evidence.test.tsx]; [B:CareerEvidenceController][B:CareerEvidenceControllerTests]. Sourced evidence creation, tags and owner boundaries Additional: [named-controls-modal-state](../../../../job-tracker-ui/e2e/named-controls-modal-state.spec.ts). | No new dedicated loaded visual proof; shared-theme exposure only. See original gaps. | Delete and many-item search/keyboard browser flow | Regression retained |
| **PRES-C05** — CV library create/copy/delete/templates/share/publication/PDF | Shared | 02 (confirm) | [F:cv-builder-page][F:cv-builder-page.test.tsx], [F:cv-template-thumbnail][F:cv-template-thumbnail.test.tsx]; [B:CvBuilder][B:CvBuilderTests], [B:PublicCvController][B:PublicCvControllerTests]. General/job-specific creation, delete cancel, duplication fresh slug, public revoke/republish; existing public browser PDF Additional: [named-controls-modal-state](../../../../job-tracker-ui/e2e/named-controls-modal-state.spec.ts). | Inherited library/public CV/PDF smoke; complete publication chain not exercised. | Complete library→publish/unpublish/revoke old link browser chain | Regression retained |
| **PRES-C06** — Studio tabs, preview debounce/pages/fit/save state/mobile panes | Direct | 01, 03 | [F:cv-builder-deep-link][F:cv-builder-deep-link.test.tsx]; [B:CvBuilder][B:CvBuilderTests]. Five tabs, deep-link/error/save state and preview retry; NEW real mobile Edit/Preview, reload and desktop split Additional: [semantic-foundations](../../../../job-tracker-ui/e2e/semantic-foundations.spec.ts), [builder-preview-keyboard](../../../../job-tracker-ui/e2e/builder-preview-keyboard.spec.ts). | V1/V2/V3 loaded panes, keyboard scroll, retry, edit/preview breakpoints. | Keyboard preview scroll/focus (known F15), all theme/page interactions **Gate:** Tooltip P4-03-D01, revision F01/D01 and dedicated rendering fidelity gates before broader editor work. P4-03 closes the preview keyboard-access portion; template/print fidelity is not closed. | Conditional |
| **PRES-C07** — Visibility/order/custom sections and item/document overrides | Direct | 01 (omitted-section contrast), 02 (confirm), 03 | [F:cv-builder-deep-link][F:cv-builder-deep-link.test.tsx], [F:cvBuilder][F:cvBuilder.test.ts]; [B:CvBuilder][B:CvBuilderTests]. Add/edit/delete/order/hide, override renders without master change; NEW persisted headline and sibling isolation Additional: [semantic-foundations](../../../../job-tracker-ui/e2e/semantic-foundations.spec.ts), [named-controls-modal-state](../../../../job-tracker-ui/e2e/named-controls-modal-state.spec.ts), [builder-preview-keyboard](../../../../job-tracker-ui/e2e/builder-preview-keyboard.spec.ts). | V1 omitted labels; V3 override/undo/redo; canonical/sibling API readback. | Native drag/touch and override reset-to-source browser flow; item-level real saved overrides beyond headline | Scoped acceptance |
| **PRES-C08** — Capability-aware templates/typography/color/header/skills/sidebar/photo | Direct | 02 | [F:cv-builder-deep-link][F:cv-builder-deep-link.test.tsx], [F:cvBuilder][F:cvBuilder.test.ts], [F:cv-template-thumbnail][F:cv-template-thumbnail.test.tsx]; [B:CvBuilder][B:CvBuilderTests]. Template change clears incompatible defaults; normalized overrides reach shared renderer, safe color/markdown Additional: [named-controls-modal-state](../../../../job-tracker-ui/e2e/named-controls-modal-state.spec.ts). | V1/V2 named template/customize controls; complete template fidelity is unverified. | Complete template×advanced control visual/render parity; inaccessible color controls baseline **Gate:** Complete template/control visual fidelity before template migration. P4-02 closes the specifically unnamed option controls; not every custom color-widget interaction. | Conditional |
| **PRES-C09** — A4/Letter/density/margins/dates/document locale/section presentation | Direct | 02 | [F:cvBuilder][F:cvBuilder.test.ts], [F:cv-builder-deep-link][F:cv-builder-deep-link.test.tsx]; [B:CvBuilder][B:CvBuilderTests]. Page sizes, NB controls/default labels/dates, section grid/columns; existing long searchable PDF browser Additional: [named-controls-modal-state](../../../../job-tracker-ui/e2e/named-controls-modal-state.spec.ts). | V2 page-size controls; V3 preview viewport, not print margin correctness. | All advanced combinations, print margins and long localized text manual review **Gate:** Dedicated margins/pagination/render-output acceptance before CV presentation migration. | Conditional |
| **PRES-C10** — Undo/redo, save queue, dirty guard, history restore/preview lifecycle | Shared | 02 (confirm), 03 (same editor) | [F:cv-builder-deep-link][F:cv-builder-deep-link.test.tsx]; [B:CvBuilder][B:CvBuilderTests]. Undo/redo, failed save retry, guard cancel, restore-as-new-version; NEW saved override reload Additional: [named-controls-modal-state](../../../../job-tracker-ui/e2e/named-controls-modal-state.spec.ts), [builder-preview-keyboard](../../../../job-tracker-ui/e2e/builder-preview-keyboard.spec.ts). | V3 autosave/undo/redo/viewport/preview retry; stale browser writes remain separate. | Multi-browser stale-CV revision remains separate defect; history-tab browser restore and offline navigation **Gate:** F01/D01 revision contract before save/history restructuring; serialize editor work. | Conditional |
| **PRES-C11** — Section and whole-document AI improve/translate/instruction/grammar review | Theme only | 01 | [F:ai-section-assistant][F:ai-section-assistant.test.tsx], [F:cv-builder-deep-link][F:cv-builder-deep-link.test.tsx]; [B:AiWorkspace][B:AiWorkspaceTests], [B:AiPrivacyPolicy][B:AiPrivacyPolicyTests], [B:ProEntitlementAuthorization][B:ProEntitlementAuthorizationTests]. NEW reject/close, edited acceptance, failure retry, whole-document apply/reject and malformed/missing/duplicate IDs rejected; no implicit PUT | V1/P2 Free locks; component accept/reject/regenerate evidence only; no provider invocation. | Real model factual validation and section→whole review interactions; Free-disabled controls proven in new browser | Regression retained |
| **PRES-C12** — Private PDF and published anonymous CV/PDF, long searchable pages | Theme only | 01 | [F:public-cv-page][F:public-cv-page.test.tsx]; [B:PublicCvController][B:PublicCvControllerTests], [B:PdfRenderAdmission][B:PdfRenderAdmissionTests], [B:CvBuilder][B:CvBuilderTests]. Anonymous public rendering versus private refusal; B03 shared capacity/failure; real multipage/public PDF browser | Inherited actual multipage/public PDF smoke; V3 scroll, not print-engine certification. | All templates/print engines; deployed Chromium/font behavior and PDF manual inspection **Gate:** Dedicated real preview/PDF fidelity before rendering migration. | Conditional |
| **PRES-M01** — Job-scoped manual correspondence/search/delete/paste import | Shared | 02 (confirm) | [F:end-to-end-trust-loop][F:end-to-end-trust-loop.test.tsx], [F:correspondence-search-context][F:correspondence-search-context.test.ts]; [B:CorrespondenceController][B:CorrespondenceControllerTests]. Canonical communication entry does not send mail, job context and CRUD ownership Additional: [named-controls-modal-state](../../../../job-tracker-ui/e2e/named-controls-modal-state.spec.ts). | No new dedicated loaded visual proof; shared-theme exposure only. See original gaps. | Manual note edit/delete/paste-import real browser; preserve send/log distinction | Regression retained |
| **PRES-M02** — Gmail candidate/thread import/refresh/sync/unlink/relink/move | Theme only | 01 | [F:correspondence-gmail-import][F:correspondence-gmail-import.test.tsx]; [B:GmailController][B:GmailControllerTests], [B:EmailOwnershipIntegration][B:EmailOwnershipIntegrationTests]. Candidates, selected thread import/move/refresh and diagnostics; owner-bound relationships | No new dedicated loaded visual proof; shared-theme exposure only. See original gaps. | Real provider/sandbox threads, multi-account reconnect and sync failure | Regression retained |
| **PRES-M03** — Global inbox filters/page/provider/link/direction/detail/source links | Theme only | 01 | [F:correspondence-inbox-page][F:correspondence-inbox-page.test.tsx]; [B:EmailController][B:EmailControllerTests], [B:EmailOwnershipIntegration][B:EmailOwnershipIntegrationTests]. Filter/pagination/detail/provider read failure distinct from empty | No new dedicated loaded visual proof; shared-theme exposure only. See original gaps. | Real large mailbox and attachment binary browser flows | Regression retained |
| **PRES-M04** — Compose/reply/provider/recipient/job; draft conflicts; confirm send/uncertainty | Shared | 02 (confirm) | [F:correspondence-inbox-page][F:correspondence-inbox-page.test.tsx]; [B:EmailDraftsController][B:EmailDraftsControllerTests], [B:EmailDraftPersistence][B:EmailDraftPersistenceTests], [B:EmailSendController][B:EmailSendControllerTests], [B:EmailSendAttemptStore][B:EmailSendAttemptStoreTests], [B:EmailProviderDelivery][B:EmailProviderDeliveryTests]. Revision conflicts, explicit send confirm, uncertain state has no automatic retry, deliberate new attempt Additional: [named-controls-modal-state](../../../../job-tracker-ui/e2e/named-controls-modal-state.spec.ts). | No new dedicated loaded visual proof; shared-theme exposure only. See original gaps. | Actual sandbox mail delivery and browser reconnect; do not loosen idempotency/conflict guards | Regression retained |
| **PRES-M05** — Review proposed jobs/link/reject/keep/notes/sync/create | Theme only | 01 | [F:gmail-review-page][F:gmail-review-page.test.tsx], [F:correspondence-inbox-page][F:correspondence-inbox-page.test.tsx]; [B:GmailController][B:GmailControllerTests]. Review decisions/localization and inbox review entry | No new dedicated loaded visual proof; shared-theme exposure only. See original gaps. | Real App legacy alias and suggested-job create browser workflow | Regression retained |
| **PRES-M06** — Gmail/Graph/IMAP connect/status/disconnect separate from sign-in | Direct | 04 (entry action only) | [F:email-provider-connections][F:email-provider-connections.test.tsx]; [B:MicrosoftGraphController][B:MicrosoftGraphControllerTests], [B:ImapController][B:ImapControllerTests], [B:ImapServiceSsrfGuard][B:ImapServiceSsrfGuardTests], [B:GmailController][B:GmailControllerTests]. Connection state/NB/IMAP form and provider ownership; outbound IMAP safety Additional: [settings-page-layout](../../../../job-tracker-ui/e2e/settings-page-layout.spec.ts). | V4 Connected Accounts entry; no external authorization or delivery. | Actual provider authorization/revocation/token expiry; no credentials contacted in new tests | Scoped acceptance |
| **PRES-S01** — Personal metrics/activity/funnel/company/skills/stage/salary/next actions | Shared | 02 (notice) | [F:daily-control-loop][F:daily-control-loop.test.tsx], [F:workflow-trust-signals][F:workflow-trust-signals.test.tsx]; [B:StageAnalytics][B:StageAnalyticsTests], [B:AnalyticsSalary][B:AnalyticsSalaryTests]. Empty dashboard prioritizes onboarding, attention deep links; server analytics facts Additional: [named-controls-modal-state](../../../../job-tracker-ui/e2e/named-controls-modal-state.spec.ts). | No new dedicated loaded visual proof; shared-theme exposure only. See original gaps. | Chart transformation fidelity and full populated/timezone browser dashboard | Regression retained |
| **PRES-S02** — Owner-local five visibility preferences/onboarding dismiss/notifications | Theme only | 01 | [F:onboarding-checklist][F:onboarding-checklist.test.tsx], [F:notifications-popover][F:notifications-popover.test.tsx], [F:app-shell-notifications][F:app-shell-notifications.test.tsx], [F:account-scoped-state][F:account-scoped-state.test.tsx]; [B:JobLifecycleEvent][B:JobLifecycleEventTests]. Onboarding actions; unread/read/dismiss UI and owner-scoped storage primitive | No new dedicated loaded visual proof; shared-theme exposure only. See original gaps. | Five dashboard toggles/reload per account not fully tested at mounted dashboard; ordering/resizing is new work | Regression retained |
| **PRES-S03** — Rules/reminder/table/theme/language preferences and account links | Direct | 04, 05 | [F:settings-view][F:settings-view.test.tsx], [F:theme-state][F:theme-state.test.tsx], [F:i18n-provider][F:i18n-provider.test.tsx]; [B:NotificationSettingsController][B:NotificationSettingsControllerTests], [B:RulesEngineProspect][B:RulesEngineProspectTests]. NEW failed notification retry, rule scenario preservation; NEW mobile→desktop edit + native notification/rule persistence Additional: [settings-page-layout](../../../../job-tracker-ui/e2e/settings-page-layout.spec.ts), [table-density](../../../../job-tracker-ui/e2e/table-density.spec.ts). | V4 native rule/notification saves and responsive drafts; V5 independent columns/page/density. | Initial single rules 500 unconfirmed; unsaved rule drafts are not persisted across tab unmount; table preference/router identity change gap **Gate:** P4-04-O02 concurrent notification writes remain unproven; preserve awaited-save tests. | Conditional |
| **PRES-S04** — AI privacy/usage/limits/Free-Pro/server entitlement/conditional billing | Direct | 04 | [F:settings-view][F:settings-view.test.tsx], [F:ai-usage-card][F:ai-usage-card.test.tsx], [F:pro-feature-notice][F:pro-feature-notice.test.tsx], [F:planCatalog][F:planCatalog.test.ts]; [B:AiPrivacyPolicy][B:AiPrivacyPolicyTests], [B:AiUsageMeter][B:AiUsageMeterTests], [B:ProEntitlementAuthorization][B:ProEntitlementAuthorizationTests], [B:BillingController][B:BillingControllerTests]. Local-only AI setting, limits/locks, billing readiness; NEW real Free CV AI denied UI and API Additional: [settings-page-layout](../../../../job-tracker-ui/e2e/settings-page-layout.spec.ts). | V1/V4 locked Free/zero-usage states; M1 synthetic admin Pro state only. | Real checkout/webhooks/portal; billing/account deletion issues retain independent queue | Scoped acceptance |
| **PRES-S05** — Account ZIP/encrypted backup/lifecycle/deletion confirmations | Direct | 02 (confirm), 04 | [F:account-data-export][F:account-data-export.test.tsx]; [B:AccountDataExport][B:AccountDataExportTests], [B:BackupController][B:BackupControllerTests], [B:AccountDeletion][B:AccountDeletionTests], [B:DatabaseBackupRunner][B:DatabaseBackupRunnerTests]. ZIP protected download, recent auth, server enable flag and exact deletion phrase; service deletion/backup Additional: [named-controls-modal-state](../../../../job-tracker-ui/e2e/named-controls-modal-state.spec.ts), [settings-page-layout](../../../../job-tracker-ui/e2e/settings-page-layout.spec.ts). | V4 no-job ZIP/disabled deletion and wrapped actions; no real restore/deletion rehearsal. | Real restored account/database and paid deletion/provider cancellation operational proof; not safe to run against production | Scoped acceptance |
| **PRES-A01** — Admin user/create/roles/reset/delete/last-admin/self guards | Shared | 02 (confirm) | [F:admin-users-page][F:admin-users-page.test.tsx]; [B:UsersController][B:UsersControllerTests], [B:ApiAuthorizationPosture][B:ApiAuthorizationPostureTests]. Demotion/delete confirm, last-admin server checks; NEW non-admin crafted create/read denied Additional: [named-controls-modal-state](../../../../job-tracker-ui/e2e/named-controls-modal-state.spec.ts). | P2 non-admin API denial; M1 synthetic admin shell only, not a user-management audit. | Role revocation during mounted admin view and actual reset delivery; route can render empty shell without granting privilege | Regression retained |
| **PRES-A02** — Audit list/detail/supported undo/job restore | Shared | 02 (notice) | [F:admin-audit-page][F:admin-audit-page.test.tsx]; [B:AuthAndSystemController][B:AuthAndSystemControllerTests], [B:ApiAuthorizationPosture][B:ApiAuthorizationPostureTests]. Unavailable-versus-empty retry and NB stored event text; server admin-only posture Additional: [named-controls-modal-state](../../../../job-tracker-ui/e2e/named-controls-modal-state.spec.ts). | No new dedicated loaded visual proof; shared-theme exposure only. See original gaps. | Successful undo and job-restore UI against persisted API; role posture test is not undo behavior proof | Regression retained |
| **PRES-A03** — System/build/DB/AI/mail/SMTP/test/probe/benchmark/maintenance | Theme only | 01 | [F:admin-system-page][F:admin-system-page.test.tsx]; [B:AuthAndSystemController][B:AuthAndSystemControllerTests], [B:MaintenanceJobDispatcher][B:MaintenanceJobDispatcherTests], [B:CvCorpusHarness][B:CvCorpusHarnessTests]. Health/error/NB, SMTP submit and benchmark controls; dispatcher authorization and modes | No new dedicated loaded visual proof; shared-theme exposure only. See original gaps. | Production SMTP/model/corpus/maintenance and sensitive-data presentation; no live jobs launched | Regression retained |
Classification totals: **15 conditional**, **34 regression retained**, **8 scoped acceptance**. These counts describe the review disposition, not the percentage of user behavior tested.
[F:landing-page.test.tsx]: ../../../../job-tracker-ui/src/landing-page.test.tsx
[F:planCatalog.test.ts]: ../../../../job-tracker-ui/src/planCatalog.test.ts
[F:LandingPage.authRedirect.test.tsx]: ../../../../job-tracker-ui/src/LandingPage.authRedirect.test.tsx
[B:AccountPlansTests]: ../../../../JobTrackerApi.Tests/AccountPlansTests.cs
[F:login-page.test.tsx]: ../../../../job-tracker-ui/src/login-page.test.tsx
[F:verify-email-page.test.tsx]: ../../../../job-tracker-ui/src/verify-email-page.test.tsx
[F:turnstile-widget.test.tsx]: ../../../../job-tracker-ui/src/turnstile-widget.test.tsx
[B:LocalAuthIdentityTests]: ../../../../JobTrackerApi.Tests/LocalAuthIdentityTests.cs
[B:AuthAndSystemControllerTests]: ../../../../JobTrackerApi.Tests/AuthAndSystemControllerTests.cs
[F:microsoft-legacy-relink-page.test.tsx]: ../../../../job-tracker-ui/src/microsoft-legacy-relink-page.test.tsx
[B:GoogleTokenValidatorTests]: ../../../../JobTrackerApi.Tests/GoogleTokenValidatorTests.cs
[B:MicrosoftTokenValidatorTests]: ../../../../JobTrackerApi.Tests/MicrosoftTokenValidatorTests.cs
[F:two-factor-settings.test.tsx]: ../../../../job-tracker-ui/src/two-factor-settings.test.tsx
[B:TwoFactorControllerTests]: ../../../../JobTrackerApi.Tests/TwoFactorControllerTests.cs
[B:SessionsControllerTests]: ../../../../JobTrackerApi.Tests/SessionsControllerTests.cs
[F:session-boundary.test.ts]: ../../../../job-tracker-ui/src/session-boundary.test.ts
[F:account-scoped-state.test.tsx]: ../../../../job-tracker-ui/src/account-scoped-state.test.tsx
[B:AuthSessionRevocationTests]: ../../../../JobTrackerApi.Tests/AuthSessionRevocationTests.cs
[F:profile-page.test.tsx]: ../../../../job-tracker-ui/src/profile-page.test.tsx
[B:AvatarStorageTests]: ../../../../JobTrackerApi.Tests/AvatarStorageTests.cs
[F:sidebar-active-nav.test.ts]: ../../../../job-tracker-ui/src/sidebar-active-nav.test.ts
[F:app-shell-notifications.test.tsx]: ../../../../job-tracker-ui/src/app-shell-notifications.test.tsx
[F:quick-command-preservation.test.tsx]: ../../../../job-tracker-ui/src/quick-command-preservation.test.tsx
[B:JobApplicationsAuthorizationTests]: ../../../../JobTrackerApi.Tests/JobApplicationsAuthorizationTests.cs
[B:CompanyRelationshipTests]: ../../../../JobTrackerApi.Tests/CompanyRelationshipTests.cs
[F:theme-state.test.tsx]: ../../../../job-tracker-ui/src/theme-state.test.tsx
[F:i18n-provider.test.tsx]: ../../../../job-tracker-ui/src/i18n-provider.test.tsx
[F:confirm.test.tsx]: ../../../../job-tracker-ui/src/confirm.test.tsx
[F:prompt.test.tsx]: ../../../../job-tracker-ui/src/prompt.test.tsx
[F:dialog-flow.test.tsx]: ../../../../job-tracker-ui/src/dialog-flow.test.tsx
[B:SessionContextMiddlewareTests]: ../../../../JobTrackerApi.Tests/SessionContextMiddlewareTests.cs
[B:CurrentUserIdLiveEvaluationTests]: ../../../../JobTrackerApi.Tests/CurrentUserIdLiveEvaluationTests.cs
[B:OwnershipGuardTests]: ../../../../JobTrackerApi.Tests/OwnershipGuardTests.cs
[F:job-discovery.test.tsx]: ../../../../job-tracker-ui/src/job-discovery.test.tsx
[B:JobDiscoveryControllerTests]: ../../../../JobTrackerApi.Tests/JobDiscoveryControllerTests.cs
[B:JobOpportunitySyncTests]: ../../../../JobTrackerApi.Tests/JobOpportunitySyncTests.cs
[B:SavedJobSearchAlertTests]: ../../../../JobTrackerApi.Tests/SavedJobSearchAlertTests.cs
[F:quick-capture.test.tsx]: ../../../../job-tracker-ui/src/quick-capture.test.tsx
[B:JobImportServiceTests]: ../../../../JobTrackerApi.Tests/JobImportServiceTests.cs
[B:JobImportHttpTransportTests]: ../../../../JobTrackerApi.Tests/JobImportHttpTransportTests.cs
[B:JobApplicationsControllerTests]: ../../../../JobTrackerApi.Tests/JobApplicationsControllerTests.cs
[F:captureUrl.test.ts]: ../../../../job-tracker-ui/src/captureUrl.test.ts
[B:CvBuilderTests]: ../../../../JobTrackerApi.Tests/CvBuilderTests.cs
[F:application-workspace-overlay.test.tsx]: ../../../../job-tracker-ui/src/application-workspace-overlay.test.tsx
[F:daily-control-loop.test.tsx]: ../../../../job-tracker-ui/src/daily-control-loop.test.tsx
[B:JobApplicationsEndpointBehaviorTests]: ../../../../JobTrackerApi.Tests/JobApplicationsEndpointBehaviorTests.cs
[F:confirm-flow.test.tsx]: ../../../../job-tracker-ui/src/confirm-flow.test.tsx
[B:JobLifecycleEventTests]: ../../../../JobTrackerApi.Tests/JobLifecycleEventTests.cs
[F:kanban-grouped-board.test.tsx]: ../../../../job-tracker-ui/src/kanban-grouped-board.test.tsx
[F:pipeline.test.ts]: ../../../../job-tracker-ui/src/pipeline.test.ts
[B:JobPipelineTests]: ../../../../JobTrackerApi.Tests/JobPipelineTests.cs
[F:companies-relationship.test.tsx]: ../../../../job-tracker-ui/src/companies-relationship.test.tsx
[F:offer-comparison.test.tsx]: ../../../../job-tracker-ui/src/offer-comparison.test.tsx
[B:AnalyticsSalaryTests]: ../../../../JobTrackerApi.Tests/AnalyticsSalaryTests.cs
[F:csv-export.test.tsx]: ../../../../job-tracker-ui/src/csv-export.test.tsx
[B:CsvExportTests]: ../../../../JobTrackerApi.Tests/CsvExportTests.cs
[F:applicationWorkspace.test.ts]: ../../../../job-tracker-ui/src/applicationWorkspace.test.ts
[F:application-route-contracts.test.ts]: ../../../../job-tracker-ui/src/application-route-contracts.test.ts
[B:ApplicationWorkspaceTests]: ../../../../JobTrackerApi.Tests/ApplicationWorkspaceTests.cs
[F:application-intelligence.test.tsx]: ../../../../job-tracker-ui/src/application-intelligence.test.tsx
[F:workflow-trust-signals.test.tsx]: ../../../../job-tracker-ui/src/workflow-trust-signals.test.tsx
[B:JobApplicationsWorkflowSignalsTests]: ../../../../JobTrackerApi.Tests/JobApplicationsWorkflowSignalsTests.cs
[B:JobApplicationsAppliedDateHistoryTests]: ../../../../JobTrackerApi.Tests/JobApplicationsAppliedDateHistoryTests.cs
[F:application-workflow-assist.test.tsx]: ../../../../job-tracker-ui/src/application-workflow-assist.test.tsx
[B:ApplicationIntelligenceTests]: ../../../../JobTrackerApi.Tests/ApplicationIntelligenceTests.cs
[B:StrategySnapshotOperationTests]: ../../../../JobTrackerApi.Tests/StrategySnapshotOperationTests.cs
[F:application-checklist.test.tsx]: ../../../../job-tracker-ui/src/application-checklist.test.tsx
[B:ApplicationChecklistTests]: ../../../../JobTrackerApi.Tests/ApplicationChecklistTests.cs
[F:application-assets.test.tsx]: ../../../../job-tracker-ui/src/application-assets.test.tsx
[F:cv-builder-deep-link.test.tsx]: ../../../../job-tracker-ui/src/cv-builder-deep-link.test.tsx
[B:ApplicationAssetsTests]: ../../../../JobTrackerApi.Tests/ApplicationAssetsTests.cs
[F:application-drafts.test.ts]: ../../../../job-tracker-ui/src/application-drafts.test.ts
[B:SubmittedApplicationPackageTests]: ../../../../JobTrackerApi.Tests/SubmittedApplicationPackageTests.cs
[B:JobApplicationsApplicationPackageTests]: ../../../../JobTrackerApi.Tests/JobApplicationsApplicationPackageTests.cs
[F:attachments.test.tsx]: ../../../../job-tracker-ui/src/attachments.test.tsx
[B:AttachmentsControllerTests]: ../../../../JobTrackerApi.Tests/AttachmentsControllerTests.cs
[B:AttachmentConsistencyTests]: ../../../../JobTrackerApi.Tests/AttachmentConsistencyTests.cs
[B:AttachmentFlagsRecomputeTests]: ../../../../JobTrackerApi.Tests/AttachmentFlagsRecomputeTests.cs
[F:interview-prep.test.tsx]: ../../../../job-tracker-ui/src/interview-prep.test.tsx
[B:InterviewPrepPersistenceTests]: ../../../../JobTrackerApi.Tests/InterviewPrepPersistenceTests.cs
[B:InterviewAiContextTests]: ../../../../JobTrackerApi.Tests/InterviewAiContextTests.cs
[B:InterviewPrepTests]: ../../../../JobTrackerApi.Tests/InterviewPrepTests.cs
[B:JobApplicationsFollowUpDraftTests]: ../../../../JobTrackerApi.Tests/JobApplicationsFollowUpDraftTests.cs
[F:application-calendar.test.tsx]: ../../../../job-tracker-ui/src/application-calendar.test.tsx
[F:settings-view.test.tsx]: ../../../../job-tracker-ui/src/settings-view.test.tsx
[B:ApplicationCalendarControllerTests]: ../../../../JobTrackerApi.Tests/ApplicationCalendarControllerTests.cs
[B:RulesEngineProspectTests]: ../../../../JobTrackerApi.Tests/RulesEngineProspectTests.cs
[B:NotificationSettingsControllerTests]: ../../../../JobTrackerApi.Tests/NotificationSettingsControllerTests.cs
[F:operations-page.test.tsx]: ../../../../job-tracker-ui/src/operations-page.test.tsx
[B:OperationsControllerTests]: ../../../../JobTrackerApi.Tests/OperationsControllerTests.cs
[B:UserOperationStoreTests]: ../../../../JobTrackerApi.Tests/UserOperationStoreTests.cs
[B:CvProcessingOperationTests]: ../../../../JobTrackerApi.Tests/CvProcessingOperationTests.cs
[B:CareerProfileControllerTests]: ../../../../JobTrackerApi.Tests/CareerProfileControllerTests.cs
[B:CareerProfileServiceTests]: ../../../../JobTrackerApi.Tests/CareerProfileServiceTests.cs
[F:career-workspace-page.test.tsx]: ../../../../job-tracker-ui/src/career-workspace-page.test.tsx
[B:ProfileCvControllerTests]: ../../../../JobTrackerApi.Tests/ProfileCvControllerTests.cs
[B:CvProfileDiffServiceTests]: ../../../../JobTrackerApi.Tests/CvProfileDiffServiceTests.cs
[B:CvExtractionCoverageTests]: ../../../../JobTrackerApi.Tests/CvExtractionCoverageTests.cs
[F:career-evidence.test.tsx]: ../../../../job-tracker-ui/src/career-evidence.test.tsx
[B:CareerEvidenceControllerTests]: ../../../../JobTrackerApi.Tests/CareerEvidenceControllerTests.cs
[F:cv-builder-page.test.tsx]: ../../../../job-tracker-ui/src/cv-builder-page.test.tsx
[F:cv-template-thumbnail.test.tsx]: ../../../../job-tracker-ui/src/cv-template-thumbnail.test.tsx
[B:PublicCvControllerTests]: ../../../../JobTrackerApi.Tests/PublicCvControllerTests.cs
[F:cvBuilder.test.ts]: ../../../../job-tracker-ui/src/cvBuilder.test.ts
[F:ai-section-assistant.test.tsx]: ../../../../job-tracker-ui/src/ai-section-assistant.test.tsx
[B:AiWorkspaceTests]: ../../../../JobTrackerApi.Tests/AiWorkspaceTests.cs
[B:AiPrivacyPolicyTests]: ../../../../JobTrackerApi.Tests/AiPrivacyPolicyTests.cs
[B:ProEntitlementAuthorizationTests]: ../../../../JobTrackerApi.Tests/ProEntitlementAuthorizationTests.cs
[F:public-cv-page.test.tsx]: ../../../../job-tracker-ui/src/public-cv-page.test.tsx
[B:PdfRenderAdmissionTests]: ../../../../JobTrackerApi.Tests/PdfRenderAdmissionTests.cs
[F:end-to-end-trust-loop.test.tsx]: ../../../../job-tracker-ui/src/end-to-end-trust-loop.test.tsx
[F:correspondence-search-context.test.ts]: ../../../../job-tracker-ui/src/correspondence-search-context.test.ts
[B:CorrespondenceControllerTests]: ../../../../JobTrackerApi.Tests/CorrespondenceControllerTests.cs
[F:correspondence-gmail-import.test.tsx]: ../../../../job-tracker-ui/src/correspondence-gmail-import.test.tsx
[B:GmailControllerTests]: ../../../../JobTrackerApi.Tests/GmailControllerTests.cs
[B:EmailOwnershipIntegrationTests]: ../../../../JobTrackerApi.Tests/EmailOwnershipIntegrationTests.cs
[F:correspondence-inbox-page.test.tsx]: ../../../../job-tracker-ui/src/correspondence-inbox-page.test.tsx
[B:EmailControllerTests]: ../../../../JobTrackerApi.Tests/EmailControllerTests.cs
[B:EmailDraftsControllerTests]: ../../../../JobTrackerApi.Tests/EmailDraftsControllerTests.cs
[B:EmailDraftPersistenceTests]: ../../../../JobTrackerApi.Tests/EmailDraftPersistenceTests.cs
[B:EmailSendControllerTests]: ../../../../JobTrackerApi.Tests/EmailSendControllerTests.cs
[B:EmailSendAttemptStoreTests]: ../../../../JobTrackerApi.Tests/EmailSendAttemptStoreTests.cs
[B:EmailProviderDeliveryTests]: ../../../../JobTrackerApi.Tests/EmailProviderDeliveryTests.cs
[F:gmail-review-page.test.tsx]: ../../../../job-tracker-ui/src/gmail-review-page.test.tsx
[F:email-provider-connections.test.tsx]: ../../../../job-tracker-ui/src/email-provider-connections.test.tsx
[B:MicrosoftGraphControllerTests]: ../../../../JobTrackerApi.Tests/MicrosoftGraphControllerTests.cs
[B:ImapControllerTests]: ../../../../JobTrackerApi.Tests/ImapControllerTests.cs
[B:ImapServiceSsrfGuardTests]: ../../../../JobTrackerApi.Tests/ImapServiceSsrfGuardTests.cs
[B:StageAnalyticsTests]: ../../../../JobTrackerApi.Tests/StageAnalyticsTests.cs
[F:onboarding-checklist.test.tsx]: ../../../../job-tracker-ui/src/onboarding-checklist.test.tsx
[F:notifications-popover.test.tsx]: ../../../../job-tracker-ui/src/notifications-popover.test.tsx
[F:ai-usage-card.test.tsx]: ../../../../job-tracker-ui/src/ai-usage-card.test.tsx
[F:pro-feature-notice.test.tsx]: ../../../../job-tracker-ui/src/pro-feature-notice.test.tsx
[B:AiUsageMeterTests]: ../../../../JobTrackerApi.Tests/AiUsageMeterTests.cs
[B:BillingControllerTests]: ../../../../JobTrackerApi.Tests/BillingControllerTests.cs
[F:account-data-export.test.tsx]: ../../../../job-tracker-ui/src/account-data-export.test.tsx
[B:AccountDataExportTests]: ../../../../JobTrackerApi.Tests/AccountDataExportTests.cs
[B:BackupControllerTests]: ../../../../JobTrackerApi.Tests/BackupControllerTests.cs
[B:AccountDeletionTests]: ../../../../JobTrackerApi.Tests/AccountDeletionTests.cs
[B:DatabaseBackupRunnerTests]: ../../../../JobTrackerApi.Tests/DatabaseBackupRunnerTests.cs
[F:admin-users-page.test.tsx]: ../../../../job-tracker-ui/src/admin-users-page.test.tsx
[B:UsersControllerTests]: ../../../../JobTrackerApi.Tests/UsersControllerTests.cs
[B:ApiAuthorizationPostureTests]: ../../../../JobTrackerApi.Tests/ApiAuthorizationPostureTests.cs
[F:admin-audit-page.test.tsx]: ../../../../job-tracker-ui/src/admin-audit-page.test.tsx
[F:admin-system-page.test.tsx]: ../../../../job-tracker-ui/src/admin-system-page.test.tsx
[B:MaintenanceJobDispatcherTests]: ../../../../JobTrackerApi.Tests/MaintenanceJobDispatcherTests.cs
[B:CvCorpusHarnessTests]: ../../../../JobTrackerApi.Tests/CvCorpusHarnessTests.cs
+147
View File
@@ -0,0 +1,147 @@
# P4-06 — Shared validation checkpoint
Application under review: `c99f4fb7ddf522eb75ed7d644b0469fb59124412` on `codex/ui-redesign-phase4`, 2026-09-13. This checkpoint changes acceptance documentation and two browser-test readiness boundaries only. **No application, backend, dependency, CI, deployment, schema or Phase 5 implementation changes. No B07 work. F04 remains open.** The containing commit is discoverable with `git log -- docs/redesign/phase-4/p4-06`.
Sources: [approved plan](../../phase-3/PHASE4_IMPLEMENTATION_PLAN.md), [Phase 3 impact](../../phase-3/PRESERVATION_IMPACT_MATRIX.md), [Phase 2 contracts](../../phase-2/PRESERVATION_MATRIX.md), [traceability](../../phase-2/TRACEABILITY.md), and all five implementation records below. Historical statements such as “next slice not started” describe their individual checkpoints; this report reconciles their current status without rewriting historical evidence.
## Acceptance and Phase 5 readiness
**CONDITIONAL GO for Phase 5 planning, not blanket approval for broad page migration or production release.** The representative Phase 4 primitives compose without replacing MUI or moving state owners. Open named/focus/contrast failures must be resolved within their separately authorized owner before accepting migration of the affected surface. In particular shell/command planning must account for P4-02-D01 and the manually reproduced P4-06-O01/O02 below; tooltip contrast remains a shared-control gate. Package/tailoring and broader CV editor work have independent blocking integrity/rendering prerequisites.
The exact recommended next task is **plan the bounded Phase 5 AppShell/grouped-navigation migration**: reconcile existing destinations/legacy links and the 57 contracts with the approved information architecture; retain the private provider tree, route/query contracts and account-switch boundary; specify desktop collapse versus mobile drawer state, focus entry/return, account/notification/command behavior and compatibility tests. Include the known shell/command/feedback defects as acceptance prerequisites. Identify the first small implementation diff and its EN/NB × light/dark × desktop/320px evidence before editing. Do not include Dashboard, Jobs/Board, job details or CV redesign in that first slice. This is a recommendation only; no Phase 5 ticket/package has been created.
## Combined foundation and reuse boundary
| Slice | Retained result | Combined responsibility / limit |
|---|---|---|
| [P4-01](../p4-01/README.md) | Semantic MUI palette, both themes, 3px focus-visible treatment, loaded fixtures, readable omitted CV sections | Existing provisional hue/font/identity; background/paper/elevated, text, border, focus, action and status roles. Status labels/icons retain meaning. Printed white CV paper/template accents remain document styling, not application theme errors |
| [P4-02](../p4-02/README.md) | Names for existing CV/AI/attachment controls, labelled confirm/prompt/command dialogs, persistent loaded-state live region | Preserve MUI focus trap/return and existing field/save owners. Announce completion only after observed loading; error-only callers do not announce false completion. No general form framework or per-background-refresh announcements |
| [P4-03](../p4-03/README.md) | Named keyboard-scrollable CV preview region, focused edit/preview pane survives width changes | Existing preview HTML/iframe, save queue, pagination and renderer remain. Keyboard access is accepted; margin/template fidelity and stale-revision safety are not thereby certified |
| [P4-04](../p4-04/README.md) | PageHeader/PageSection, opt-in title/section/description typography, width/gutters/rhythm | Settings is the only page consumer. Semantic h1/h2/h3, wrap-safe actions/text; no page-wide Save or new draft owner. Reading 60rem; data 82.5rem and editor 100% are aliases awaiting real consumer acceptance, not pre-certified migrated pages |
| [P4-05](../p4-05/README.md) | Opt-in Comfortable/Compact MUI table/card spacing on existing Jobs/Trash | Default Comfortable; local component state only, no persistence/API/schema. Same columns/actions/sorting/paging/statuses/selection. Existing 768px card adaptation; target sizing independent of density |
Inspected owners: `theme.ts`, `mui-theme.d.ts`, `layout/PageLayout.tsx`, `layout/AppShell.tsx`, `App.tsx`, `ViewStateNotice.tsx`, Settings subcards, `JobTable.tsx`, `CvBuilderEditor.tsx`, and the named-control/dialog callers. Compared Phase 3→P4-05 diffs with the records. `App.tsx` only opts Settings into the reading header/description; its routes/auth/provider owners are unchanged. `AppShell` combines semantic colors/focus with an optional layout prop, retaining the original navigation groups, widths, collapse key and handlers. Several other source-file diffs from the docs restructure are comment/link changes only.
Consumers should use MUI semantic palette/focus, select a reviewed page-width role, compose headings/sections at the real semantic level and opt into density only where it makes sense. These primitives own presentation, not selection/query/draft/persistence. Future screens need their own populated/error/long-content fixtures; they must not invent replacement page wrappers or a competing table/theme system to bypass failed acceptance. Editor breakpoints (900/1024) remain intentionally distinct from the shell/table's 768px boundary.
Whole-container opacity on omitted CV sections/items was removed in P4-01 because it reduced editable-text contrast. Existing inclusion/visibility indicators still communicate omission. Editing, persistence, canonical-versus-variant ownership and generated output semantics are unchanged. Transient drag opacity is a different retained behavior.
## Preservation reconciliation
The [57-row acceptance matrix](PRESERVATION_ACCEPTANCE.md) retains every original group and its underlying sub-capabilities, test references, extra P4 evidence and unresolved gaps. **57/57 are mapped; this is not exhaustive behavioral coverage.** Disposition: 8 scoped acceptances, 34 retained-regression groups and 15 conditional groups with specific migration gates. These are review categories, not a percentage of product readiness.
Representative high-risk protection spans real account isolation/permissions; query/selection/row actions and workspace Back; dirty navigation; CV override/autosave/undo/redo with canonical/sibling readback; named dialogs and focus return; real upload/document ownership; explicit AI accept/reject/edited acceptance in component/service tests; native Settings saves and failure recovery. Real model truthfulness, provider mail/payment/calendar delivery, all historic restore paths and all route/state combinations remain outside the local proof.
P2-D01 remains the one expected browser failure: native SQLite submitted-package capture returns 500 after successful setup. **Later archived-binary assertions are not reached.** Service tests for immutable packages do not close that native gap. Source/history concurrency (F01/audit D01), session identity (B02) and creation-intent idempotency are separate contracts.
## Verification adjustment discovered at this checkpoint
The initial complete run reported **46 actual passes, five unexpected failures, and P2-D01 expected failure** (reporter: 47 passed, five failed). Three P4-01 scans sampled partially transparent dialog/toast content: company buttons 4.37/4.12:1 and a saving toast 4.48:1. Two P4-05 checkbox-wrapper focus samples read 0px while the native input was focused. A focused rerun of the same unmodified 16 cases passed, so the initial result is retained rather than erased or called a clean baseline.
Inspection found normal finite MUI Fade/Grow transitions in P4-01 and `ButtonBase` applying the wrapper focus class through React state. The focused instrumented run observed company-dialog opacity between approximately 0.798 and 0.956 immediately before waiting for finite transitions, and a notification-toast transition at 0.956. All 16 focused cases passed both before and after the readiness adjustment. The bounded test changes are:
- [semantic-foundations.spec.ts](../../../../job-tracker-ui/e2e/semantic-foundations.spec.ts): at loaded-state axe boundaries, allow a paint cycle and await currently running **finite** animations. Record animation type/opacity in result attachments. Keep normal motion enabled, infinite loading animations untouched, all axe rules/thresholds and the original scoped assertion. This tests settled loaded content, not every intermediate animation frame.
- [table-density.spec.ts](../../../../job-tracker-ui/e2e/table-density.spec.ts): use the normal bounded assertion timeout to observe the existing 3px solid wrapper ring after native focus. The ring requirement, focus assertion, keyboard actions, data/paging/actions and test count are unchanged. No eventual failure is converted into a pass or rule exclusion.
No product color or interaction was changed to address these observations. Full rerun and transition evidence are summarized in [RESULTS.json](RESULTS.json). The two readiness changes are the only executable changes in P4-06. No new browser/Jest/backend cases are introduced.
## Visual, accessibility and responsive evidence
V1–V5 refer to fresh execution of the existing five P4 browser files in the final complete run. All use the built static frontend and real disposable local API with synthetic users/data. Browser/provider traffic is blocked by the fixtures. The [visual review](VISUAL_REVIEW.md) records inspected frames, capture limitations and manual observations; all 33 retained fresh images and scan summaries are indexed in [RESULTS.json](RESULTS.json). Original P4 screenshots remain unchanged.
| Evidence | Populated workflow / assertions | Limits |
|---|---|---|
| V1 `semantic-foundations` | Companies loading→error/Retry→empty→real populated; company form keyboard/return; Jobs labelled statuses; command/nav focus; loaded CV and Settings, both themes; company full EN/NB matrix | Gates contrast only, attaches other violations/incompletes. Historical full-scan results must not be described as full axe passes |
| V2 `named-controls-modal-state` | Four theme/locale cases, named CV controls/cover-letter options; actual attachment rename/purpose controls; prompt/confirm focus; company failed-save draft; command dialog | Explicit command-list/mobile-progress baseline findings retained. Provider AI success not called; modal-toast limitation still open |
| V3 `builder-preview-keyboard` | Four theme/locale cases; one/multi-page native preview, keyboard PageDown/Home/End, pane retention at 390/768/899/900/1024/1440, preview 503/Retry, native autosave/undo/redo and source/sibling isolation | Known light Redo-tooltip contrast remains a narrow expected finding. Does not prove margins/templates, whole-editor screen-reader operation or revision safety |
| V4 `settings-page-layout` | Four theme/locale cases; one h1/named sections; 1920/1440/1024/768/767/390/320 reflow; long EN/NB heading, rule draft through resize; awaited native rule/notification saves, 503 retry, ZIP and account-link actions | No concurrent SQLite safety claim. Existing tab-unmount draft behavior retained. No paid deletion/restore/provider operation |
| V5 `table-density` | Four theme/locale cases; both densities, all columns/actions, checked selection, native sort/page/delete/Trash restore/workspace Back, 1440/1024/768 tables and 390/320 cards, scroll focus/keyboard, 32px fine/44px phone targets, error/Retry | Local preference only; no actual coarse-pointer hardware or saved-view CRUD/partial bulk-failure certification. CV document density is separate |
| M1 manual local browser | Running local app in Codex in-app browser; Settings loaded h1/h2/h3 and theme-menu keyboard selection/return; desktop sidebar collapse, reload persistence, 320px drawer Tab/Escape and return; light/Bokmål and dark/English visual inspection | Synthetic seeded admin; no real user/production data. Exposed pre-existing collapsed-drawer and long admin-badge failures below. This is manual UI/AX observation, not NVDA/Narrator certification |
Manual visual review distinguishes readable main-page headings/forms/cards from shell defects; it does not rely solely on a zero-overflow body measurement. The table fixtures check actual descendant bounds and title width, retained horizontal scrolling and stable content. Both densities retain labelled status plus selection checkboxes rather than color-only meaning. The standard drawer returns focus on Escape; the collapsed-mobile first item is a documented counterexample to a universal focus-visibility claim.
The evidence ledger reports **violations and incomplete rules separately**. P4-01's contrast-only gate and the later narrow known-defect assertions are not full accessibility passes. The inherited generic `accessibility.spec.ts` waits for the main landmark, not every populated route's data, and does not attach its incomplete results; its success must not substitute for V1–V5 or be included as a complete scan census. Incomplete color contrast, aria-hidden-focus, table/other checks require human review; reading representative screenshots/names does not resolve every node. Manual checks of static headings, labels, visible focus, wrapping and incomplete contexts supplement the automation, without certifying screen-reader announcements. Reduced-motion media is exercised by V2–V5; V1 keeps normal transitions. Full native screen reader, physical touch/software keyboard, OS forced-colors and 200%/400% browser-zoom testing remain intentional gaps. Every affected migration must add appropriate proof before acceptance.
## Open/deferred issue reconciliation
| Issue | Current status/evidence | Owner / Phase 5 effect |
|---|---|---|
| Original unnamed CV/AI/attachment controls and preview keyboard region | Closed only for the named P4-02/P4-03 targets; current fixtures verify them | No remaining blocker for those bounded fixes; not all controls/render combinations certified |
| Historical standalone TS2571 | Not present in current successful type gate; historical evidence preserved | No current blocker; retain standalone CI gate |
| F04/B06 ingress | **Open**, no deployed peer/listener/firewall/NAT/IPv6/DNS/TLS/restart evidence collected | Production/release gate; not a reason to replace local UI foundations |
| P2-D01 native package/tailoring SQLite ordering | **Open**, unchanged expected failure, archive assertions unreached | Blocks package/tailoring/document-relationship restructuring; separately repair/prove native archive before affected migration |
| P4-02-D01 command List children | **Open**, retained axe `list` result | Shell/command owner must resolve structural semantics before that migration is accepted |
| P4-02-D02 company save feedback outside modal | **Open**, retained draft but transient toast outside accessible modal subtree | Company form owner; require durable accessible in-modal failure, preserve modal background isolation |
| P4-02-D03 mobile progress scrolling | **Open**, retained `scrollable-region-focusable` | Job workspace/mobile owner before restructuring that surface |
| P4-02-D04 literal AI context `{name}` | **Open**, both locales; no context/API change here | Application AI content owner before affected UI migration |
| P4-03-D01 light Redo Tooltip contrast | **Open**, known 3.89:1 context, narrowly recognized by inherited tests | Separately scoped shared-theme repair before accepting affected hovered/focused controls; no global contrast exemption |
| P4-04-O01 toast overlap | **Open**, existing transient feedback can obscure bottom actions | Shell/feedback placement owner; normal dismissal is not a repair |
| P4-04-O02 SQLite notification-save contention | **Open**, earlier 2/10 concurrent attempts failed; current fixtures await PUT before readback | Separate backend reliability owner; no claim that concurrent preferences are safe; does not require page primitive replacement |
| P4-05-O01 raw English statuses/browser-locale dates | **Open**, stable keys/semantics retained, EN/NB density/paging names work | Jobs localization owner; migration must preserve raw custom labels and date meaning |
| P4-06-O01 collapsed desktop state leaks into mobile drawer | **Newly observed baseline defect**, reproduced manually: collapse→reload→320px→open→Tab. Mobile retains icons only; names remain in AX via title. First Dashboard row is y=74–118 under fixed header; center hit-test returns HEADER, not focused button, despite 3px outline. Expanded control is y=130–174 and hit-tests correctly. Escape returns to trigger | Shell/responsive owner; blocks acceptance of the first shell migration until mobile labels and focus visibility are independently protected. Present in pre-Phase-4 `f696f23` AppShell: shared `desktopNavCollapsed` label/padding branches plus app-bar z-index above drawer. No P4 product change introduced it |
| P4-06-O02 long admin version badge at 320px | **Newly observed baseline limitation**, synthetic `e2e-verification` badge overlaps logo/language controls in light/Bokmål and dark/English. Normal non-admin fixtures do not exercise the badge | Shell/admin header owner; long metadata must reflow before shell acceptance. Same pre-P4 badge/layout code; not proof of current production overlap with a shorter version |
| CV margins/templates/preview/pagination fidelity | **Open**, keyboard access does not fix document geometry or theme-specific rendering | Dedicated rendering/PDF acceptance before broad CV migration; preserve template options and preview/PDF relationship |
| F01/audit D01 stale revision; creation idempotency | **Open**, distinct from completed account isolation | Separate integrity owners; serialize CV editor changes with revision work; do not begin B07 here |
| P2-O01 isolated initial rules 500 | **Unconfirmed** historical observation; not closed by passing runs and not equated with reproduced notification contention | Separate reliability triage if it recurs; no silent retry allowance |
| P3-O01/O02 analytics definitions/navigation retention | **Open**, [Phase 3 decisions](../../phase-3/OPEN_DECISIONS.md) retained | Dashboard/route migration owners must define population/period and query/error behavior before changing those surfaces |
| Production runner/browser gate, provider delivery, restore/rollback, billing/deletion configuration; F19/F20/F21 | **Unverified/open**, [known issues](../../../roadmap/known-issues.md) unchanged | Separate release/operational/domain gates. Local tests do not close them or authorize deployment; calendar/timezone/worker/configuration fixes are outside this checkpoint |
No deferred defect was silently fixed. New baseline observations are recorded in the existing TODO ledger, not turned into Phase 5 implementation tickets.
## Final validation
Fresh commands ran on Windows/PowerShell, local .NET SDK and Chromium, with normal single-worker/serialized settings. Synthetic DBs and authenticated traces/logs are ignored artifacts, not committed credentials. The final complete browser run took 7.8 minutes, with one attempt per case and no unexpected failures. Final values and exact outcome distinction are in [RESULTS.json](RESULTS.json).
| Gate | Inherited P4-05 | Final P4-06 |
|---|---:|---|
| Backend Release | 916 | **916 passed**, zero failed/skipped |
| Frontend Jest | 354 / 75 suites | **354 passed / 75 suites**, zero failed/skipped |
| Browser actual success | 51 | **51 passed**; reporter says 52 because it includes the expected failure |
| Browser expected failure | P2-D01 | Retained, not counted as actual success |
| Rate-limit / ingress / PDF | 9 / 6 / 1 | **9 / 6 / 1 passed** |
| Configuration/Compose | 3 | **3 passed** |
| TypeScript / lint / frontend production / API Release | Passing | **All passed**; API zero warnings/errors; separate e2e TypeScript also passed |
| Secret / whitespace / docs/PRES links | Passing | **Passed**; 124 current/root Markdown files, zero missing local targets; all 57 unique contracts and 147 referenced test targets reconciled |
Additional unchanged local checks: supply-chain script tests **3**, model-evaluation harness tests **5**, browser-extension node tests **3**. B01 transport/SSRF, B02 session/ownership, B03 admission/recovery and B05 export regressions remain part of the 916 backend suite; native account-isolation and CSV/public PDF browser cases pass, alongside the separate B04/ingress/PDF burst suites. The PDF burst test uses inert child processes to measure shared capacity; inherited browser smoke also generates real Chromium PDFs. No F04 production topology claim follows from those local tests.
The retained scan census is **118 scans**, with **eight known rule occurrences**: command `list` four, mobile `scrollable-region-focusable` two, light-tooltip `color-contrast` two. V1/V4/V5 have zero violations in their 38/20/24 retained scans. Incomplete-rule occurrences remain separate: color contrast 92, aria-prohibited-attr 34, aria-hidden-focus 24, aria-valid-attr-value 4 and th-has-data-cells 4. These counts are occurrences across scans, not unique defects; none is treated as a pass.
Phase 3 inherited 916 backend / 313 frontend / 23 actual browser successes plus P2-D01. Phase 4 adds **41 Jest tests** (20+12+0+3+6) and **28 browser cases** (12+4+4+4+4), reaching 354 and 51. P4-06 adds zero cases; two existing browser files gain readiness checks only. Backend/security/configuration counts are unchanged. No CI/package/infrastructure adjustment was necessary.
```powershell
$env:DOTNET_ROOT='C:/Users/Connor/.dotnet'
$env:DOTNET_HOST_PATH='C:/Users/Connor/.dotnet/dotnet.exe'
& $env:DOTNET_HOST_PATH test JobTrackerApi.Tests/JobTrackerApi.Tests.csproj --configuration Release --no-restore --logger 'trx;LogFileName=p4-06.trx' --results-directory .artifacts/redesign-p4-06 -- xUnit.parallelizeTestCollections=false xUnit.maxParallelThreads=1
& $env:DOTNET_HOST_PATH build JobTrackerApi/JobTrackerApi.csproj --configuration Release --no-restore -warnaserror
# In job-tracker-ui:
npm test -- --watchAll=false --runInBand --json --outputFile=../.artifacts/p4-06-jest.json
npm run typecheck
npm run lint
$env:NEXT_PUBLIC_API_BASE_URL='http://localhost:5302/api'
$env:NEXT_TELEMETRY_DISABLED='1'
npm run build
$env:PLAYWRIGHT_STATIC_EXPORT='true'
$env:PLAYWRIGHT_PREBUILT_EXPORT='true'
$env:PLAYWRIGHT_JSON_OUTPUT_FILE='../.artifacts/p4-06-browser.json'
node node_modules/@playwright/test/cli.js test --reporter=list,json
# Run these sequentially; each owns its own disposable API on port 5302.
node node_modules/@playwright/test/cli.js test --config=playwright.rate-limits.config.ts --reporter=list,json
node node_modules/@playwright/test/cli.js test --config=playwright.ingress.config.ts --reporter=list,json
node node_modules/@playwright/test/cli.js test --config=playwright.pdf.config.ts --reporter=list,json
# At repository root:
python scripts/test-ingress.py
python scripts/test-supply-chain.py
python scripts/test-ollama-evaluation.py
node --test browser-extension/tests/*.test.mjs
python scripts/supply-chain.py scan-secrets
python .artifacts/p4-04-check-doc-links.py
git diff --check
git diff --cached --check
```
Special browser reports use separate `PLAYWRIGHT_JSON_OUTPUT_FILE` names (`p4-06-rate-limits.json`, `p4-06-ingress.json`, `p4-06-pdf.json`). Historical capture environment flags remain unset so prior PNGs are never overwritten. An additional ignored TypeScript project includes the two edited e2e files plus MUI augmentation; standalone application TypeScript does not include e2e. No test retries are configured locally. No provider/dependency vulnerability network query or production CI verdict is claimed.
Before push: verify all 57 unique IDs match the source ledger, local Markdown/test links resolve, changed files contain no application/CI/package changes, staged secret/whitespace checks pass. Push only the requested Phase 4 branch, verify remote SHA equals HEAD and the working tree is clean. **Stop before Phase 5 and B07.**
Final scope review: 33 synthetic screenshots, the report/matrix/visual review/result ledger, Phase 4 index/Phase 2 trace/TODO updates, and the two test-readiness edits above. No Phase 4 historical evidence was overwritten. The API/application source trees and CI/package files have no diff from `c99f4fb7`. This completes the acceptance checkpoint with the conditional verdict and open gates stated above; it does not approve deployment or begin the next phase.
File diff suppressed because one or more lines are too long
@@ -0,0 +1,21 @@
# P4-06 visual review
2026-09-13, real static frontend/API fixtures at the final candidate. [RESULTS.json](RESULTS.json) records all 33 retained PNGs with case/state and hashes. These are representative frames, not pixel-diff golden baselines or exhaustive visual approval. The following images were opened and inspected at this checkpoint; no application content/CSS was hidden or changed for this review.
| Surface | Inspected evidence | Result / limit |
|---|---|---|
| Settings, four theme/locale combinations | [Light EN](visual/settings-page-layout-general-1440-light-en.png), [light NB](visual/settings-page-layout-general-1440-light-nb.png), [dark EN](visual/settings-page-layout-general-1440-dark-en.png), [dark NB](visual/settings-page-layout-general-1440-dark-nb.png) | Main headings/sections align; title/description remain compact and readable; longer NB description wraps without losing controls. Selected tabs and form boundaries remain distinguishable. Existing section cards are retained, not a new dashboard composition |
| Settings at 320px, error state | [General dark NB](visual/settings-page-layout-general-320-dark-nb.png), [notification failure dark NB](visual/settings-page-layout-notifications-error-dark-nb.png) | Header/body/section labels wrap; error retains an unchecked draft and reachable save/next action. The English error message is an intentionally injected fixture response. Manual light/NB 320px review also confirmed the main reflow, while exposing the separate admin badge issue |
| Jobs status and navigation focus | [Light](visual/semantic-foundations-jobs-nav-light.png), [dark](visual/semantic-foundations-jobs-nav-dark.png) | Distinct text-labelled statuses, row action icons and visible inverse sidebar focus. Existing compact page heading and full flat menu are unchanged; this is not the Phase 5 shell or Jobs redesign |
| Desktop density | [Comfortable light EN](visual/table-density-desktop-comfortable-light-en.png), [Compact light EN](visual/table-density-desktop-compact-light-en.png), [Compact dark NB](visual/table-density-desktop-compact-dark-nb.png) | Same data, custom status, selection and actions; 59/51px ordinary-row measurements retained in all four theme/locale cases. Long rows may grow. Text remains readable in both modes; raw English bulk statuses/browser-locale dates remain P4-05-O01. These frames follow keyboard horizontal scrolling; some edge columns are clipped at the current scroll position. They do not establish start-of-scroll alignment. Native scrolling, selection and action reachability are covered separately by the behavior fixture |
| Phone density, all theme/locale combinations | [320 Comfortable light EN](visual/table-density-phone-320-comfortable-light-en.png), [320 Compact dark NB](visual/table-density-phone-320-compact-dark-nb.png), [390 Compact light NB](visual/table-density-phone-390-compact-light-nb.png), [390 Comfortable dark EN](visual/table-density-phone-390-comfortable-dark-en.png) | Existing cards retain long role/company/status, data, listing and edit/status/delete actions. Buttons wrap rather than disappearing; checked selection and status labels supplement color. Dense still permits long text to grow. Existing rounded cards, bold role typography and tall narrow-screen content remain later Jobs design work; they are not newly approved brand styling |
| CV editor / preview | [One-page light EN](visual/builder-preview-keyboard-one-page-light-en.png), [phone preview dark NB](visual/builder-preview-keyboard-preview-390-dark-nb.png), [failed-preview dark NB](visual/builder-preview-keyboard-error-dark-nb.png) | Preview-region outline is visible, white document paper remains distinct from dark app UI; unavailable preview retains old content and retry action. Omitted editable section labels remain legible with visibility icons. Existing horizontal-overflow warning, margins, small phone print text, large document whitespace and fixed-header/scroll composition are visible limitations; no template/pagination fidelity approval |
| Shared dialogs | [Command light EN](visual/named-controls-modal-state-command-light-en-1440.png), [rename dark NB](visual/named-controls-modal-state-prompt-dark-nb-1440.png) | Focus has a distinct shape, text/description/input/count/actions are readable, background remains isolated/dimmed. Command List semantics and company-error feedback are separate open defects despite readable pictures |
## Capture and manual-review limitations
Some post-axe NB desktop captures omit sidebar glyphs or parts of labels, a capture limitation already investigated/documented in [P4-01](../p4-01/README.md). It is still visible in the current Settings/density images. Those frames support main-content review, **not complete NB desktop-navigation visual certification**. The dedicated EN navigation images and the manual expanded NB mobile drawer show the controls/names. Do not treat this as a reason to hide icons, normalize screenshots or assert a universal repaint fix; obtain stable navigation evidence for the actual shell migration.
Manual interaction used the current running localhost app in the in-app browser: sign in to its synthetic seeded admin, Settings, collapse sidebar, keyboard focus, reload, resize to 320px, open drawer, Tab and Escape. The collapse persisted and Escape returned focus, but collapsed mobile labels disappeared and the first focused row was physically occluded by the app bar. At 1440px expand again; keyboard-select Light in the real theme menu (focus returns), select Norsk, resize to 320px and inspect main headings/forms. Expanded mobile first-row focus was visible. The long `e2e-verification` admin badge overlapped header content in both inspected themes. Findings and pre-P4 source comparison are [P4-06-O01/O02](README.md#opendeferred-issue-reconciliation). The temporary viewport was reset and the tab closed.
This combines screenshot inspection, actual keyboard interaction and AX/DOM observations. It is **not** an NVDA/Narrator or physical-device test. No claim of 200%/400% browser zoom, forced colors, real touch/software keyboards, every tooltip/disabled state or every incomplete axe node. No production, personal career data or real provider account was used.
Binary file not shown.

After

Width:  |  Height:  |  Size: 113 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 108 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 196 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 193 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 111 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 115 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 24 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 22 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 75 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 74 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 107 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 102 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 21 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 58 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 111 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 112 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 111 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 92 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 96 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 93 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 96 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 34 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 38 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 30 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 129 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 127 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 136 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 134 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 45 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 48 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 49 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 50 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 138 KiB