docs(redesign): define Phase 3 UX architecture
This commit is contained in:
@@ -37,6 +37,8 @@ AI should support this flow naturally and contextually. It must never invent fac
|
||||
|
||||
## Status
|
||||
|
||||
2026-09-10: [Phase 3 UX architecture checkpoint](phase-3/README.md), based on Phase 2 `d6d3dd9`, defines grouped navigation, all 31 route destinations, 57 PRES impacts, workflow/data boundaries and the bounded Phase 4 foundation plan. Documentation only; no visual implementation or B07. F04 remains open. [Phase 2](phase-2/README.md) retains the executed 916 backend / 313 frontend baseline and explicit browser/provider/production gaps. Earlier status entries below are historical.
|
||||
|
||||
These documents define the intended target state. They should be updated as the remaining functional work is completed. The full redesign implementation should begin only after a stable pre-redesign baseline has been created and protected by tests.
|
||||
|
||||
2026-09-09: [Phase 1 source audit](audit/README.md) completed on `codex/ui-redesign-audit`: current routes, protected functionality, component/test/API inventories, identity/storage boundaries and proposed migration gates. No redesign implementation or B07 started. Required release checks and F04 production verification remain separate from this audit's completion.
|
||||
|
||||
@@ -1,5 +1,7 @@
|
||||
# Redesign traceability
|
||||
|
||||
Successor planning checkpoint: [Phase 3 impact matrix and architecture](../phase-3/PRESERVATION_IMPACT_MATRIX.md). It maps all 57 contracts to proposed destinations/validation, without changing their requirements or claiming implemented/visual parity. Phase 4 has not started.
|
||||
|
||||
Phase 2 starts at `2d0f131`. The [preservation matrix](PRESERVATION_MATRIX.md) is the stable baseline: **PRES-E01…PRES-A03**, in the original ledger's groups (not one contiguous numeric range). Old references such as C07 remain valid aliases. Subdivide a later workflow with a suffix, for example `PRES-C07.override-reset`; do not reuse an ID or silently change its meaning.
|
||||
|
||||
## Required chain for each later change
|
||||
|
||||
@@ -0,0 +1,54 @@
|
||||
# Accessibility plan
|
||||
|
||||
ARC-16; all PRES groups, with structural priorities E07/E08, J05/J07, W01/W06, C03/C06–C11 and M04. Accessibility is a release criterion per migrated capability, not a final theme polish pass.
|
||||
|
||||
## Existing evidence and first priorities
|
||||
|
||||
Phase 1 carries F14 shared contrast failures and builder preview keyboard-scroll failure after viewport transition. Phase 2 adds behavioral viewport tests, but does not close F14. The original axe suite samples eight routes and can finish before full data/controls load. A green shell scan is not proof of loaded builder/import/send/admin accessibility.
|
||||
|
||||
Priority order: (1) semantic foreground/background/focus pairs; (2) named fields/landmarks and modal focus; (3) loaded preview keyboard access and reorder alternatives; (4) complete responsive task traversal and chart alternatives. Fix each at the responsible shared component before multiplying it across screens.
|
||||
|
||||
## Contracts by interaction
|
||||
|
||||
| Area | Required behavior | Evidence required |
|
||||
|---|---|---|
|
||||
| Landmarks and headings | Skip link, labelled primary/secondary nav, one main, one h1; sensible heading hierarchy | Real App route transitions, keyboard and accessibility tree |
|
||||
| Navigation | Active current page, collapsed link names, menu grouping, route-heading focus | Expanded/rail/mobile; close vs navigate focus behavior |
|
||||
| Fields/errors | Persistent label, help/error association, required status; summary focuses first invalid field; draft retained | RichTextField/Customize selects, date/autocomplete, server validation failure |
|
||||
| Tables | Table headers/sort state, named row selection/actions, noninteractive text plus explicit links | Keyboard sort/select/bulk; no whole-row click hijacking controls |
|
||||
| Mobile cards | Same information/actions with translated role/company accessible names | Bokmål long titles, touch/keyboard, no English-only label inheritance |
|
||||
| Drag/reorder | Move earlier/later or exact status menu for every drag action; pickup/move/drop/cancel announced | CV, checklist, Kanban; focus stays on moved item |
|
||||
| Dialog/drawer | Labelled purpose, initial focus, trap only when modal, Escape policy, trigger return, dirty confirm | Nested confirmation and mobile software keyboard; no stacked invisible traps |
|
||||
| Preview | Named scroll region/iframe, meaningful title, keyboard entry/scroll/exit, actual document pagination | Loaded multipage CV, switch desktop→mobile→desktop and zoom |
|
||||
| AI review | Current/proposed/source names, insert/delete semantics not color alone, deliberate Accept/Reject | Keyboard edited proposal and no-write Reject; long diff/mobile |
|
||||
| Async states | Busy/loading status, polite completion, actionable error; no repeated announcement per keystroke | Operations, render, import, failed save, delayed read after account switch |
|
||||
| Charts | Text summary, exact data values table/list, period/denominator/sample, non-color legend | Keyboard access without pointer tooltip; no unreadable SVG-only values |
|
||||
| Notifications | Accessible unread count, names/timestamps and action names; read ≠ task complete | Popover/full centre, update announcements without focus theft |
|
||||
| Menus/commands | Search name, result groups/count, selected result, arrow/Enter/Escape behavior | IME, focus return, denied/unavailable commands and no private results after logout |
|
||||
| Motion | Honor reduced motion; no information relies on animation | Reorder/view/dialog completion under reduced motion |
|
||||
| Contrast/focus | Internal target: ordinary text ≥4.5:1, large text ≥3:1, essential controls/focus ≥3:1 against adjacent surface | Both modes and states; computed rendered pairs, not swatch-only test |
|
||||
| Touch/reflow | Aim 44 px touch hit area, visible focus, ordinary content usable at 320 CSS px | 200%/400% zoom, text spacing, forced colors, touch/virtual keyboard |
|
||||
|
||||
The numeric thresholds above are project validation targets, not a compliance certification. Disabled controls also need readable adjacent explanations; active important labels cannot use low contrast merely because the design looks quiet.
|
||||
|
||||
## Loaded-state automated matrix
|
||||
|
||||
Use seeded synthetic owner data. Wait for a meaningful named loaded field/row/action, **not just body/main**. Scan and interact after expanding:
|
||||
- Career sections, extraction review including low-confidence choices and history.
|
||||
- CV Content, Customize, AI review, History and long loaded preview.
|
||||
- Job application drafts, documents, checklist, correspondence, interview and dirty confirmation.
|
||||
- Inbox draft/send review/uncertain result; Settings security/provider/deletion controls.
|
||||
- Populated Jobs table/board/cards, saved filters, bulk/trash results.
|
||||
- Admin data/denial/confirmation and aggregate charts when implemented.
|
||||
|
||||
For each migrated shared primitive: EN/NB × light/dark × desktop/phone plus relevant loading/error/locked states. Existing representative browser coverage is a floor, not an instruction to assert only initial pages. Retain all Phase 2 behavior tests and add focused user outcomes rather than CSS snapshots.
|
||||
|
||||
## Manual validation still required
|
||||
|
||||
Use NVDA or Narrator on Windows for primary tasks; record tool/browser, exact route/state, actions and outcome. Verify complete keyboard flow, focus restoration, reading order, data-table alternatives, live-region repetition and escape from iframe/scroll regions. Real touch/virtual keyboard and at least one mobile screen reader require separate access if unavailable locally.
|
||||
|
||||
Test a long Norwegian form, many custom statuses, extreme company/title strings, multipage CV, reduced motion, forced colors, browser zoom and increased text spacing. An emulator screenshot does not prove these interactions. Any unavailable manual evidence stays an explicit gap on its PRES trace row.
|
||||
|
||||
## Stop conditions
|
||||
|
||||
No broad component/page propagation while shared naming/focus/contrast regression remains. Do not disable axe rules or hide failed controls to get a green test. P2-D01 must not be disguised by an “empty” loaded-state fixture; its package workflow remains blocked. No public accessibility claim until manual primary-flow evidence exists. F04 production ingress and CI runner gates remain separate.
|
||||
@@ -0,0 +1,57 @@
|
||||
# AI interaction model
|
||||
|
||||
ARC-11; PRES-W03, PRES-W05, PRES-W06, PRES-W09, PRES-W10, PRES-C03, PRES-C04, PRES-C11, PRES-S04, PRES-E09. NEW-07 is shared contextual access, not a new autonomous agent platform.
|
||||
|
||||
## Grounding contract
|
||||
|
||||
AI must never invent experience, skills, qualifications, education, employment, achievements/metrics, certifications, languages, dates or personal facts. Job requirements describe the employer's needs, not the user's abilities. Unknown is distinct from absent.
|
||||
|
||||
Source context is explicit: current canonical items, selected CV overrides, known job text, user-supplied notes or specifically included attachments. Show source identity/last-known revision where available. Existing models do not supply universal claim-level provenance; a source attachment chip is not proof that every generated sentence is grounded. New structured claim references/unsupported-claim validation need a separately scoped API/evaluation contract.
|
||||
|
||||
When source support is missing: omit the claim, mark it unverified for review or ask the user to add truthful information. Never invent numeric achievements or add a job keyword as an asserted skill. Treat imported job/document content as data, not instructions to change permissions, transmit private files or bypass review. Keep existing server AI privacy/entitlement and source ownership controls.
|
||||
|
||||
## Three entry surfaces, one domain action
|
||||
|
||||
1. Inline action beside a summary, letter, answer or section.
|
||||
2. Contextual panel listing the small set of actions valid for the current job/CV/profile.
|
||||
3. Command entry routing to that same action/review surface.
|
||||
|
||||
The panel uses explicit context and selected source; it does not scrape unrelated routes or retain A's context after switching accounts. No hidden conversation memory, automatic generation on navigation, broad tools or background writes. Commands can open review but cannot silently apply changes.
|
||||
|
||||
## Suggestion states
|
||||
|
||||
| State | Presentation / available actions | Mutation boundary |
|
||||
|---|---|---|
|
||||
| Ready | Target scope and selected sources, action controls | No change |
|
||||
| Generating | Cancel when supported, bounded progress, request identity | No accepted content written |
|
||||
| Review | Current / Proposed / Sources; readable diff and edit proposal | Original retained |
|
||||
| Accepted into draft | “Applied to this draft/CV” with resulting save state | Existing domain action only; distinguish explicit Save vs builder autosave |
|
||||
| Rejected / closed | Proposal cleared; original editor restored | No PUT/save implied |
|
||||
| Regenerating | Keep original and prior proposal until replacement succeeds; clear prior acceptance | No automatic acceptance of replacement |
|
||||
| Invalid/unsupported | Explain structure/source validation error; retry or edit manually | Cannot Apply malformed/missing/duplicate block IDs |
|
||||
| Failed/timeout/busy | Safe message, retry when allowed, retain original | No stale/partial silent apply |
|
||||
| Provider unavailable / privacy disabled / Free locked | Explain supported reason; manual workflow and settings/plan link as applicable | No new request/charge, no fake output |
|
||||
| Context changed / account expired | Discard or require a fresh review against current content | Cannot apply response to different owner/resource |
|
||||
|
||||
An accepted suggestion is not proof of factual accuracy; meaningful support/review checks remain mandatory. Generation failure and legitimate “no supported improvement” are different states.
|
||||
|
||||
## Review interaction
|
||||
|
||||
Use the existing current-versus-suggested UI first. Text diff has insert/delete labels and screen-readable order, not color alone. Never force acceptance of all changes when only part is supported; per-change acceptance is a future extension where the existing action supports whole output only. Manual edit before Accept remains.
|
||||
|
||||
Target label is beside Apply: “Apply to this CV,” “Use in this letter draft,” or “Review changes to Career Profile.” No ambiguous universal “Save everything.” Translate changes language without changing facts; show target document language separately from UI language.
|
||||
|
||||
If source/editor changes during generation, require refreshed review against the current value. Do not rebase proposals silently or imply this solves server optimistic concurrency. API payload IDs/source selection must remain owner-scoped; stale-response rejection follows B02. Regenerate/Retry is user-initiated and respects limits; no retry loop on every render.
|
||||
|
||||
## Domain specifics
|
||||
|
||||
- Match: distinguish deterministic requirement comparison from optional AI explanation. Show scoring method/sample/freshness limits, not a promise of hiring probability.
|
||||
- CV: preserve per-section and whole-document flows and strict original block matching; accepted edits update only variant settings.
|
||||
- Profile extraction: explicit low-confidence selection and discard; don't convert extracted guesses into canonical facts.
|
||||
- Letter/answers: retain original until accepted into job draft; no auto-send.
|
||||
- Interview: generated questions/prep are proposals; Add to prep is deliberate. Suggested answers cannot invent personal examples.
|
||||
- Correspondence: AI draft preparation is distinct from provider send confirmation/attempt identity. Never auto-resend uncertain delivery.
|
||||
|
||||
## Evidence before consolidation
|
||||
|
||||
Phase 2 AI tests cover reject/close/no-write, edit then accept, invalid/missing/duplicate block IDs and CV-only mutation. Preserve those oracles when extracting presentation. Add delayed-response/context-change, cancelled generation, unavailable provider, keyboard diff and two-account scenarios. Model factuality needs controlled known-source evaluations; mocked suggestions prove UI boundaries only. No “hallucination-proof” certification is claimed.
|
||||
@@ -0,0 +1,51 @@
|
||||
# Application shell
|
||||
|
||||
ARC-03; PRES-E01–PRES-E09, PRES-S02–PRES-S04, PRES-A01–PRES-A03. Reuse [AppShell](../../../job-tracker-ui/src/layout/AppShell.tsx) and [App](../../../job-tracker-ui/src/App.tsx). They already support grouped items, longest-path active matching, collapse persistence, mobile drawer, breadcrumbs, account actions and notification access.
|
||||
|
||||
## Structure
|
||||
|
||||
```text
|
||||
Desktop
|
||||
┌ Sidebar (expanded / rail) ┬ Search/commands Notifications Account ┐
|
||||
│ Dashboard │ Breadcrumb if useful │
|
||||
│ JOB SEARCH │ Page title / context Primary action │
|
||||
│ CAREER │ Secondary workspace navigation │
|
||||
│ INSIGHTS │ Main content [AI panel] │
|
||||
│ ACCOUNT / ADMIN │ │
|
||||
└──────────────────────────┴────────────────────────────────────────────┘
|
||||
Mobile: compact top bar → contextual title/actions → content
|
||||
Menu opens a modal navigation drawer; search, bell and account stay reachable.
|
||||
```
|
||||
|
||||
Global bar owns navigation utilities, not a repeated second job/CV header. Contextual page header owns title, description, scope and one primary action plus explicit secondary/overflow actions. Detail WorkspaceHeader owns role/company/status/deadline or CV name/save/publication state.
|
||||
|
||||
## Reuse and responsibility
|
||||
|
||||
Retain the current collapse preference (device-local, non-private), 254/84 px starting widths and <768 px drawer breakpoint until content testing demonstrates a change. Do not reset collapse just because group labels change. Collapsed links have persistent accessible names and tooltips; the active child determines one primary owner through explicit metadata for /discover, /companies and other non-nested paths.
|
||||
|
||||
Keep navigation metadata near existing App route/title ownership; extend it with logical parent/title information only as needed. Do not create a router framework, move to Next routing or recreate the router on theme/density changes. Route identity churn is a source-backed risk requiring a regression test before touching that owner.
|
||||
|
||||
## Global controls
|
||||
|
||||
- Search opens the existing command dialog. Keyboard and visible button share one action.
|
||||
- Notification bell has count and accessible unread summary; no CV/mail body in its collapsed label.
|
||||
- Account menu: Account & security, Settings, Connections, theme, language, sign out. Existing provider-link/security controls remain on their pages; appearance actions do not create another settings store.
|
||||
- A contextual “AI help” entry appears only where supported actions/context exist. It opens a narrow action panel, not automatic chat or generation. Without an eligible context, omit this entry rather than showing a global disabled assistant.
|
||||
- Build metadata remains admin-only. No operational configuration in a personal header.
|
||||
- Keep current light/dark/system and EN/Bokmål hydration; UI language and document language remain distinct.
|
||||
|
||||
## Identity and navigation lifetimes
|
||||
|
||||
Preserve the B02 authenticated-tree unmount, pending-request abort and stale response/mutation rejection on identity/session transition. A new panel, command result, notification list or preview may not outlive that tree. No second Axios client, persisted private command history or unscoped draft store.
|
||||
|
||||
Navigation goes through existing dirty protection. Cancel keeps the document and focus; Discard is deliberate. An account boundary clears private content even if unsaved: do not ask B to retain A's draft. Logout retains existing server invalidation/local cleanup. Role-hidden navigation supplements, never replaces, server authorization. Denied admin/API pages show safe unavailable/permission states without fetching hidden individual data.
|
||||
|
||||
## Interaction requirements
|
||||
|
||||
Skip-to-main link, labelled navigation landmark, one main region, logical h1 and route-change focus on the new page title. Closing mobile drawer/command/bell returns focus to its trigger; selecting a route closes the surface and focuses the new heading. Avoid multiple active modal focus traps. A persistent desktop sidebar is not a modal dialog.
|
||||
|
||||
Sticky headers must not obscure focused controls at zoom or with wrapped Bokmål text. Reserve no permanent AI column when it is closed. On phone use full-height dialogs for long tasks and preserve scroll/draft state through viewport changes.
|
||||
|
||||
## Gate before shell migration
|
||||
|
||||
Extend existing sidebar-active-nav, app-shell-notifications, quick-command-preservation, account-isolation and redesign-preservation tests with collapse persistence, mobile focus return, all logical parent routes, theme/language changes during dirty editing and two-account command/notification disposal. Loaded EN/NB × light/dark × phone/desktop evidence is required. Implement this only after Phase 4 foundations; no shell rewrite is part of Phase 3.
|
||||
@@ -0,0 +1,44 @@
|
||||
# Career Profile UX
|
||||
|
||||
ARC-08; PRES-C01–PRES-C04, PRES-C07, PRES-C10, PRES-C11, PRES-E06, PRES-E09. Sources: [CareerProfilePage](../../../job-tracker-ui/src/views/CareerProfilePage.tsx), [career sections](../../../job-tracker-ui/src/views/career/CareerProfileSections.tsx), [CvVariant](../../../JobTrackerApi/Models/CvVariant.cs), Phase 2 canonical/sibling isolation regression.
|
||||
|
||||
## One canonical source
|
||||
|
||||
Career Profile is the account-owned structured career singleton. Account /profile owns login identity/email/security; CVs own identified settings and item overrides. Label every edit destination before editing, including AI review:
|
||||
|
||||
| Scope label | What changes | What must not change |
|
||||
|---|---|---|
|
||||
| Career Profile — shared source | Canonical selected profile fields after explicit profile save/import acceptance | Account login/email/security; existing CV overrides; frozen submitted packages |
|
||||
| This CV only — [name] | Selected variant settings/item override | Canonical profile, sibling CVs, other owners |
|
||||
| This application — [role/company] | Job draft, letter, answers or existing job-specific artifact | Canonical data; unrelated application drafts |
|
||||
| Suggestion — not saved | Review proposal only | Any stored user-owned content until deliberate acceptance/save |
|
||||
|
||||
Live CVs can reflect later canonical edits where they inherit the source. Never promise that editing Career Profile leaves all rendered live CVs unchanged. Existing overridden fields remain overridden; frozen submissions remain historical. Show this consequence near profile Save and the variant's source label. An existing published live CV also needs clear explanation; it is not an immutable submitted snapshot.
|
||||
|
||||
## Page organization
|
||||
|
||||
Overview gives completeness and actionable missing information, recent import/history and CV links. Edit offers personal information, summary, work, education, skills, languages, interests and **all existing long-tail/custom sections**. Evidence has its existing sourced statement/title/category/tags list/add/delete. Import review/history stays a distinct activity with operation status.
|
||||
|
||||
Do not force onboarding before access. Profile completeness is guidance, not a public employability score or requirement to invent content. No “missing skill” autofill from job requirements. Desired role/location/remote/salary preferences are NEW-13 only where not currently represented; current job fields do not satisfy career intent preferences.
|
||||
|
||||
Preserve avatar editing, raw CV text copy, manual edit, history restore, extraction rebuild/improve/reprocess, retry/cancel and low-confidence selections. Do not reduce the canonical schema to the shorter illustrative section list.
|
||||
|
||||
## Import and AI review
|
||||
|
||||
Choose/upload source → processing with operation ID → compare extracted proposal with current profile → select supported changes (including low-confidence controls) → accept or discard. Display source document/field/confidence evidence when returned. Confidence alone does not verify truth.
|
||||
|
||||
Discard leaves canonical data intact. Failed extraction retains original and recovery actions; cancellation is not success. Low-confidence or conflicting personal claims require explicit user verification. User edits the proposal before acceptance where supported. No silent replacing of profile or automatic propagation from an AI assistant.
|
||||
|
||||
Privacy/entitlement/provider availability explains disabled actions and offers manual editing. Never send unselected attachment content or retain private extracted text in global shell state.
|
||||
|
||||
## Source and override interaction
|
||||
|
||||
Variant item references retain stable source keys. “Edit Career Profile” navigates to source; “Customize in this CV” creates/edits the existing override. “Use profile value” resets only that override, showing current source value first. Profile item removal can leave stale selections/overrides: surface an unresolved source link with repair choices, not silent reassignment to a similarly named item. Exact missing-source behavior needs a focused fixture before changing it.
|
||||
|
||||
Do not add one-click “promote all CV changes to profile.” If later requested, it needs an explicit field-level review and same-account server contract. No generic synchronization framework or schema move.
|
||||
|
||||
## Preservation and migration gate
|
||||
|
||||
Current save/history/projection behavior remains, but F01 record concurrency is unresolved. Plan source/override wording independently; coordinate any save/history/conflict owner edits with D01–D03 and recovery gates. B02 alone is not optimistic concurrency.
|
||||
|
||||
Before restructuring: native A→B stale-state denial; canonical/sibling unchanged after variant override; profile inherited-field propagation and override reset; extraction accept/discard/low-confidence/no-provider states; history restore; long sections and loaded keyboard names. Phase 2 already proves a headline override path, not every item/restore/import combination.
|
||||
@@ -0,0 +1,59 @@
|
||||
# Commands, notifications and tasks
|
||||
|
||||
ARC-12; PRES-E07–PRES-E09, PRES-J01–PRES-J04, PRES-J08, PRES-W04, PRES-W11, PRES-W12, PRES-M01–PRES-M06, PRES-S02–PRES-S04.
|
||||
|
||||
## Command palette
|
||||
|
||||
Extend [QuickCommandDialog](../../../job-tracker-ui/src/components/QuickCommandDialog.tsx), which already has six static commands and job/company search. NEW-02 expands it; no competing command platform.
|
||||
|
||||
| Group | Results / actions | Scope and implementation limit |
|
||||
|---|---|---|
|
||||
| Context | Open Match, tailor current CV, review current letter, interview prep | Only supported actions for current resource; opens existing review/action, never auto-applies |
|
||||
| Navigate | Dashboard, Jobs, Discover, Follow-ups, Companies, Offers, Career Profile, CVs, Documents, Analytics, Correspondence, Settings | Existing pages first; new routes only after they have meaningful content |
|
||||
| Find | Jobs, companies, CV names, supported document metadata | Owner-scoped reads, labelled entity kind; CV/library read reuse, document search awaits bounded projection |
|
||||
| Create | Add/import job; create CV | Opens review/template/name flow; not a background POST or auto-generated content |
|
||||
| Preferences | Light/dark/system, EN/Bokmål, density when implemented | Existing preference handlers and clear current selection; no new account identity |
|
||||
| Administrative | Authorized page navigation | Server still gates every action; no reset/delete/run-maintenance shortcut |
|
||||
|
||||
Blank query shows a short useful command list, not every button in the product. Preserve current job/company result destinations and Add's no-write behavior. Context actions may rank ahead of generic navigation; don't hide ordinary manual commands when AI is unavailable.
|
||||
|
||||
Ctrl+K / Cmd+K and visible search button open the same modal. Focus goes to a **labelled** search input (placeholder alone insufficient). Arrow keys move among results, Enter activates, Home/End reach boundaries, Escape clears a nested scope or closes, Tab remains inside the modal. Do not intercept these keys while IME composition is active; don't steal unrelated editor shortcuts. When closing without navigation restore the trigger; after navigation focus destination heading.
|
||||
|
||||
Group headings/result count and loading/error/no-match states are announced. Existing search catches map errors to empty arrays; improve that deliberately during command migration, not with an assertion that current search distinguishes outage. Debounce, cancel stale results, cap result sets and never generate PDFs/AI during search. No private recent searches in localStorage. Clear query/results on close and identity change.
|
||||
|
||||
## Notification centre
|
||||
|
||||
Reuse NotificationsPopover, UserNotification read/unread/dismiss and operation links. Bell opens a recent list; optional /notifications is an expanded view of the same store. Show unread/all, clear timestamps, safe summaries, mark read and dismiss. Opening a link marks/read behavior must be explicit and must not execute the underlying job action.
|
||||
|
||||
| Event | Current source / availability | Planned behavior |
|
||||
|---|---|---|
|
||||
| Background work progress/success/failure | UserOperation + notifications exist | Link /operations or actual result; preserve retry/cancel identity and failure |
|
||||
| Saved NAV search changes | Saved-search alert results exist | Retain existing alert/dismiss flow; unified centre producer only after end-to-end evidence |
|
||||
| Job follow-up/deadline | Rules/reminders feed and email preference exist | Centre event producer/dedup needs verification/addition; don't equate reminder rows with stored notifications |
|
||||
| Upcoming interview | No general scheduled interview resource | NEW-06 event data first; no inference from stage |
|
||||
| Task due | Checklist has no due date | NEW-04 scheduling contract first |
|
||||
| Document/application state | Existing workspace/artifact events | Link only persisted event/result; avoid one notification per keystroke/preview |
|
||||
| System message | Existing operation/config failures where relevant | Actionable owner-safe messages, no infrastructure secrets |
|
||||
|
||||
Future producers need event identity/dedup, ownership, expiry/read behavior and navigation tests. Do not introduce a general event bus as a presentation task. Muting/hiding a notification is not completing a checklist item or deleting a job.
|
||||
|
||||
## Distinct lifecycles
|
||||
|
||||
- **Task:** actionable job checklist item; pending/done/dismissed, manual or system/auto-signal, persistent ID/order. Completing it changes task state. Due date/time/reminder and cross-job tasks view are new contracts, not already implemented.
|
||||
- **Notification:** notice about a recorded event or work needing attention. Read/dismiss affects the notice only.
|
||||
- **Calendar event:** scheduled time/date, provider identity and timezone; current job deadline/follow-up creation and ICS are existing features. It is not a generic task completion store.
|
||||
- **Email:** external message with actual delivery, provider and consent constraints. Draft/edit/review/send/uncertain attempt remain distinct from notifications and manual correspondence logs.
|
||||
|
||||
Retain Google/Outlook writable-permission/status actions and ICS fallback from [ApplicationCalendarActions](../../../job-tracker-ui/src/components/ApplicationCalendarActions.tsx). Current kinds are follow-up and deadline; no general scheduled interview/calendar sync is proven. A future interview event needs date/time/timezone, explicit calendar link and duplicate-creation semantics. Calendar/timezone baseline defects keep their original owner; no event schema work here.
|
||||
|
||||
## Mail architecture and integrations
|
||||
|
||||
Transactional account/reminder email already has server SMTP configuration and admin test/settings. Gmail, Microsoft Graph and IMAP connection capabilities also exist, with differing read/send capabilities. Preserve those; the original brief's “choose an email provider” is a future deployment/product decision, not evidence that no email architecture exists.
|
||||
|
||||
Correspondence primary entry keeps inbox filters, read details/attachment metadata, provider compose/reply, persisted draft versions, explicit review/send, uncertain-delivery handling, thread import/link/unlink/move and review candidates. A note/pasted message does not send an email. Retry after unknown delivery must use the existing explicit attempt controls.
|
||||
|
||||
LinkedIn recruiter links or imported listing URLs are **not** a LinkedIn integration. No unsupported scraping, auto-apply or synchronization is planned. NAV remains the supported discovery mechanism; additional jobs/calendars/providers need explicit future contracts and authorization.
|
||||
|
||||
## Tests before migration
|
||||
|
||||
Command job/company/Add behavior, keyboard active result/focus, dirty navigation, account switch and stale result rejection; notification read/dismiss does not complete task; link to operation/job section survives aliases; task auto/manual/dismissed rules and keyboard ordering retained. Mail requires real sandbox delivery/reconnect/uncertainty evidence before changing provider flows; Phase 2 mocks are not provider certification.
|
||||
@@ -0,0 +1,47 @@
|
||||
# Component architecture
|
||||
|
||||
ARC-15; affected contracts are in each row and the full [impact matrix](PRESERVATION_IMPACT_MATRIX.md). Names describe responsibilities, not a mandate for one file per name. Retain existing implementations until a scoped consumer needs the shared behavior.
|
||||
|
||||
## Retain, refactor, consolidate or add
|
||||
|
||||
| Target responsibility | Existing owner | Disposition and boundary | PRES |
|
||||
|---|---|---|---|
|
||||
| AppShell / Sidebar | layout/AppShell; App nav/title helpers | **Refactor** existing grouped/collapsed/drawer presentation; preserve auth tree, collapse and active matching. Extract Sidebar only if it simplifies this owner | E07–E09 |
|
||||
| PageHeader | AppShell title/breadcrumb/rightActions plus local page headers | **Consolidate** heading/action hierarchy; keep one h1 and no duplicated global/detail header | E07, E08, W01, C06 |
|
||||
| WorkspaceHeader | local WorkspaceHeader in ApplicationWorkspacePage; CV header | **Retain/refactor** per-domain content; share layout only, not save/status semantics | W02, C06, C10 |
|
||||
| MetricCard | DashboardView metricCards/Card | **Refactor** as data-labelled presentation; no fetching/AI in a card | S01 |
|
||||
| DashboardWidget | DashboardView SectionCard + visibility menu | **Add later** catalogue/order/size wrapper in Phase 8; existing visibility migrated | S02 |
|
||||
| DataTable / MobileDataCard | JobTable and CompaniesTable use MUI Table; admin uses MUI X grid | **Retain** engines; share toolbar/state/cell styles where proven. TanStack Table is installed but no current src import was found; do not introduce it as a migration prerequisite | J05, J06, J08, A01 |
|
||||
| StatusBadge | pipeline statusLabel/statusTone and inline Chips | **Consolidate** presentation using existing status semantics; custom values retained | J07, W02, S01 |
|
||||
| FilterBar | JobTable inline/mobile controls; SavedViewsMenu | **Refactor** presentation around same filters/saved-view owner | J05, S03 |
|
||||
| EmptyState / ErrorState / LoadingSkeleton | ViewStateNotice, useViewResource, local skeletons | **Consolidate** semantics/retry/focus; existing owner still decides data/error states. Do not create three wrappers when one composition suffices | E08 and all loaded pages |
|
||||
| QuickPreviewDrawer | ApplicationWorkspace optional props; no active host | **Add only after parity fixture**, read-only summary/navigation. Do not mount second full editor | W01, J05 |
|
||||
| CommandPalette | QuickCommandDialog + App keyboard trigger | **Refactor/extend** existing action callbacks and owner-scoped result reads | E07, J04, J08 |
|
||||
| NotificationCentre | NotificationsPopover + Notifications API | **Refactor/extend** same store; new full route only when needed | S02, W11, W12 |
|
||||
| AIAction | AiSectionAssistant, CoverLetterAiAssistant, InterviewAiAssistant, document AI tab, aiWorkspace | **Consolidate** state/entry presentation, retaining each API/context and entitlements | C11, W03, W06, W09, S04 |
|
||||
| AIReviewDiff | current/proposed builder, extraction and letter views | **Consolidate** readable comparison/reject/apply UI; domain validations and payload identity remain local | C03, C11, W06 |
|
||||
| DocumentCard / row | CvBuilderPage, Attachments, SubmittedPackagesSection | **Add index projection view**, reuse domain open/download handlers; never merge resource persistence | C05, W07, W08 |
|
||||
| WorkspaceTabs | ApplicationWorkspace tabs; CV studio tabs; settings TabPanel | **Refactor** semantics/responsive selector where repeated; preserve dirty guards and active resource | W01, C06, S03 |
|
||||
| SettingsSection | SettingsView SectionCard; security/provider cards in ProfilePage | **Consolidate** layout/help/errors only; server/local settings scopes stay separate | E04–E06, M06, S03–S05 |
|
||||
| Form fields and dates | MUI TextField/Select/Autocomplete/DatePicker; RichTextField, TagsInput | **Retain + targeted accessibility refactor** for names/help/errors. No form framework or HTML storage migration | C01, C07, W06, J03 |
|
||||
| Dialog / Drawer / confirmation | MUI, confirm, prompt, toast | **Retain** mechanics; standardize focus/name/dirty behavior and mode styling | E08, W01, S05 |
|
||||
| Task row / Timeline | ApplicationChecklist, ApplicationTimeline, InterviewPrep | **Retain/refactor** domain structures; no universal task/event object | W02, W04, W09, W10 |
|
||||
| Chart container | DashboardView SVG helpers | **Add small composition only as needed** for title/period/values table; keep calculations in owner/service | S01 |
|
||||
| Theme providers/tokens | theme, ThemeProvider, themePrefs, themeBootstrap, I18nProvider | **Retain/refine**; no second theme, locale or preference authority | E08 |
|
||||
| Auth/session/API boundary | App, api, sessionBoundary, accountPlan | **Retain unchanged** unless a separately evidenced defect; server identity/permissions remain authoritative | E02–E09, S04 |
|
||||
|
||||
Unreachable Attachment, JobFlowBar, Markdown and UserManagementCard in the earlier census are not authorized deletions. Shared component extraction must prove all existing consumers, not assume file size or duplicate names require a new abstraction.
|
||||
|
||||
## Data and state ownership
|
||||
|
||||
Presentation primitives accept current state/callbacks, not raw account IDs with their own API clients. Form draft, persistence revision, selected source and send attempt remain in the relevant domain owner. A UI “scope” label is not authorization. No generic hook that conflates account profile singleton, identified CV, package capture and mail send.
|
||||
|
||||
Keep API cancellation/provenance and private-tree lifetime. Existing resource loads may be split only with latest-response and owner boundary tests. Avoid duplicating network loads between a header, sidebar panel and content. Newly consolidated Documents/Analytics need explicit bounded reads, not hidden browser crawls.
|
||||
|
||||
Reusable components should emerge from actual repeated behavior. E.g. MUI already implements Button/Dialog semantics; standardizing its theme is enough. AI review can share a comparison frame while retaining different extraction/block/letter acceptance validators. Do not flatten them into one unsafe Apply callback.
|
||||
|
||||
## File and implementation discipline
|
||||
|
||||
Keep current folder layout initially. Add small shared modules next to existing components/theme only when first consumers migrate. No bulk rename, barrel re-export tree, new package/workspace or Storybook dependency in Phase 4. Use existing test/browser fixtures for representative states.
|
||||
|
||||
Do not move App's provider order, router creation and navigation presentation in the same change. Do not change CV save owner while extracting visual fields. Do not run mail draft/send restructuring alongside generic document work. Components listed “add later” are not Phase 4 scope just because their names appear in this document.
|
||||
@@ -0,0 +1,54 @@
|
||||
# CV workspace
|
||||
|
||||
ARC-09; PRES-C05–PRES-C12, PRES-W05, PRES-W07, PRES-E08, PRES-E09. Retain [CvBuilderEditor](../../../job-tracker-ui/src/views/CvBuilderEditor.tsx), [customization](../../../job-tracker-ui/src/components/cv/CvCustomizeTab.tsx), [cvBuilder client](../../../job-tracker-ui/src/cvBuilder.ts) and the shared server preview/PDF renderer.
|
||||
|
||||
## Library and editor
|
||||
|
||||
The /career/builder library is labelled CVs. Preserve name/create/copy/delete, template gallery with actual rendered thumbnails, publish/unpublish/share and PDF download. A public slug is separate from private numeric identity. Documents links here rather than exposing a second CV editor.
|
||||
|
||||
```text
|
||||
CV name · This CV only · optional linked job Save state · Undo Redo · Export
|
||||
[Content | Template | Customize | AI tools | History]
|
||||
[Section navigation + selected editor] [Live paginated preview]
|
||||
[Page n of m · Fit width]
|
||||
```
|
||||
|
||||
Existing studio capabilities are preserved regardless of tab order. Recommend Content as the primary editing task; template choice stays obvious for creation. A tab-order change is presentation only and requires keyboard/route regression. Reuse current editor state/save owner rather than remounting it on every tab, theme or viewport change.
|
||||
|
||||
## Content and scope
|
||||
|
||||
Each section: localized title, visibility, position, source/inherited/override marker, edit and contextual AI. Expand one or more sections; users are not forced to close previous work. Retain built-in item visibility/order, custom/preset/free-text sections, stable keys, hide/remove and manual content. Reorder uses existing native drag plus Move up/down controls; mobile and keyboard have equal outcomes.
|
||||
|
||||
“Inherited from Career Profile” links to the source. “Customized in this CV” offers comparison/reset. Reset changes only the override; it does not delete the career item. Job-specific variants show the linked job without implying ownership of that job or automatic submission. Restoring source or an old version must never bypass the correct server-owned resource lookup.
|
||||
|
||||
## Bounded customization with advanced parity
|
||||
|
||||
Default Customize shows template, accent, supported typography, font size, margins and spacing. Advanced disclosure retains every existing setting:
|
||||
|
||||
- Template-capability-aware heading/header styles, colors, photo and icons.
|
||||
- Skills presentation/groups, one/two columns, sidebar and section columns.
|
||||
- A4/Letter, document density, date format and document language.
|
||||
- Per-section rows/grid/compact/bubbles and section spacing/order/visibility.
|
||||
- Unsupported-setting handling and the server's normalization/fallback behavior.
|
||||
|
||||
This is intentionally constrained to CV layout, not a word processor. Do not drop current advanced settings because the brief lists fewer. No arbitrary absolute positioning, HTML editor or new font/template engine. UI Comfortable/Compact density is **not** CV document density.
|
||||
|
||||
Template switches retain compatible settings and make unsupported options unavailable with explanation. Existing saved template/settings IDs remain renderable. Any destructive reset is explicit; do not silently reset a CV when changing application theme.
|
||||
|
||||
## Preview and persistence
|
||||
|
||||
Keep debounced server preview, actual page boundaries, automatic fit and shared HTML/PDF engine. Preview is render-only; no implicit AI or profile writes. Maintain latest-result sequencing and dispose old preview/blob work on unmount/account switch.
|
||||
|
||||
Desktop split needs independent labelled, keyboard-scrollable panes. Mobile has Edit / Preview, remembers section/scroll, keeps save/export accessible and never compresses both into a phone. Manual zoom (NEW-12) is optional incremental work; Fit width already exists. Browser page zoom/reflow remains accessible even if manual preview zoom is deferred.
|
||||
|
||||
Save states: loading, editing/unsaved, saving, saved, failed with retry, reauthentication required. Do not show Saved before acknowledgement. Retain current local save queue and dirty navigation guard; it only serializes one editor and cannot resolve concurrent writers. Undo/redo is editor settings history; persisted version restore creates a new version rather than erasing history. Do not label either as conflict protection.
|
||||
|
||||
PDF failures/busy admission use existing B03 contract with understandable retry; never start parallel renders for preview thumbnails or bypass the shared generator. Private export/public published export retain separate authorization/publication checks.
|
||||
|
||||
## AI
|
||||
|
||||
Per-section improve/translate/custom instruction and whole-document translate/improve/spelling retain source/target language, current/proposed comparison, edit/accept/reject and strict block identity validation. Reject/close/error does not modify settings. Accept targets this variant; if a separate Save follows, say so. Do not place “apply to Career Profile” beside CV Accept.
|
||||
|
||||
## Required evidence before migration
|
||||
|
||||
Phase 2's mobile headline override and AI tests are a starting point. Add source reset/inherited edit, custom item reorder/hide, history/undo/reload, public unpublish, long searchable multipage PDF and unsupported template settings. Exercise selected-source context and native package relationships after P2-D01 is repaired separately. Loaded preview keyboard scroll after viewport transition is an F14 gate. Do not edit this stateful owner concurrently with stale-revision work; no F01 fix is claimed by this UX plan.
|
||||
@@ -0,0 +1,106 @@
|
||||
# Dashboard architecture
|
||||
|
||||
ARC-04 / ARC-05; PRES-S01, PRES-S02, PRES-W02–PRES-W12, PRES-C05, PRES-A01–PRES-A03. New work: NEW-01, NEW-05, NEW-08, NEW-11 in [Open decisions](OPEN_DECISIONS.md).
|
||||
|
||||
## Existing implementation and honest metric meanings
|
||||
|
||||
[DashboardView](../../../job-tracker-ui/src/components/DashboardView.tsx) calls stats, analytics, analytics-overview, tags, tag-trends and reminders under /jobapplications. It persists five owner-local visibility flags: cards, activity, funnel, companies, skills. No order, resize, goal or server layout contract exists.
|
||||
|
||||
[AnalyticsService](../../../JobTrackerApi/Services/AnalyticsService.cs), [analytics controller](../../../JobTrackerApi/Controllers/JobApplicationAnalyticsController.cs) and [DTOs](../../../JobTrackerApi/Models/AnalyticsDtos.cs) establish these constraints:
|
||||
|
||||
- stats.active and overview.totalActive count **non-deleted tracked jobs**, including closed and pre-application statuses. They do not measure in-flight applications. total includes deleted rows.
|
||||
- The funnel counts jobs **currently** in each canonical stage. It is not a historical cohort conversion funnel. Unknown custom values may be absent from that canonical-stage series; byStatus retains raw values.
|
||||
- Monthly analytics selects jobs applied within a month-aligned window, then counts their dated responses in the displayed months. It is not all responses received in that period, and not an eventual response probability.
|
||||
- Source breakdown uses current Company.Source and includes prospects. Top-source/top-company lists are truncated; do not treat their sum as the whole population.
|
||||
- Time in stage is median **current occupancy age**, with fallback to DateApplied or SavedAt when a transition is unavailable. It is not completed-stage duration.
|
||||
- Median first response uses rows with both dates; averageDaysSinceApplied is application age, not response speed. Current calculations clamp negative durations; data-quality labeling must not pretend dates were verified.
|
||||
- Upcoming interview captions derived from “interview-prep” signals identify preparation work, **not scheduled interviews**.
|
||||
|
||||
These are source-backed semantic limitations (P3-O01 in Open decisions). Preserve access to current reports, but label them accurately during their scoped migration. No analytics implementation or retrospective data repair occurs here.
|
||||
|
||||
## Default personal layout
|
||||
|
||||
Useful immediately: tracked-job summary; recorded response summary with denominator; current interview/offer counts; attention/follow-ups/deadlines; application activity; current pipeline distribution; companies and tags; onboarding when incomplete. Keep existing salary/stage/source details reachable from Analytics. New data-dependent widgets are absent until supported, never placeholder zeroes.
|
||||
|
||||
Suggested visual order: “Next actions” and key counts first, activity/pipeline next, companies/tags and details below. A new user sees real empty states with Add/import job and Review Career Profile. No sample jobs or fake success metrics. Users may hide any widget; if all are hidden show an intentional layout-empty state with Customize/Restore defaults.
|
||||
|
||||
## Layout contract for later Phase 8
|
||||
|
||||
A small catalogue defines widget ID, localized title, supported sizes and data owner. Use CSS grid with discrete small/medium/wide spans; do not start with a dashboard framework or free-positioned canvas. Plain ordered IDs plus visibility and size metadata suffice; no stored HTML or career content.
|
||||
|
||||
Customize mode supports show/hide, drag/reorder plus Move earlier/later, size choices on suitable charts/lists, and Restore defaults with a clear confirmation. Changes give immediate preview; storage failure leaves usable content and a retry/message, never silently claims persistence. Unknown IDs are ignored safely without losing known entries; invalid sizes fall back to defaults. Preserve existing five hidden/visible choices when migrating; do not silently re-enable hidden widgets.
|
||||
|
||||
Use one logical order across breakpoints. Mobile has a single-column feed and move/hide controls; desktop width preferences remain saved but inactive on mobile. Charts have supported size ranges, metrics fixed height with wrapped labels. Reset affects only dashboard layout, not jobs, account preferences, goals or canonical profile.
|
||||
|
||||
**Persistence decision OD-04:** recommend owner-keyed device-local metadata first, matching current scope, clearly labelled “Saved for this account on this device.” Cross-device layout requires a separately tested server preference contract before Phase 8; do not claim localStorage syncs devices. Either option must validate owner from the active identity, dispose A's state on switch, handle corrupt/stale data and avoid storing content. Theme/density settings are separate; no generic preference blob that merges unrelated security controls.
|
||||
|
||||
## Widget catalogue and data requirements
|
||||
|
||||
Availability: **Existing** = current endpoint/behavior with stated meaning; **Derivable** = fields exist, but a bounded owner-scoped aggregate or read composition is still needed; **New data** = required facts/contracts do not currently exist. No client N+1 fetch across every job to build global metrics.
|
||||
|
||||
| ID / widget | Availability and data source | Definition / boundary / empty behavior |
|
||||
|---|---|---|
|
||||
| DW-01 Tracked jobs | Existing: stats.active | Non-deleted records; rename display accordingly, not in-flight applications |
|
||||
| DW-02 Active applications | Derivable: Status, DateApplied, IsDeleted | Explicit applied active-stage mapping; exclude prospects/closed, unknown separate. Do not reuse DW-01 |
|
||||
| DW-03 Total recorded jobs / trash | Existing: total/deleted | Label deleted inclusion; trash link retains restore semantics |
|
||||
| DW-04 Applications this week | Derivable: DateApplied | Distinct submissions in agreed local week; no SavedAt substitution; period/timezone gate |
|
||||
| DW-05 Applications this month | Existing monthly applied point | Calendar month label; not rolling appliedLast30Days |
|
||||
| DW-06 Applications last 30 days | Existing: appliedLast30Days | Rolling server-time period, labelled as such until timezone contract is settled |
|
||||
| DW-07 Interviews | Existing: current Interview stage | “Jobs currently at interview”; not number of meetings or all-time interviews |
|
||||
| DW-08 Upcoming interviews | New data: scheduled interview start/end/timezone | Do not infer appointment from Interview status, deadline or follow-up |
|
||||
| DW-09 Offers | Existing: current Offer stage | Current recorded offers, link /offers; historical offer count needs events |
|
||||
| DW-10 Rejections | Existing: normalized current Rejected stage | Current recorded outcome; neutral language, no failure badge |
|
||||
| DW-11 Response rate | Existing period series or source rates, different denominators | Display exact cohort/window and responses/applied sample; no mixing overview and period denominators. No sample = “Not enough recorded data” |
|
||||
| DW-12 Interview conversion | Derivable with data-quality qualification: status events + application cohort | Distinct applied jobs that reached Interview / submitted cohort; current Interview count is not this numerator |
|
||||
| DW-13 Offer conversion | Derivable with same historical cohort | Distinct jobs reaching Offer / submitted cohort (explicit label); missing history shown, not fabricated |
|
||||
| DW-14 Application funnel | Existing canonical distribution | Label “Current pipeline”; include Unknown/custom bucket when migrating. Historical conversion is separate NEW work |
|
||||
| DW-15 Applications over time | Existing analytics monthly points | Applied counts, period/source subtitle and accessible values table |
|
||||
| DW-16 Applications by status | Existing byStatus | Preserve custom/raw values, aliases and unknown labels |
|
||||
| DW-17 Applications by sector | New normalized sector coverage | No reliable tracked-job sector dimension found; NAV listing data alone does not cover tracked history |
|
||||
| DW-18 Applications by location | Derivable JobApplication.Location | Unknown explicit; raw text first, normalized municipality grouping needs a mapping contract |
|
||||
| DW-19 Applications by source | Existing source response summary; complete count needs aggregate | Company.Source is mutable company-level provenance, not original job capture source; top six is not full breakdown |
|
||||
| DW-20 Applications by role | Derivable JobTitle | Raw role/title distribution; normalized role families require taxonomy, not automatic AI classification |
|
||||
| DW-21 Average response time | Derivable DateApplied/ResponseDate | Arithmetic mean over valid paired responses, show n; existing median offered separately, do not relabel it average |
|
||||
| DW-22 Median first recorded response | Existing overview median | Available dated sample; no implication missing dates mean no response |
|
||||
| DW-23 Time in pipeline stages | Existing current occupancy medians | Label current-stage age and fallback; completed durations/history trends need new aggregation |
|
||||
| DW-24 AI match statistics | Derivable per-job deterministic match output, aggregate missing | Require score definition, profile/job version and scored sample; do not trigger generation on dashboard view |
|
||||
| DW-25 Recent activity | Job-scoped recentActivity/timeline exists; global read missing | Bounded owner event feed, source links and safe summaries; monthly applications chart is not event history |
|
||||
| DW-26 Deadlines | Existing job deadlines/reminders | Upcoming/overdue date-only semantics; full period read coverage must be declared |
|
||||
| DW-27 Tasks | Existing per-job checklist; cross-job aggregate missing | Pending/done/dismissed, stable IDs; “Tasks due” awaits per-task due dates |
|
||||
| DW-28 Follow-ups / attention | Existing reminders/workflowSignal | Keep existing reason/action links; feed includes more than overdue follow-ups |
|
||||
| DW-29 CV usage | Derivable CvVariant job link + package metadata, aggregate missing | Current linkage separate from recorded submitted version. A download alone is not “used to apply” |
|
||||
| DW-30 CV performance | Future qualified historical join | Submission cohort + frozen CV/version + outcomes, n and missing-data rate; correlation only; P2-D01 gate |
|
||||
| DW-31 Recently edited CVs | Existing library UpdatedAtUtc | Bound list and safe editor links; not performance |
|
||||
| DW-32 Weekly goals | New optional goal preference | Disabled until chosen, editable/disable/pause; no default quota. Completion uses valid DateApplied, never encouraging unsuitable applications |
|
||||
| DW-33 AI recommendations | Existing deterministic next steps; new AI aggregation/panel optional | Label rule-based guidance honestly; user-invoked AI only, grounded reasons, hide/ignore, no implicit edits |
|
||||
| DW-34 Companies | Existing topCompanies | Recorded activity and responses; top eight and unknowns disclosed |
|
||||
| DW-35 Skills/tags and trends | Existing tags/tag-trends | Job tags, not the user's verified skills. tags does not consume a months parameter; label its actual period |
|
||||
| DW-36 Salary insights | Existing currency/period groups | Preserve separate currencies/periods; no inferred FX conversion |
|
||||
| DW-37 Work arrangement | New consistent tracked dimension | Imported description text alone is not a reliable remote/hybrid aggregate |
|
||||
| DW-38 Interview/offer trends | Derivable historical events with completeness limits | Not current-stage counts plotted as historical outcomes; no synthetic transition dates |
|
||||
| DW-39 Response/match trends | Partial existing monthly responses; match history missing | Define cohort vs events, scoring version and missing history before trend claims |
|
||||
|
||||
Period controls must explain which widgets are all-time, current snapshot or selected-period. Do not put a global “this month” above unfiltered all-time data. Zero, unknown, loading, unauthorized/provider-unavailable and failed are distinct. No automatic polling/generation per widget beyond current service needs. Keyboard/data-table alternatives accompany every chart.
|
||||
|
||||
## Separate aggregate admin dashboard
|
||||
|
||||
Propose /admin overview; retain /admin/users, /admin/audit and /admin/system. Current system page is operational diagnostics, not product analytics. Never compute product metrics by downloading individual profiles or the existing admin user table into a dashboard.
|
||||
|
||||
| Candidate | Current evidence | Required implementation / honest limit |
|
||||
|---|---|---|
|
||||
| Registered users | Identity users exist | New authorized server count; define inclusion of pending/deleting accounts |
|
||||
| New users by period | ApplicationUser has no registration timestamp | Reliable creation event/timestamp contract and historical coverage; do not infer from OAuth-linked dates |
|
||||
| Active users | Sessions exist, no agreed activity metric | Define meaningful activity/time window/retention; active sessions are not active people |
|
||||
| Total jobs tracked | Admin system exposes operational counts | Verify scope and deletion inclusion; new explicit aggregate endpoint for product meaning, not reuse diagnostic counts blindly |
|
||||
| Interviews/offers recorded | Job statuses/events exist | Server aggregate with distinct job/event meaning and missing-history qualification |
|
||||
| CVs created | CvVariant timestamps exist | Authorized count/time buckets; owner-scoped personal library is not admin aggregate |
|
||||
| Documents generated | Several artifact types/render paths exist | Define successful persisted artifact vs PDF render/download/retry; no unified document counter today |
|
||||
| AI usage | Usage metering exists | Aggregate actions/tokens/period/failures as supported; no prompts, responses or career facts |
|
||||
| Common sectors | No reliable shared sector dimension | Future normalized dimension and privacy-safe grouping |
|
||||
| Common locations/roles/technologies | Job location/title/tags exist | New bounded aggregate; use job metadata, not individual profile skill extraction |
|
||||
| Subscription/trial metrics | Stripe status fields/entitlements exist; no generic trial contract proven | Define paid/active/cancelled periods from billing authority; never infer trials from Free accounts |
|
||||
| Onboarding/adoption/churn/conversion | Current checklist/UI alone does not supply product event funnel | Future event/consent/retention definitions; no fabricated denominator |
|
||||
|
||||
Privacy: aggregate-only responses, no owner IDs/names/emails/job descriptions/CV content. For sensitive breakdowns propose fixed coarse cohorts, minimum cell size 10 with complementary suppression, no arbitrary filters/drill-down that reconstruct smaller groups. This is a review proposal, **not an anonymity guarantee**. Totals/period differences and rare roles can still identify; evaluate release scope/retention before implementation. Support access remains separately authorized/audited and cannot be reached by clicking an analytics bar. Denial must be server-enforced even when admin navigation is hidden.
|
||||
|
||||
Admin dashboard work waits for OD-09's metric/privacy definition. Personal layout settings never affect aggregate scopes or admin operational controls.
|
||||
@@ -0,0 +1,52 @@
|
||||
# Design-system architecture
|
||||
|
||||
ARC-14; PRES-E08 and all consumers, especially PRES-J05, PRES-C06–PRES-C09 and PRES-S03. **Retain MUI/Emotion, MUI icons and existing theme providers.** No evidence justifies a competing library or state/router replacement.
|
||||
|
||||
## Foundation and ownership
|
||||
|
||||
[theme.ts](../../../job-tracker-ui/src/theme.ts) already supplies palettes, typography, custom shadows, CSS variables, breakpoints and MUI overrides. themePrefs/themeBootstrap/ThemeProvider preserve initial paint and light/dark/system selection. AppShell currently has separate hardcoded navy/indigo constants; migrate them to semantic theme roles deliberately after shared-state contrast proof.
|
||||
|
||||
Use the existing theme as the token authority; page CSS variables may alias it. No parallel JSON token compiler, token package or generic design-system runtime. Typed augmentation only for small roles the current theme cannot express. Existing MUI Button/TextField/Select/Dialog APIs remain; do not wrap every primitive merely to rename it.
|
||||
|
||||
## Token proposal
|
||||
|
||||
Values below are **working architecture proposals**, to validate in P4 fixtures. Final brand hue/logo is not selected.
|
||||
|
||||
| Family | Planned roles / scale | Usage |
|
||||
|---|---|---|
|
||||
| Brand | primary main/on-primary, interaction hover/selected/focus | One hue; keep current #5B5BD6 as provisional continuity, not final approved identity |
|
||||
| Text | primary, secondary, muted, disabled, inverse, link | Explicit foreground/background pairs; avoid arbitrary opacity for required copy |
|
||||
| Surfaces | canvas, content, subtle, raised, overlay, navigation | Light neutral canvas with content layer; dark layered neutral surfaces rather than inversion |
|
||||
| Borders | subtle separator, control boundary, strong/selected, error, focus | Separator need not meet same contrast as an essential form boundary |
|
||||
| Status | info/success/warning/error plus neutral; each background/text/icon/border | Pipeline text and icon alongside color; no identical semantic mapping assumed across unrelated domains |
|
||||
| Typography | body 14/20, dense/support 13/18, caption 12/16; section 18/24, page 28/34 desktop and 24/30 phone; weights 400/600/700 | Preserve Archivo/system stack and æ/ø/å; numerals tabular where useful; rem sizing, no fixed-height clipping |
|
||||
| Spacing | 4, 8, 12, 16, 24, 32, 48 px equivalents | Related controls vs sections; reuse existing page/card/gap variables |
|
||||
| Radii | control 8, panel 12, overlay 16; pill only for small status/tag | Subtle distinction without every surface being a nested rounded card |
|
||||
| Elevation | flat/base, subtle raised, overlay | Borders/surface contrast carry dark-mode depth; no glow/glass dependency |
|
||||
| Motion | immediate feedback, ~120–180 ms disclosure, ≤220 ms overlays as proposal | No animated metric counters; reduced-motion removes nonessential movement |
|
||||
| Layout | existing responsive breakpoints; page max-width by reading/data/editor mode | Reading content bounded, tables/editor can use width; no one-width-fits-all |
|
||||
| Density | Comfortable/Compact spacing variants | Application surfaces only; separate from CV document density |
|
||||
|
||||
Retain existing heading semantics separately from style variants: a page can be h1 with page-title styling rather than inheriting a marketing hero size. Do not change font loading/hosting or add a typeface dependency in foundations.
|
||||
|
||||
## Light and dark
|
||||
|
||||
Choose and test both schemes as first-class palettes. Navigation can retain a distinct tonal surface while honoring mode and contrast; no assumption that current fixed navy is inaccessible everywhere. Dark hover/selected/focus layers need visible borders/outlines without washing out content. Avoid gradients and glass in core product surfaces; any existing public marketing treatment can wait for its own migration.
|
||||
|
||||
One semantic role may need different foregrounds in different modes. Never compute on-primary/alert text by blindly lightening/darkening one color and assume it meets contrast. P4 explicitly verifies actual rendered pairs, including disabled-adjacent explanations and focus indicators. Prefer outline + offset for focus over low-opacity shadow alone.
|
||||
|
||||
## Component variants and state contract
|
||||
|
||||
Use contained primary for one main action, outlined secondary and text tertiary. Destructive confirm is explicit and labelled; red is not the default presentation of ordinary rejection outcomes. Pro/AI unavailable controls need visible reasons and manual alternatives, not only disabled opacity.
|
||||
|
||||
Buttons, inputs, selects/comboboxes, checkboxes, switches, tabs, table headers/rows, badges, alerts, menus, dialogs and drawers need default/hover/focus/selected/disabled/error/loading definitions. Focus is distinguishable from selected. Form label/error/help IDs stay linked. Placeholder is a hint, not a label.
|
||||
|
||||
Empty/error/loading states use the existing ViewStateNotice and MUI primitives with consistent semantics. Keep old content while refreshing where the owner currently supports it, but clearly mark a refresh failure; never replace an error with fake zero metrics.
|
||||
|
||||
## Page primitives
|
||||
|
||||
Minimal set: PageHeader (heading/description/actions), WorkspaceHeader (identified resource/scope/state), PageSection (optional heading, no mandatory card), and a small data/reading/editor width contract. Reuse existing Shell/SectionCard patterns only where source repetition warrants extraction. See [Component architecture](COMPONENT_ARCHITECTURE.md) for owners and explicit deferred additions.
|
||||
|
||||
## Phase 4 acceptance
|
||||
|
||||
First establish semantic state pairs and visible focus with a loaded representative form/table/alert fixture in both schemes and locales. Keep current brand and route tree. Later adjust typography/layout primitives only after responsive checks. Test meaningful interaction/contrast, not snapshots of CSS or token names. No visual identity sign-off, accessibility certification or production release is implied by this planning package.
|
||||
@@ -0,0 +1,48 @@
|
||||
# Documents UX
|
||||
|
||||
ARC-10; PRES-C05–PRES-C12, PRES-W05–PRES-W08, PRES-M04, PRES-S05, PRES-E09. NEW-11 covers missing cross-job read projections, not a replacement storage model.
|
||||
|
||||
## Purpose and existing resources
|
||||
|
||||
Documents is an owner-scoped **index of existing resources** with links to the editor that owns each one. It does not make every artifact a new generic Document record.
|
||||
|
||||
| Category | Existing backing / destination | State and relationship rule |
|
||||
|---|---|---|
|
||||
| CVs | CvVariant / CV library and editor | Current settings + canonical inherited content; optional job link; private/public independent of submission |
|
||||
| Cover letters | Job letter text/history and ApplicationAssets | One job's draft/versions; edit at job Application → Letter |
|
||||
| Application answers / recruiter draft | Existing package draft fields | Job-owned text; not a new standalone response library |
|
||||
| Uploaded attachments | Attachments owned through job | Purpose/type/size/name/date; current upload/rename/AI-use/download/delete retained |
|
||||
| References / certificates | Attachment categories where the existing purpose supports them | Display as uploaded evidence; no new verification/credential issuer system |
|
||||
| Generated materials | Existing variant/letter/tailored output paths | Generated preview/PDF may be transient; do not claim every download is stored |
|
||||
| Submitted packages | Submitted package records, frozen content and archived files | Immutable historical evidence; version/time/job and captured source identifiers |
|
||||
| Email drafts | Existing correspondence draft service | Context link to Correspondence; not a file or proof of delivery |
|
||||
|
||||
A certificate uploaded to a job is not automatically a verified Career Profile qualification. A public CV is not automatically submitted. A frozen package is a recorded snapshot, not confirmation that an employer received it.
|
||||
|
||||
## Index and data availability
|
||||
|
||||
Proposed /documents has text search, type, linked job and Draft / Submitted filters; sort by updated/captured date where present. CV public/private state is a separate badge/filter. Row/card: name, kind, linked role/company, source/version when recorded, draft/frozen state and open/download actions. Mobile uses structured cards; desktop may use a compact table/list.
|
||||
|
||||
CV library reads exist. Attachments, letters and package history are mainly job-scoped. A coherent cross-job index/search needs a bounded server projection with authenticated-owner queries, pagination, supported sort and metadata-only responses. Do not download every job/body/attachment to synthesize an index in the browser. Until that projection exists, provide honest links to CVs and selected-job documents rather than pretending a complete All documents result.
|
||||
|
||||
No binary relocation, schema unification or new upload-to-account bucket is presumed. General account-level reference storage would be a separately approved NEW requirement. Preserve job attachment limits and safe response headers; never render file content in search snippets.
|
||||
|
||||
## Relationships and actions
|
||||
|
||||
Open routes to the existing owner editor. Show “Used for” only when a relationship/submission actually records it. Current attachment/variant relation and submitted version are separate; changing current material cannot relabel history as the newest version.
|
||||
|
||||
Retain current CV association cardinality: CvVariant has an optional JobApplicationId and attaching may re-point it. Do not offer “attach everywhere” as though a many-to-many relation exists. Detaching does not delete the variant. Deleting a job does not imply deleting independent CVs. Preserve all ownership/reference guards.
|
||||
|
||||
Download current PDF renders current CV; archived package download uses captured content/files. Distinct labels prevent confusing the two. No regenerate button overwrites frozen packages. Capturing again creates a new package via the existing operation. Live attachment deletion never implies erasing its historical archived copy; source-copy failure stays an error.
|
||||
|
||||
AI-use toggle is explicit context inclusion permission for that attachment; do not broaden it when moving its card to Documents. Upload is not permission to use all files with every AI action.
|
||||
|
||||
## Error, dirty and authorization behavior
|
||||
|
||||
Missing/deleted/foreign resource yields existing safe API result and no private metadata. An index entry may become stale: refresh and explain unavailable; never attach another matching-name item. Navigation from a dirty letter/CV honors its guard; account switching disposes results/drafts. No owner IDs from filters select an API tenant.
|
||||
|
||||
P2-D01 blocks native SQLite package capture/tailoring. Existing mocked/service proofs are not successful archive-preservation evidence. Freeze/history presentation migration waits for its separate repair and actual unchanged HTML/letter/binary checks. A unified Documents page must not conceal that baseline defect.
|
||||
|
||||
## Validation
|
||||
|
||||
List/search isolation with A/B, draft vs frozen vs public labels, source editor links, foreign attach denied, detach keeps variant, live source mutation does not alter captured content, archived bytes survive live deletion, no extra render on listing, correct download filenames/encoding. Extend Phase 2 W07/W08 evidence before claiming complete document parity.
|
||||
@@ -0,0 +1,46 @@
|
||||
# Information architecture
|
||||
|
||||
Affected: all 57 PRES contracts; [per-group destinations](PRESERVATION_IMPACT_MATRIX.md). Recommendation ARC-01.
|
||||
|
||||
## Navigation tree
|
||||
|
||||
Use understandable labels with EN/Bokmål translations; English below specifies meaning, not final translation strings.
|
||||
|
||||
| Primary group | Primary destination | Secondary navigation / contextual entries |
|
||||
|---|---|---|
|
||||
| Home | Dashboard | Customize; links to Analytics, due follow-ups and source jobs |
|
||||
| Job search | Jobs | Tracked jobs (Table / Board), Discover, Follow-ups, Companies, Offers; Trash in workspace utilities |
|
||||
| Job search | Correspondence | Inbox, Drafts, Review; linked job and connected-provider entry |
|
||||
| Career | Career Profile | Overview, Edit, Import review/history, Evidence |
|
||||
| Career | CVs | Library/templates; selected CV editor |
|
||||
| Career | Documents | All supported artifacts; type/job/state filters; links to CV library and job editors |
|
||||
| Insights | Analytics | Overview, trends, breakdowns, stage/salary insights; source-job filters |
|
||||
| Account | Settings | Account, Security, Appearance/language, Notifications/rules, Connections, AI/plan, Data/privacy |
|
||||
| Admin, authorized only | Admin dashboard | Aggregate product overview (new); Users, Audit, System as distinct secondary pages |
|
||||
|
||||
Correspondence earns a primary entry because it has independent inbox, drafts, provider review and real-send workflows (PRES-M01–M06). Hiding it in Documents would blur messages and files. The Jobs secondary navigation keeps discovery, follow-ups, companies and offers visible without separate duplicate top-level menus. A direct child URL selects Jobs as its primary parent even when the path is not prefixed /jobs.
|
||||
|
||||
Notifications remain globally reachable through the bell; an expanded centre can have a utility route. Background operations remain reachable from the centre and Settings/System activity link for the user. Admin operations remain separate from the user's operations. No empty Admin dashboard is shipped before its aggregation exists.
|
||||
|
||||
## Page and workspace hierarchy
|
||||
|
||||
- Dashboard answers “what needs attention?” Analytics answers “what happened, over which period and sample?” A metric deep-links to its source/filter, not a second unrelated dataset.
|
||||
- Jobs is the work index. Table/Board is presentation, not pipeline identity. Discover is a separate search source within Jobs; importing still requires review.
|
||||
- Job workspace owns ongoing work on one job: Overview, Match, Application, Documents, Timeline, Notes & tasks, Interview. Correspondence is contextual within that job and also accessible through the inbox.
|
||||
- Career Profile owns canonical facts. CVs selects/renders those facts with document overrides. Documents helps find the resulting resources without creating a second CV database/editor.
|
||||
- Account means login identity, sessions, privacy and preferences. “Career Profile” never means login/email settings.
|
||||
- Admin has privileged aggregate/operational work; personal Dashboard always remains personal, even for an administrator.
|
||||
|
||||
## Secondary navigation rules
|
||||
|
||||
Keep a stable Jobs workspace navigation row on list/discovery/company/offer/follow-up surfaces. On /jobs/:id use Jobs breadcrumb/back plus document-specific tabs; do not stack both full navigation rows and seven more tabs on a phone. Secondary items live in a labelled select on narrow layouts when they cannot fit.
|
||||
|
||||
Use a simple Settings section list with links to existing /profile and /settings/connected-accounts until their content is safely relocated. Their primary owner is Settings; there are no duplicate Account/Profile menu destinations. Existing tab content, import/export, capture setup, billing availability and deletion controls remain reachable.
|
||||
|
||||
Avoid a separate “AI” route. Contextual AI actions open relevant review/assistant surfaces. Avoid top-level Cover letters, Applications, Board or Templates entries when the existing workspaces already own them.
|
||||
|
||||
## Classification and sequencing
|
||||
|
||||
Grouped navigation and Jobs consolidation are UX improvements to existing behavior. Analytics and Documents are new **destinations**, built from existing functions plus explicitly qualified read requirements. Global cross-job document search and product/admin aggregation are new API work when no suitable endpoint exists. Dashboard customization is Phase 8 work, not a prerequisite to naming its destination.
|
||||
|
||||
No capability is deprecated. MUI/Emotion and existing route/data owners remain. [Route plan](ROUTE_PLAN.md) is the authoritative migration table; [Component architecture](COMPONENT_ARCHITECTURE.md) identifies reuse. Navigation simplification must not remove advanced, provider, privileged or low-frequency functionality.
|
||||
@@ -0,0 +1,51 @@
|
||||
# Jobs workspace
|
||||
|
||||
ARC-06; PRES-J01–PRES-J10, PRES-W01, PRES-E07–PRES-E09, PRES-S03. [Current JobTable](../../../job-tracker-ui/src/components/JobTable.tsx), [KanbanBoard](../../../job-tracker-ui/src/components/KanbanBoard.tsx), SavedViewsMenu and EditJobDialog remain the owners.
|
||||
|
||||
## Structure and defaults
|
||||
|
||||
Page header: Jobs, result count and Add/import job. Secondary row: Tracked, Discover, Follow-ups, Companies, Offers; Trash in visible utilities menu. Inside Tracked: **Table / Board** switch, Search, Filters, Saved views, Columns, Comfortable/Compact. Desktop defaults to Table; phone Table choice means structured cards. The view switch is not another primary nav destination.
|
||||
|
||||
Explicit view query wins over an optional remembered owner-local choice. First use stays table; saved preference must not override a shared URL. Existing /kanban remains functional until matching query semantics and keyboard behavior work in the unified owner. Do not recreate AddJobModal or create jobs as a side effect of route mounting.
|
||||
|
||||
## Table information
|
||||
|
||||
| Default visible | Optional but preserved | Conditional new columns |
|
||||
|---|---|---|
|
||||
| Selection, company, role with next-action cue, status, location, deadline, applied date, row actions | Existing days-since and external source link toggles; page size 15/20/25; all current toggle behavior | Follow-up date, package readiness, recorded match with provenance, favourite/priority after its explicit contract |
|
||||
|
||||
Show “Not applied” for null DateApplied, not today or zero days. Long text wraps to a controlled second line with full accessible text and full page access. A row action must not also navigate; selection/status menu/external link remain independent. Do not hide existing information under hover-only interaction. Salary, contacts, descriptions and full timeline belong in preview/detail rather than making every row tall.
|
||||
|
||||
New optional match cells need bounded list data, not a request or AI call for every row. Unknown/insufficient match shows no invented percentage.
|
||||
|
||||
## Filter and saved-view contract
|
||||
|
||||
Retain server q, status (including raw custom values), companyId, location, needsFollowUp, readiness, deleted/includeDeleted, sortBy, sortDir and pagination. Filter changes reset pagination as today. Search retains debounce/error behavior. Active filters are visible chips with Clear all; clear does not alter column/density settings or stored named views.
|
||||
|
||||
Saved views already exist and are justified by repeat searches. Preserve create/select/delete and owner isolation. Do not introduce a second “saved filter” store. View/layout/density may be added only through versioned compatible presentation metadata; existing saved views must still load. Board must apply the same supported filters and result scope before consolidation; retain existing large-list limits explicitly, never silently omit jobs.
|
||||
|
||||
Selection is explicit and page-scoped unless a later “all matching” server contract is added. Show selected count and scope. On view/filter/result changes clear invalid selections deliberately, with no action on invisible stale IDs.
|
||||
|
||||
## Bulk and row actions
|
||||
|
||||
Keep edit, exact status choice, delete-to-trash, restore and existing confirmation/partial failure behavior. After partial failure report successes/failures and keep failed items actionable; never announce all succeeded. Confirmation names count and action. Trash retains deleted-only behavior and restoration, not permanent deletion.
|
||||
|
||||
JSON/CSV import/export stays in Settings → Data with a contextual Jobs utility link to that existing function. Preserve B05 bytes/formula safety; do not export only the visible page without explicit labeling.
|
||||
|
||||
## Status semantics and customization
|
||||
|
||||
Current statuses: Saved, Interested, Preparing, Applied, Waiting, Interview, Offer, Rejected, Ghosted, Withdrawn. Keep aliases, raw/custom values, unknown Other fallback and server rules. Board groups are NotApplied, Active and Closed; group-drop destinations Saved, Applied and Rejected remain distinct from precise status choices. Offer is active on the board despite its success analytics category.
|
||||
|
||||
NEW-03 proposes an owner status configuration screen under Settings, reached from Jobs: label, order and explicit mapping to existing system semantics. Until a backend contract exists, keep current free-text/custom behavior and Other group. Do not replace defaults with illustrative Screening/Final Interview/Accepted or auto-map unknown statuses. Rules, analytics and history mapping require a dedicated cross-layer change and regression before UI adoption.
|
||||
|
||||
Favourite/priority is NEW-09: no current JobApplication field was found. Propose a simple owner flag later, default off, independently filterable; do not repurpose Tags, NextAction, operation Priority or status. Defer its control until persistence/ownership and product choice are settled.
|
||||
|
||||
## Quick preview
|
||||
|
||||
NEW-10 creates an optional **read-only** drawer for scanning: role/company, status/dates, short description, next action, CV/document summary and Open full job. Do not embed another full editable seven-tab workspace or a second save queue. Existing ApplicationWorkspace overlay props remain protected but are not evidence of a currently mounted preview.
|
||||
|
||||
Open via explicit row Preview action; role/title link still opens full page. Escape closes and returns focus; opening full page preserves list filters/page/focus context. Mobile may use a full-height preview or go straight to full page if testing shows no benefit; full functionality remains in the full page. No sending, destructive mutation or AI apply inside preview.
|
||||
|
||||
## Validation before migration
|
||||
|
||||
Use PRES-J05/J06/J07 gaps from Phase 2: saved-view CRUD, partial bulk failure, trash restore, identical table/board filtered records, precise versus coarse stage movement, keyboard pickup/drop/cancel and mobile no-drag alternative. Add real App query/back/capture tests, ownership switching and long Bokmål data. Route and table/board owner changes must land together or keep the old entry; never redirect before parity.
|
||||
@@ -0,0 +1,56 @@
|
||||
# Job workspace and guided journey
|
||||
|
||||
ARC-07; PRES-W01–PRES-W12, PRES-J03–PRES-J09, PRES-M01–PRES-M05, PRES-C01, PRES-C05–PRES-C12. Reuse ApplicationWorkspacePage, ApplicationAssets, Attachments, Correspondence, InterviewPrep and the typed applicationWorkspace client.
|
||||
|
||||
## Persistent header
|
||||
|
||||
Show role, company, current status with precise edit action, location, deadline and next action. Secondary metadata: source link, saved/applied date and recorded match summary with source/freshness when available. Main CTA follows the supported next step; Edit job and overflow retain existing controls. Do not automatically start analysis/rendering when opening a page.
|
||||
|
||||
A “Tailored for this job” or “Current CV” label must link to the exact variant. No header claim that a package was submitted because a PDF was downloaded. Favourite awaits NEW-09. On mobile keep title/status/action compact; remaining metadata expands without disappearing.
|
||||
|
||||
## Section ownership
|
||||
|
||||
| Target section | Existing capabilities consolidated | Display and progressive disclosure |
|
||||
|---|---|---|
|
||||
| Overview | JobDetailsSection, ApplicationProgress, nextStep, description/translation, dates and contacts | Summary and one suggested action; expand full source description and contact details |
|
||||
| Match | ApplicationAnalysis, ApplicationMatch, strategy snapshot, reviewed workflow/status suggestions | Source requirements, supported/unknown gaps, explanation; optional AI narrative with review. “Analysis” old key maps here |
|
||||
| Application | ApplicationCvSection/TailoringSection, CoverLetterSection, package drafts and SubmittedPackagesSection | Steps within one section: CV → Letter → Answers → Submission; independent entry, explicit scope and save state |
|
||||
| Documents | Attachments plus references to current CV/letter and immutable packages | Upload/category/AI-use/rename/preview/download/delete; do not copy content into a new store |
|
||||
| Timeline | ApplicationTimeline plus correspondence and follow-up context | Activity / Correspondence subview; filters and compose/import thread actions. Sending remains its explicit review flow |
|
||||
| Notes & tasks | Existing Notes, ApplicationChecklist | Manual/system/dismissed distinction, move controls and progress. Application answers remain in Application, not overwritten into Notes |
|
||||
| Interview | InterviewPrep manual/questions/AI review/readiness/debrief/follow-up | Prep / Debrief disclosure; preserve generated question review, manual edits and source context |
|
||||
|
||||
Keep all seven reachable even before an interview; “Not yet applicable” explains missing context without hiding existing edits. Old CV/cover-letter/checklist/document/timeline/communication links translate per [Route plan](ROUTE_PLAN.md). A logical Timeline merge does not imply all emails and job events already share a backend timeline endpoint.
|
||||
|
||||
Application has four subsection controls, not an enforced wizard or duplicated route tree. Keep per-domain save/dirty boundaries and guards across tab/query changes. Choosing a new CV may reassign a relationship; explain it before performing the existing attach operation. Do not invent many-to-many CV associations.
|
||||
|
||||
## Guided journey without a forced wizard
|
||||
|
||||
| Situation observed | Suggested action | Required guard / alternative |
|
||||
|---|---|---|
|
||||
| Discover/import listing | Review captured fields; then Save job | Preview never creates. URL import retains B01. Manual entry stays available |
|
||||
| Saved job lacks usable description | Add/review source description | No invented facts or auto-submit |
|
||||
| Source available, profile missing/incomplete | Review Career Profile; optionally analyse job independently | Missing information is unknown, not proof of unfitness |
|
||||
| Match available | Inspect supported strengths/gaps, choose/tailor CV | No job requirement silently added to profile |
|
||||
| CV chosen | Prepare letter/answers | User can use existing materials or skip tailoring |
|
||||
| Material prepared | Review and freeze current package; record application | Explicit capture operation; not proof of external delivery |
|
||||
| Applied with date | Set/review follow-up and current reminders | Existing date/rule meanings retained; no automatic real email |
|
||||
| Interview stage | Open preparation and optionally add supported calendar action | Current calendar supports deadline/follow-up; scheduled interview needs NEW data |
|
||||
| Interview completed | Record debrief/outcome and optional follow-up | Do not seed achievements or company facts |
|
||||
| Offer / rejected / withdrawn / other | Review offer/record outcome, retain artifacts/history | Neutral tone; no mandatory goal or stage path |
|
||||
|
||||
Use the existing server nextStep/checklist/workflowSignal as initial source. Do not build a competing client progression engine. A dismissed/manual checklist item stays user-controlled; rerenders and layout changes must not reseed or repeat operations.
|
||||
|
||||
Status change and package capture are separate existing operations. Preserve both; never claim an atomic “Applied + immutable package + external send” transaction exists. Show partial completion and explicit retry without creating duplicate sends/packages. Any new atomic submission behavior needs a separate backend design.
|
||||
|
||||
## Full page versus preview and state
|
||||
|
||||
Full page owns writing, AI review, correspondence send, history restore, package capture and multi-step work. Preview is a summary/navigation aid. Dirty text survives ordinary viewport changes and cancelled navigation. Accepted AI suggestions change only the intended local draft/settings; saving uses its existing API contract. Account switch clears private state and invalidates stale requests even if a dialog was open.
|
||||
|
||||
Existing job IDs are application-read-model identifiers; internal Job linkage does not authorize a route/schema rewrite. Ownership, association and resource missing results stay server-enforced.
|
||||
|
||||
## Migration blockers and proof
|
||||
|
||||
**P2-D01** blocks successful native SQLite tailoring/package capture; fix under its separate ticket before restructuring those sections. Keep its expected-failure oracle visible. F01 lost-update semantics remain separate from B02 identity and creation idempotency; no new autosave/conflict system in this plan.
|
||||
|
||||
Require loaded tests covering all section aliases, draft Cancel/Discard, preserved Notes versus answer drafts, CV attach/detach, immutable historical HTML/letter/binary after live mutation, timeline/status updates, correspondence uncertain-send behavior and interview review. Test keyboard/mobile and both locales/themes; missing/foreign job stays safe. No removal of low-frequency interview/debrief/version/attachment actions for a cleaner overview.
|
||||
@@ -0,0 +1,72 @@
|
||||
# Open decisions and requirement boundaries
|
||||
|
||||
No answer is required to complete this documentation checkpoint. This register makes future dependent work reviewable; proposals are not silent product decisions.
|
||||
|
||||
## Decisions required from Connor
|
||||
|
||||
| ID / decision | Proposal / alternatives | When it affects implementation |
|
||||
|---|---|---|
|
||||
| OD-01 Product name | Keep Jobjakt until chosen. Explore Norwegian-first descriptive vs Scandinavian professional/supportive internationally readable naming; no proposed name is trademark/domain-vetted | Before brand/public-copy rollout; does not block state/focus foundations |
|
||||
| OD-02 Logo/identity | New wordmark + compact mark + favicon in both modes; retain existing mark meanwhile. Avoid generic AI-sparkle identity | Before branded shell assets; no logo generated/selected here |
|
||||
| OD-03 Final primary color | One hue. Current indigo #5B5BD6 is continuity only; muted Nordic blue/teal direction is an untested alternative | Before palette identity sign-off; semantic contrast fixes can use current hue |
|
||||
| OD-04 Dashboard persistence | Recommend owner-scoped device-local layout first; alternative account-synced layout. Both satisfy per-user isolation, only latter follows devices | Before Phase 8 persistence; server option needs API/recovery/migration assessment |
|
||||
| OD-05 Email delivery provider | Existing SMTP architecture remains. Managed transactional provider choice can change deployment/config, not the redesign's ownership of notification/mail flows | Before new email rollout or infrastructure change |
|
||||
| OD-06 External jobs/calendar scope | Preserve NAV and existing Google/Outlook deadline/follow-up + ICS. Decide separately on scheduled interviews, wider event sync or additional providers | Before NEW-06; no LinkedIn integration or auto-apply presumed |
|
||||
| OD-07 Monetisation-specific UX | Retain server Free/Pro capabilities and honest unavailable billing; no invented prices/trial countdown/checkout promises | Before new trial, paywall, pricing or aggregate subscription UI |
|
||||
| OD-08 Favourite vs priority | Recommend optional favourite only initially; richer priority levels need clear user need and persistence semantics | Before NEW-09 schema/API/UI, not a phase-4 prerequisite |
|
||||
| OD-09 Aggregate admin/privacy scope | Start with a small approved total/period set; fixed coarse breakdowns, proposed suppression threshold 10, no individual drill-down | Before NEW-08 API/retention and privacy review; threshold alone does not guarantee anonymity |
|
||||
| OD-10 Job-seeker intent intake | Optional, skippable desired role/work preferences vs retaining only current onboarding checklist | Before NEW-13 profile/personalization storage |
|
||||
| OD-11 Weekly-goal measurement | Recommend optional user-chosen application target, disabled until set; broader effort goals need their own recorded facts | Before NEW-05. No universal default number or punitive state |
|
||||
|
||||
Ordinary route grouping, MUI reuse, current language defaults and current providers are answered by the repository and this scope; they do not require more questions. Current English fallback with EN/NB authenticated preference stays. No implicit change to Norwegian-first market focus or requirement for new users to speak English.
|
||||
|
||||
## Stable new-requirement registry
|
||||
|
||||
NEW IDs do not replace or renumber PRES IDs. “Required” means part of the target brief, not approved to implement in Phase 3.
|
||||
|
||||
| ID | Requirement / classification | Existing boundary / target implementation owner |
|
||||
|---|---|---|
|
||||
| NEW-01 | Dashboard order/resize/reset and persisted layout — required | Five visibility flags already exist; Phase 8, OD-04 |
|
||||
| NEW-02 | Expanded command entities/actions — required, staged by data availability | Jobs/companies + six commands exist; command owner |
|
||||
| NEW-03 | User-configured status definitions/mapping — required target | Raw custom values exist; new server/UI semantics needed before configuration |
|
||||
| NEW-04 | Per-task due dates/reminders — required target | Checklist has no due dates; separate scheduling contract |
|
||||
| NEW-05 | Optional editable/disableable weekly goals — required target | No goal preference exists; OD-11 and period definition |
|
||||
| NEW-06 | Scheduled interviews / broader calendar events — conditional future | Only job follow-up/deadline event actions and ICS proven |
|
||||
| NEW-07 | Shared contextual AI panel/access — required | Existing domain actions/review retained, no general chat engine |
|
||||
| NEW-08 | Aggregate admin product dashboard — required target, metric-qualified | Operational admin exists; new authorized aggregation/definitions, OD-09 |
|
||||
| NEW-09 | Favourite/priority — conditional proposal | No job-level field found; do not reuse operation Priority |
|
||||
| NEW-10 | Active quick-preview host — optional UX improvement | Reusable workspace props exist, production host absent; read-only proposal |
|
||||
| NEW-11 | Bounded cross-job document/task/activity/metric reads — required where target needs them | Existing job-scoped functions are not global query endpoints; separate read projections |
|
||||
| NEW-12 | Manual CV preview zoom — optional incremental control | Automatic fit/page boundaries already exist |
|
||||
| NEW-13 | Intent-led onboarding and unsupported career preferences — conditional proposal | Existing onboarding/completeness protected; no inferred personal facts |
|
||||
| NEW-14 | Comfortable/Compact application density — required | Distinct from current CV document density and table page size |
|
||||
| NEW-15 | New logo/final identity — required logo; rename/color undecided | Keep existing assets/name until OD-01–03 |
|
||||
| NEW-16 | Consistent AI source explanation and unsupported-claim checks — required safety target | Existing review/prompt context is partial evidence, not universal factual grounding/provenance |
|
||||
|
||||
## Contradictions resolved against source
|
||||
|
||||
| Original suggestion / ambiguity | Source-backed resolution |
|
||||
|---|---|
|
||||
| Calendar integration described as wholly future | ApplicationCalendarActions already creates Google/Outlook follow-up/deadline events and ICS. Preserve these; broader scheduled events are new |
|
||||
| Choose email provider as though mail does not exist | SMTP account/reminder delivery plus Gmail/Graph/IMAP connections exist; deployment provider remains open, no replacement here |
|
||||
| “Active applications” and conversion funnel | stats.active = non-deleted jobs; current-stage counts ≠ historical conversions. Use precise catalogue definitions |
|
||||
| Upcoming interviews widget | Interview-prep task/status is not a dated appointment; new schedule data required |
|
||||
| Shared quick overlay already in production | Phase 2 call-site check finds only full-page host. Preserve reusable props; add/test real preview deliberately |
|
||||
| Short CV customization list | Full C08/C09 controls stay under Advanced; no silent removal |
|
||||
| Suggested stages include Accepted/Screening/Final Interview | Preserve ten current stages, Waiting/Ghosted and raw custom values; new mapping needs explicit contract |
|
||||
| Career Profile versus account Profile | /career owns canonical facts; /profile owns identity/security, organized under Settings |
|
||||
| Simplified menu omits mail, companies, offers, reminders/operations | Each has an explicit primary/secondary/utility home; none deleted |
|
||||
| CV “used by jobs” suggests arbitrary many-to-many reuse | Current CvVariant has optional single job reference; attach may repoint, detach preserves CV |
|
||||
| API metadata implies native package success | P2-D01 capture/tailoring fails on SQLite; expected failure is not frozen-package proof |
|
||||
| Earlier Phase 1 docs say TypeScript gate missing | Phase 2 added gate; TS2571 corrected earlier. Remote gate execution still unverified |
|
||||
| Phase 2 C06 gap row calls the preview issue F15 | The validated accessibility finding and queue A01–A03 are F14; use F14 here. Preserve the historical row rather than renumbering audit findings |
|
||||
| Phase 1 describes TanStack Table as used | Dependency exists, but current src search finds no @tanstack/useReactTable/useTable import or call. JobTable uses MUI Table directly; preserve its actual owner, not an assumed engine |
|
||||
| Latest brief mentions pre-Phase-4 layout work | Phase 4 remains shared foundations; broad shell/screens are Phase 5 after contracts/gates |
|
||||
|
||||
## Separately recorded baseline debt
|
||||
|
||||
**P3-O01 — analytics presentation semantics, source-confirmed limitations.** Dashboard currently labels non-deleted tracked count as active applications, an interview-prep count as upcoming, and uses datasets with different windows. Source: DashboardView, AnalyticsService, JobApplicationAnalyticsController. Future chart migration must use definitions in [Dashboard architecture](DASHBOARD_ARCHITECTURE.md), explicitly separate snapshots/cohorts/periods and avoid summing truncated breakdowns. This is not a new production incident or a fix performed in Phase 3. Aggregate data quality and timezone corrections remain separately scoped.
|
||||
|
||||
**P3-O02 — navigation metadata retention, source observation.** ApplicationWorkspace go() replaces search with only section, so followMode may be lost; QuickCommandDialog maps fetch failure to empty results. Preserve current successful workflows but target explicit query retention and error states when those owners migrate. No incident, severity escalation or implementation is claimed.
|
||||
|
||||
Keep [P2-D01/P2-O01 and intentional gaps](../phase-2/BASELINE_DEFECTS.md) separate. F01/data concurrency, D04 creation idempotency, timezone, storage/recovery, billing and worker/release issues retain the [validated queue](../../audits/2026-09-07/validation/implementation-queue.md) owners. No schema before restore/rollback readiness. **F04 remains open** pending actual ingress runtime/production evidence; no operator/credential action was taken in this phase.
|
||||
@@ -0,0 +1,88 @@
|
||||
# Phase 4 implementation plan
|
||||
|
||||
**Planning only. Phase 4 has not started.** This package is a documentation checkpoint from d6d3dd9. The next phase establishes shared foundations; broad navigation/layout migration stays Phase 5 under the original redesign sequence. No B07 work is included.
|
||||
|
||||
## Entry conditions
|
||||
|
||||
- Phase 3 route/impact plan is the reviewed working contract; retain all 57 PRES IDs and 31 existing patterns.
|
||||
- Current baseline is available: 916 backend, 313 frontend; general browser **23 pass + 1 documented expected failure**. No tests/gates removed.
|
||||
- Select the exact shared consumer/state fixture before editing. Gaps in [Phase 2](../phase-2/BASELINE_DEFECTS.md) remain explicit.
|
||||
- Brand, providers and cross-device layout decisions do not block the first semantic accessibility slice. Keep current identity and storage behavior.
|
||||
- No schema or persistence redesign here. R03 restore/rollback proof gates schema; D01–D03 govern editor/job revision semantics. B02 identity and creation idempotency remain distinct.
|
||||
- Local foundation work can proceed without production access. Production rollout still needs required CI and F04 ingress evidence; a feature-branch push is not deployment approval.
|
||||
|
||||
## Session-sized foundation queue
|
||||
|
||||
| Ticket / scope | Owned surface and dependencies | Regression/UX evidence | Risk / rollback |
|
||||
|---|---|---|---|
|
||||
| **P4-01 Semantic state and focus foundation** | Existing theme.ts; narrowly required theme typing/shared MUI overrides; existing browser/Jest fixtures. Coordinate with validated A01, do not duplicate it | Loaded button/chip/tab/field/alert state pairs in both modes; visible keyboard focus; preserve filled-button contrast and EN/NB labels | Broad visual reach, no schema. Revert this isolated theme/test slice if necessary; no data migration |
|
||||
| **P4-02 Named controls and modal state** | RichTextField/actual unlabelled Select call sites plus confirm/prompt/ViewStateNotice as evidenced. After P4-01; inventory callers first | Labels/helper/error links, draft retained on error, dialog focus/return, loading announcements; no mass form rewrite | Small caller changes; revert per shared primitive, retain all behavior tests |
|
||||
| **P4-03 Builder preview keyboard boundary** | Actual preview region in CvBuilderEditor and focused browser fixture; coordinate validated A02. Serialize with D01; no editor save refactor | Loaded one/multipage preview, keyboard entry/scroll/exit and mobile→desktop transition; edit/preview/undo state retained | Touches stateful editor; stop if change requires persistence redesign. No schema |
|
||||
| **P4-04 Page layout and typography primitives** | Theme/page variables plus smallest PageHeader/PageSection composition needed by existing consumers. After P4-01/02; use current hue/mark | One h1, long NB copy, 320 px reflow, reading/data/editor width, no hidden actions | Limit to one representative existing consumer, not all pages; revert primitive/consumer together |
|
||||
| **P4-05 Table/list density contract** | Theme Table styles and a bounded existing table consumer; typed Comfortable/Compact preference scoped explicitly. After P4-04 | Row selection/link/action isolation; readable values at both densities; touch hit regions; existing column/page prefs retained | No replacement table library. If preference API/schema is needed, separate that decision instead of broadening this slice |
|
||||
| **P4-06 Shared validation checkpoint** | Tests/docs only plus separately ticketed defects; after combined foundations | Loaded EN/NB × light/dark × mobile/desktop, keyboard/manual preview/form, full suites/type/lint/build and PRES traces | Do not mask failures. Foundation accepted before Phase 5 shell/pages |
|
||||
|
||||
Do not scaffold every component in COMPONENT_ARCHITECTURE.md during Phase 4. Command expansion, aggregate dashboards, document query APIs, status settings, scheduled tasks and full AI panel are later feature slices, not required to establish tokens/names/focus. A shared AI diff frame can be extracted when the first domain migrates and its validation remains intact.
|
||||
|
||||
## First implementation handoff: P4-01 only
|
||||
|
||||
Problem: F14 identified semantic small-text contrast and focus debt across shared states. Current theme and shell/page literals can produce inconsistent pairings; replacing MUI is not required.
|
||||
|
||||
Objective: make the chosen existing MUI state pairs readable and keyboard focus clear in light/dark, using the current provisional brand hue. Inspect actual rendered default/hover/focus/selected states for Chips, outlined/contained Buttons, Tabs and Alerts. If a failure lives in one local hardcoded style, include only that directly responsible override with caller evidence.
|
||||
|
||||
Start with theme.ts and existing theme/accessibility test owners. Add a populated fixture through the existing test app/environment; no new public test route, component gallery framework or production data. Verify real foreground/background/icon/focus pairs. Preserve labels, action outcomes and enabled/disabled behavior. Do not merely test that token names exist or choose new arbitrary global colors.
|
||||
|
||||
**Exclude:** App route/provider changes, navigation grouping, sidebar rewrite, dashboard cards/layout, CV save/preview extraction (separate P4-03), final logo/color/font choice, API/schema, dependencies, billing, B07. Do not silently bundle all of A01–A03.
|
||||
|
||||
Acceptance:
|
||||
1. Original targeted contrast/focus failure reproduced or explicitly matched to prior evidence; fixed at the responsible shared layer.
|
||||
2. Representative loaded fixtures verify both themes and active states, including no regression to filled-button foregrounds.
|
||||
3. Keyboard focus visible; names/semantics/actions preserved in EN/Bokmål.
|
||||
4. Related Jest/browser checks, standalone TypeScript, lint and production build pass; full frontend suite remains at least the unchanged 313 plus intentional additions.
|
||||
5. Backend/B01–B05 contracts unchanged; execute relevant suite at checkpoint if shared tooling/API changes occur. Do not claim fresh full backend run without executing it.
|
||||
6. Document actual PRES-E08 and affected consumer evidence, source/contrast measurement, changed files and any remaining manual gaps. Commit separately, review before P4-02/next surface.
|
||||
|
||||
## Foundation stop conditions
|
||||
|
||||
Stop the affected slice if it requires a new component library, HTTP/auth change, schema, broad state rewrite or unresolved product semantics. Do not expand a theme fix into routing or all page styling.
|
||||
|
||||
Do not proceed to broad representative migration with failing named/focus/contrast states. P2-D01 must be independently repaired and successful native package/archive tests obtained before package/tailoring restructuring. Do not co-edit CvBuilderEditor with D01, even if one change seems visual. A mounted save queue remains insufficient against stale browsers.
|
||||
|
||||
No hiding functions, test exclusions, CSS overflow clipping or broad axe suppression to create apparent parity. Unexpected known-baseline recurrence is recorded separately, with affected work paused as necessary.
|
||||
|
||||
## Later sequencing, without starting it
|
||||
|
||||
1. Review P4 foundation evidence.
|
||||
2. Phase 5 shell/navigation grouping, retaining existing routes/provider tree; add drawer/account/command gap tests first.
|
||||
3. Jobs Table/Board owner and /kanban alias in one scoped migration after filter/query parity. Keep discovery/companies/offers/reminders reachable.
|
||||
4. Existing-data dashboard/Analytics presentation with accurate definitions. New metrics do not block relocating already available charts.
|
||||
5. Job workspace sections **after** package/native and relevant integrity gates; CV editor **after** revision/focus gates. Keep mail-send owner isolated.
|
||||
6. Phase 6 review, then Phase 7 remaining routes using each PRES trace.
|
||||
7. Phase 8 customization/new data requirements only after relevant product decisions and backend/recovery readiness.
|
||||
8. Full QA/release evidence; cleanup only with proven unreferenced code and explicit preservation sign-off.
|
||||
|
||||
## Safe coordination
|
||||
|
||||
Theme fixture planning and backend baseline defect investigation can be independent if separately authorized and owned. Source/metric definition documentation can proceed independently from UI primitives. Do not concurrently mutate theme.ts or App.tsx from several visual sessions.
|
||||
|
||||
Serialize route helper/App/private-tree changes; serialize table/board integration at its shared owner. Serialize D01 with preview/editor extraction. Serialize document index work with package persistence changes only after their contracts settle. Mail send/draft state is never a generic document-form refactor.
|
||||
|
||||
No backend security queue is automatically authorized by this planning sequence. F04 and B07 retain their existing scope/approval boundaries.
|
||||
|
||||
## Phase 3 checkpoint validation
|
||||
|
||||
Method: inspect the current application source and model/controller contracts; compare against Phase 1 full ledger/routes and Phase 2 assertion/gap mapping. Read the product specification package. Validate local Markdown/source links, complete ID/route coverage, new-requirement catalogue, representative existing test names and documentation-only Git diff. No rendered visual prototype or production visit was necessary to validate a documentation-only plan.
|
||||
|
||||
Commands were run from repository root using PowerShell/Python/Git. Full application suites were not rerun solely for prose changes; their unchanged Phase 2 evidence is reused with that limitation. Source-backed observations P3-O01/P3-O02 are recorded, not repaired.
|
||||
|
||||
| Executed command / review | Result |
|
||||
|---|---|
|
||||
| git switch -c codex/ui-redesign-phase3 d6d3dd9 | Dedicated branch created at the requested clean checkpoint |
|
||||
| python - (inline document/PRES/route/link validator) | 19 required deliverables; 57 unique PRES rows exactly match the original ledger; 31 routes exactly match current App.tsx; 16 ARC and 16 NEW definitions; 39 widget IDs; all 73 local package links resolve |
|
||||
| python - (inline Markdown table and named-test checks) | Balanced fences and consistent table columns; named existing regression references checked against Phase 2/current test files |
|
||||
| rg / Get-Content current source and model review | Confirmed route/query/provider boundaries, current statuses, canonical/variant relationship, widget field availability and source-backed limitations; corrected draft references before completion |
|
||||
| git diff --check and git diff --cached --check | Passed; no whitespace errors |
|
||||
| git diff --cached --name-only / --stat | 22 Markdown files only: 19 package files, root index, traceability link and TODO; no app/test/build/CI/schema changes |
|
||||
| python scripts/supply-chain.py scan-secrets | Passed on the staged documentation; no high-confidence credential patterns found |
|
||||
|
||||
This proves architecture-document completeness and consistency with inspected source. It does not prove a future migration, manual usability, AI factual quality, provider operation, remote CI or production ingress. Commit/push status is reported with the final checkpoint SHA; no deployment is performed.
|
||||
@@ -0,0 +1,106 @@
|
||||
# Preservation impact and traceability
|
||||
|
||||
Every row preserves the **complete original capability group**, not just the shorthand below. Authority: [Phase 1 ledger](../audit/FUNCTIONALITY_INVENTORY.md), [Phase 2 tests/gaps](../phase-2/PRESERVATION_MATRIX.md) and [traceability contract](../phase-2/TRACEABILITY.md). All 57 IDs retain meaning. No deprecation is proposed.
|
||||
|
||||
## Architectural recommendation index
|
||||
|
||||
| Recommendation | Planned change / existing behavior retained | Affected groups | Phase 4 or later validation |
|
||||
|---|---|---|---|
|
||||
| ARC-01 [Information architecture](INFORMATION_ARCHITECTURE.md) | Group current capabilities, retain every low-frequency destination | All 57 | Full destination ledger and role visibility; no removed function |
|
||||
| ARC-02 [Routes](ROUTE_PLAN.md) | Keep 31 patterns; staged Board alias and precise old section mapping | E01–E09, J01–J10, W01–W12, C01–C12, M01–M06, S01–S05, A01–A03 | Real App entries/back/refresh/capture/dirty/account switch |
|
||||
| ARC-03 [Shell](APP_SHELL.md) | Reuse collapse/drawer/commands/private-tree lifetime | E07–E09, S02–S04, A01–A03 | Focus, current parent, identity disposal, theme/locale |
|
||||
| ARC-04 [Personal dashboard](DASHBOARD_ARCHITECTURE.md) | Preserve current charts/visibility; data-qualified expansion | S01, S02, W02–W12, C05 | Exact metric denominators/source; owner layout and nonavailable states |
|
||||
| ARC-05 [Admin dashboard](DASHBOARD_ARCHITECTURE.md) | Separate new aggregate view from current admin actions | A01–A03, S04 | Server authorization/aggregate-only response; no individual drill-down |
|
||||
| ARC-06 [Jobs](JOBS_WORKSPACE.md) | Table/Board one view owner; existing filters/statuses/bulk retained | J01–J10, W01, S03 | Saved views, filtered parity, partial failure, restore, keyboard |
|
||||
| ARC-07 [Job workspace](JOB_WORKSPACE.md) | Consolidate sections without changing artifact/send ownership | W01–W12, M01–M05, C05–C12 | Native package success, source relationships, dirty/send/history |
|
||||
| ARC-08 [Career](CAREER_PROFILE_UX.md) | Explicit canonical source and import review | C01–C04, C07, C10, C11, E06, E09 | Source/override/reset, import accept/discard, owner denial |
|
||||
| ARC-09 [CV](CV_WORKSPACE.md) | Clean editor/preview and advanced disclosure, full controls retained | C05–C12, W05, W07 | Pagination/preview focus, history, AI no-write, canonical isolation |
|
||||
| ARC-10 [Documents](DOCUMENTS_UX.md) | Index existing artifacts; no replacement store | W05–W08, C05–C12, M04, S05 | Owner list/download/attach, current vs frozen, immutable bytes |
|
||||
| ARC-11 [AI](AI_INTERACTION_MODEL.md) | Contextual reviewed suggestions with explicit target | W03, W05, W06, W09, W10, C03, C04, C11, S04, E09 | Accept/reject, stale/malformed/context switch, source eval |
|
||||
| ARC-12 [Commands/notices/tasks](COMMANDS_NOTIFICATIONS_TASKS.md) | Retain command, reminder, inbox and provider distinctions | E07–E09, J01–J04, J08, W04, W11, W12, M01–M06, S02–S04 | No-write command, task vs notice, real send safeguards |
|
||||
| ARC-13 [Responsive](RESPONSIVE_STRATEGY.md) | Adapt existing mobile workflows without losing features | All 57 | Breakpoint dirty/focus preservation; real touch/zoom |
|
||||
| ARC-14 [Design system](DESIGN_SYSTEM_ARCHITECTURE.md) | Refine MUI tokens/states, keep stack/identity | All 57; E08 shared owner | Loaded mode/locale/contrast/state fixtures |
|
||||
| ARC-15 [Components](COMPONENT_ARCHITECTURE.md) | Small extractions with domain state kept intact | All 57 | Consumer regression; no duplicated network/save owner |
|
||||
| ARC-16 [Accessibility](ACCESSIBILITY_PLAN.md) | Structural focus/naming/contrast first | All 57 | Loaded axe + keyboard + manual assistive technology |
|
||||
|
||||
Ranges above use existing PRES aliases (e.g. E07 = PRES-E07); they never define new IDs. New capabilities use NEW-01–NEW-16 in Open decisions. Their presence does not count as implemented preservation.
|
||||
|
||||
## 57-group change-impact matrix
|
||||
|
||||
“Retained” = **yes, required by this plan**, not a claim that a migration has executed. Baseline test names below identify representative Phase 2 evidence; the linked Phase 2 row includes exact paths, other tests and known limits. New verification described here is work for the phase touching that surface. Phase 4 only exercises relevant shared foundations; it does not restructure all these workflows.
|
||||
|
||||
| PRES ID | Existing behavior → proposed UX / destination | Retained? / impact | Representative existing evidence → required migration proof |
|
||||
|---|---|---|---|
|
||||
| PRES-E01 | Product/Free–Pro/unavailable billing → public /, later brand presentation | Yes; public copy later | landing-page, planCatalog → EN/NB/mobile/locked availability, no invented purchase flow |
|
||||
| PRES-E02 | Login/register/remember/reset/verify → same public routes, shared form states | Yes; shared field impact | login-page, verify-email-page, LocalAuthIdentityTests → loaded errors, token submit, safe redirect/provider config |
|
||||
| PRES-E03 | Provider login/link/relink → same routes under account entry | Yes; no provider redesign | microsoft-legacy-relink-page, GoogleTokenValidatorTests, MicrosoftTokenValidatorTests → real sandbox popup/origin/revoke/relink |
|
||||
| PRES-E04 | 2FA/recovery/trusted device → Settings security at existing /profile | Yes; nested form preservation | two-factor-settings, TwoFactorControllerTests → focus and full recovery/revoke traversal |
|
||||
| PRES-E05 | Sessions/revoke/logout → Settings security and account menu | Yes; high-risk shell lifetime | SessionsControllerTests, account-isolation browser → actual session card/revocation + private disposal |
|
||||
| PRES-E06 | Avatar/name/email/password → /profile under Settings Account | Yes; distinct from Career Profile | profile-page, AvatarStorageTests → upload/remove/password/email-change and cross-account denial |
|
||||
| PRES-E07 | Collapse/mobile/active nav/commands → grouped shell, expanded existing palette | Yes; first shell migration | sidebar-active-nav, quick-command-preservation, browser keyboard → every logical parent, drawer focus, collapse/dirty preferences |
|
||||
| PRES-E08 | Theme/EN–NB/feedback/error routes → semantic tokens and common states | Yes; Phase 4 direct impact | theme-state, i18n-provider, confirm/prompt → loaded schemes/locales/reduced motion/error route |
|
||||
| PRES-E09 | Account-switch/stale read/write/BFCache handling → unchanged boundary for all new surfaces | Yes; mandatory regression | session-boundary, SessionContextMiddlewareTests, account-isolation → stale command/panel/draft/results cannot cross identity |
|
||||
| PRES-J01 | NAV discovery/filter/source details → Jobs Discover at /discover | Yes; relocate navigation | job-discovery, JobDiscoveryControllerTests → loaded search/error/mobile; NAV production availability separate |
|
||||
| PRES-J02 | Saved search/run/delete/alerts/dismiss → same Discover workspace | Yes; no new store | job-discovery, SavedJobSearchAlertTests → delete/alert-to-centre/reload and owner isolation |
|
||||
| PRES-J03 | Manual/URL/paste preview/company/tags/date create → shared Add/import action | Yes; reviewed create unchanged | quick-capture, JobImportHttpTransportTests → preview no write, duplicate/company/date failure; B01 intact |
|
||||
| PRES-J04 | Extension/bookmarklet/share + post-create artifacts → same capture contract | Yes; route sensitivity | captureUrl, quick-command-preservation, extension tests → real capture/review/optional attachment failure and no replay create |
|
||||
| PRES-J05 | Table/cards/filter/sort/page/columns/saved views → Tracked Table/Board | Yes; high-risk view owner | daily-control-loop, account-scoped-state, workspace browser → saved-view CRUD, filter parity/back/focus, long NB cards |
|
||||
| PRES-J06 | Edit/bulk status/delete/trash/restore → same actions and /trash utility | Yes; no hard-delete substitution | JobApplicationsAuthorizationTests, confirm-flow → native partial bulk failure, restore, selected scope |
|
||||
| PRES-J07 | Grouped pointer/keyboard board + exact status → /jobs?view=board after parity | Yes; delayed alias | kanban-grouped-board, pipeline → same filtered IDs, keyboard cancel and unknown custom group |
|
||||
| PRES-J08 | Company/contact/pipeline/date/related jobs → Jobs Companies, /companies?edit=id | Yes; no lost directory | companies-relationship, CompanyRelationshipTests → full contact persistence and command entry |
|
||||
| PRES-J09 | Offer compensation/decision/notes/source links → Jobs Offers at /offers | Yes; no calculator rewrite | offer-comparison, AnalyticsSalaryTests → many-offer mobile, currency/period and source links |
|
||||
| PRES-J10 | CSV/JSON export/import/conversion/counts → Settings Data plus Jobs link | Yes; formats unchanged | CsvExportTests, csv-export/browser → BOM/typed dates/formulas and native import counts, no full-restore claim |
|
||||
| PRES-W01 | Full workspace/aliases/optional props → new section map + optional read-only host | Yes; no active preview assumed | application-route-contracts, application-workspace-overlay, actual App browser → every alias, followMode, dirty/back/focus and new host |
|
||||
| PRES-W02 | Details/progression/next action/dates/contacts/history → header/Overview/Timeline | Yes; same records/stages | workflow-trust-signals, JobApplicationsAppliedDateHistoryTests → native edit/status/history, null applied date |
|
||||
| PRES-W03 | Analysis/match/strategy/reviewed status suggestions → Match section | Yes; context explained | application-intelligence, application-workflow-assist → loaded provider/error/source/freshness and explicit apply |
|
||||
| PRES-W04 | Checklist CRUD/dismiss/complete/order/next step → Notes & tasks | Yes; due date remains new | application-checklist, ApplicationChecklistTests → keyboard/mobile persisted actions, manual vs auto |
|
||||
| PRES-W05 | Select/attach/create/tailor CV → Application → CV | Yes; relationship unchanged | application-assets, ApplicationAssetsTests → source context, foreign attach denied; native tailoring blocked by P2-D01 |
|
||||
| PRES-W06 | Letter/manual/AI review/history/dirty guard → Application → Letter | Yes; independent draft/save | application-assets AI reject, ApplicationAssetsTests → whole-browser accept/reject/restore/Cancel/Discard |
|
||||
| PRES-W07 | Answers/drafts/frozen packages/archived downloads → Application → Submission + Documents history | Yes; migration blocked | SubmittedApplicationPackageTests; browser expected failure → **P2-D01 native capture and post-source-mutation archived bytes required** |
|
||||
| PRES-W08 | Upload/drop/purpose/name/AI use/preview/download/delete → Documents section/index | Yes; owner-bound binary | attachments, AttachmentConsistencyTests → native rename/drop/download/delete; archived survival after W07 fix |
|
||||
| PRES-W09 | Manual/AI interview questions/answers/ready/remove → Interview Prep | Yes; explicit Add/review | interview-prep, InterviewPrepPersistenceTests → mobile keyboard/reload and no invented answer facts |
|
||||
| PRES-W10 | Debrief/follow-up draft/date/readiness → Interview Debrief | Yes; no scheduled meeting inferred | interview-prep, JobApplicationsFollowUpDraftTests → persisted debrief and followMode navigation |
|
||||
| PRES-W11 | Rules/reminders/notifications/ICS/Google/Outlook → Follow-ups + job calendar controls | Yes; supported providers retained | application-calendar, settings-view, ApplicationCalendarControllerTests → permission/ICS/timezone + provider sandbox; new event scope separate |
|
||||
| PRES-W12 | Operation pending/progress/fail/retry/cancel and notices → /operations utility + centre | Yes; operation identity retained | operations-page, OperationsControllerTests → no duplicate starts, result links/cancel/late response |
|
||||
| PRES-C01 | Full canonical profile and long-tail sections → Career Profile Edit | Yes; global scope explained | profile-page, CareerProfileControllerTests, account-isolation/browser → same-account save, A/B replay denial, all sections |
|
||||
| PRES-C02 | Overview/completeness/raw text/avatar/history/restore → Career overview/history | Yes; not a new score | career-workspace-page, CareerProfileServiceTests → native restore/projection, copy/raw accessibility |
|
||||
| PRES-C03 | Extract/rebuild/improve/reprocess/diff/low confidence/accept/discard | Yes; Import review workspace | profile-page, CvProfileDiffServiceTests, CvExtractionCoverageTests → loaded low-confidence/discard/cancel/provider failure; actual extraction corpus |
|
||||
| PRES-C04 | Sourced evidence CRUD/tags/truthfulness → Career Evidence | Yes; no invented skill bank | career-evidence, CareerEvidenceControllerTests → edit context/delete/owner isolation and source navigation |
|
||||
| PRES-C05 | CV library/create/copy/delete/gallery/publish/share/PDF → CVs | Yes; same IDs/slugs | cv-builder-page, CvBuilderTests/PublicCvControllerTests → template controls, publication lifecycle and owned links |
|
||||
| PRES-C06 | Studio tabs/live preview/fit/page/save/mobile modes → focused editor/preview | Yes; high-risk visual owner | cv-builder-deep-link, redesign-preservation browser → loaded preview focus/scroll, modes without remount |
|
||||
| PRES-C07 | Item/section selection/order/override/custom content → scoped section editor | Yes; all controls | cv-builder-deep-link, cvBuilder, canonical/sibling browser → reset/inherit/missing-source/reorder/hide |
|
||||
| PRES-C08 | Template-aware typography/header/skills/layout/photo/icons → Customize + Advanced | Yes; no control dropped | cv-builder-deep-link, cv-template-thumbnail, CvBuilderTests → supported/unsupported values and preview/PDF equivalence |
|
||||
| PRES-C09 | A4/Letter/density/margins/dates/language/presentations/columns → Advanced document controls | Yes; app density separate | cvBuilder, CvBuilderTests, existing multipage PDF browser → real multipage/grid/bubble cases in both document locales |
|
||||
| PRES-C10 | Undo/redo/save queue/dirty/history/restore → persistent editor state | Yes; F01 remains separate | cv-builder-deep-link, CvBuilderTests → browser history/undo/reload/failed save; no concurrency overclaim |
|
||||
| PRES-C11 | Section/document AI translate/improve/spelling/review → shared comparison frame | Yes; accept/reject retained | ai-section-assistant, cv-builder-deep-link → malformed IDs, changed source, rejected suggestion no mutation |
|
||||
| PRES-C12 | Private and published PDF/preview/searchable long docs → same export/public path | Yes; B03 preserved | PublicCvControllerTests, PdfRenderAdmissionTests → private denial, unpublish, all-render paths/busy recovery |
|
||||
| PRES-M01 | Job manual correspondence/search/delete/paste/import → Timeline Correspondence | Yes; log ≠ send | end-to-end-trust-loop, CorrespondenceControllerTests → current-job context and manual record mutation |
|
||||
| PRES-M02 | Gmail search/import/refresh/thread link/unlink/move → job Correspondence/inbox | Yes; relationship checks | correspondence-gmail-import, EmailOwnershipIntegrationTests → foreign thread/job denial and provider reconnect |
|
||||
| PRES-M03 | Global inbox/filter/paging/message/attachment info/job links → primary Correspondence | Yes; not hidden in Documents | correspondence-inbox-page, EmailControllerTests → native paging/detail/empty vs provider failure |
|
||||
| PRES-M04 | Compose/reply/provider/drafts/review/send/attempt uncertainty → same inbox domain | Yes; high-risk send boundary | EmailDraftPersistenceTests, EmailSendAttemptStoreTests → draft conflict, explicit send, unknown delivery, no auto-resend |
|
||||
| PRES-M05 | Review candidates/proposals/link/reject/keep/notes/sync/create → inbox Review | Yes; legacy alias retained | gmail-review-page, GmailControllerTests → old route/result/link/create confirmation and owner scope |
|
||||
| PRES-M06 | Google/Graph/IMAP status/connect/disconnect → Settings Connections | Yes; login vs mailbox distinction | email-provider-connections, provider tests → actual grants/reconnect/disabled capability; no unsupported send |
|
||||
| PRES-S01 | Counts/activity/funnel/company/tag/stage/salary/next steps → Dashboard + Analytics | Yes; precise labels, no fabricated metrics | daily-control-loop, StageAnalyticsTests → P3-O01 definitions, period/unknown/sample/error and data table |
|
||||
| PRES-S02 | Five owner visibility flags/onboarding/dismiss/bell/read/dismiss → layout migration + centre | Yes; new layout additive | onboarding-checklist, notifications-popover → preference migration/A-B/reset/corrupt storage before Phase 8 |
|
||||
| PRES-S03 | Rules/email/table/theme/language/preferences → Settings sections + context links | Yes; scopes retained | settings-view, browser responsive save → scenario fields/error retry/resize and separate document density |
|
||||
| PRES-S04 | AI privacy/usage/limits/Free–Pro/billing status/checkout/portal → Settings AI/plan | Yes; server authority | ai-usage-card, ProEntitlementAuthorizationTests, BillingControllerTests → honest unavailable/provider/entitlement, no invented trial |
|
||||
| PRES-S05 | Account export/encrypted backup/lifecycle/delete confirmation → Settings Data/privacy | Yes; recent auth retained | account-data-export, AccountDeletionTests, BackupControllerTests → safe confirmation/download and restore-readiness gap explicit |
|
||||
| PRES-A01 | Admin users/create/roles/reset/delete/last-admin protections → Admin Users | Yes; aggregate view does not replace tools | admin-users-page, UsersControllerTests, nonadmin browser → role revocation/denial/confirmation and no user-data analytics |
|
||||
| PRES-A02 | Audit list/detail/supported undo/job restore → Admin Audit | Yes; exact supported actions | admin-audit-page → native undo/restore/owner and confirmation; not generic mutation |
|
||||
| PRES-A03 | System health/build/database/AI/email/config/test/benchmark/maintenance → Admin System | Yes; separate from product counts | admin-system-page, MaintenanceJobDispatcherTests → privileged actions retained; secrets not in dashboard |
|
||||
|
||||
## Trace chain and readiness
|
||||
|
||||
For every subsequent change record:
|
||||
|
||||
**PRES-ID + original sub-workflow → ARC/NEW requirement → implementation commit and owner → named executed regression → visual/UX evidence → remaining gaps.**
|
||||
|
||||
Use a scoped trace sheet linked from [Phase 2 traceability](../phase-2/TRACEABILITY.md); the table above is planning impact only. Example, not completed work:
|
||||
|
||||
| PRES / requirement | Architecture | Implementation | Regression | Visual/UX |
|
||||
|---|---|---|---|---|
|
||||
| PRES-E08 accessible semantic states | ARC-14/16; P4-01 | Not started | Existing theme/feedback tests plus planned loaded contrast/focus fixture | Not performed |
|
||||
| PRES-J07 unified Board entry | ARC-02/06 | Not started, Phase 5 | Filtered parity, exact status/keyboard cancel and /kanban alias | EN/NB, themes, phone/desktop/touch pending |
|
||||
| PRES-W07 frozen package | ARC-07/10 | Blocked by P2-D01 | Native capture currently expected failure; post-capture assertions unproven | No migration approval |
|
||||
|
||||
**57/57 groups mapped, zero approved removals.** This is 100% architecture traceability, not 100% automated workflow coverage or implementation readiness. Phase 2 contains explicit provider, production, accessibility, visual and native SQLite gaps. Preserve them until evidence closes them.
|
||||
@@ -0,0 +1,53 @@
|
||||
# Phase 3 — UX architecture checkpoint
|
||||
|
||||
Based on **d6d3dd9**, on **codex/ui-redesign-phase3**, 2026-09-10. This package defines the target architecture; it does not implement it. No application code, routes, styling, APIs, schema, dependencies or CI configuration change in this phase. Phase 4 and B07 have not started. **B06 implementation complete; F04 remains open.**
|
||||
|
||||
## Authority and reading order
|
||||
|
||||
The [product brief](../ASTRA_HANDOFF.md), [original design direction](../MASTER_REDESIGN_SPEC.md), [Phase 1 full functionality ledger](../audit/FUNCTIONALITY_INVENTORY.md) and [Phase 2 preservation matrix](../phase-2/PRESERVATION_MATRIX.md) remain authoritative. This package resolves presentation choices using current source. It never replaces a PRES contract with its shorter summary. Later user instructions govern any conflict with the original illustrative brief.
|
||||
|
||||
| Document | Decision it supplies |
|
||||
|---|---|
|
||||
| [Information architecture](INFORMATION_ARCHITECTURE.md) | Grouped navigation and where every less-visible capability lives |
|
||||
| [Route plan](ROUTE_PLAN.md) | All 31 existing patterns, aliases, query/state contracts and staged additions |
|
||||
| [Application shell](APP_SHELL.md) | Existing shell reuse, account boundaries, headers and navigation behavior |
|
||||
| [Dashboards](DASHBOARD_ARCHITECTURE.md) | Personal layouts, data-qualified widget catalogue and separate aggregate admin |
|
||||
| [Jobs workspace](JOBS_WORKSPACE.md) | One table/board workspace, filters, statuses, bulk operations and preview |
|
||||
| [Job workspace](JOB_WORKSPACE.md) | Section ownership and optional guided application journey |
|
||||
| [Career Profile](CAREER_PROFILE_UX.md) | Canonical editing, extraction review and source propagation |
|
||||
| [CV workspace](CV_WORKSPACE.md) | Editor/preview, source overrides, advanced controls and history |
|
||||
| [Documents](DOCUMENTS_UX.md) | Federated discovery of existing artifacts and frozen relationships |
|
||||
| [AI interaction](AI_INTERACTION_MODEL.md) | Grounding, explicit review, destination scope and provider failures |
|
||||
| [Commands, notifications and tasks](COMMANDS_NOTIFICATIONS_TASKS.md) | Contextual commands and distinct task/event/message lifecycles |
|
||||
| [Responsive strategy](RESPONSIVE_STRATEGY.md) | Mobile task behavior and density |
|
||||
| [Design system](DESIGN_SYSTEM_ARCHITECTURE.md) | MUI tokens, states and bounded visual proposals |
|
||||
| [Component architecture](COMPONENT_ARCHITECTURE.md) | Retain/refactor/consolidate/add map |
|
||||
| [Accessibility](ACCESSIBILITY_PLAN.md) | Loaded-state and manual gates before repeating shared defects |
|
||||
| [Preservation impact](PRESERVATION_IMPACT_MATRIX.md) | All 57 contracts, recommendations and implementation evidence chain |
|
||||
| [Open decisions](OPEN_DECISIONS.md) | Genuine product choices, contradictions and unavailable data |
|
||||
| [Phase 4 plan](PHASE4_IMPLEMENTATION_PLAN.md) | Small foundation tickets, dependencies and first slice |
|
||||
|
||||
## Scope classification
|
||||
|
||||
- **Existing / preserve:** all 57 PRES groups, including advanced CV controls, NAV alerts, correspondence delivery safeguards, owner-bound artifacts, Google/Outlook calendar actions, public CVs, account security and admin operations.
|
||||
- **Existing / improve UX:** grouped navigation, one Jobs view switch, clear job sections, source/override labels, coherent document entry, discoverable settings, shared error/focus presentation.
|
||||
- **New:** explicitly numbered NEW requirements in [Open decisions](OPEN_DECISIONS.md), such as dashboard layout order/size, broader commands, density, aggregate admin analytics and due-dated tasks. Availability and implementation phases differ; a candidate metric is not an available feature.
|
||||
- **Baseline defects / debt:** P2-D01 SQLite package/tailoring failure; F14 loaded accessibility; separate concurrency, idempotency, calendar and paid-lifecycle queues; failed remote CI browser runner; F04 runtime ingress evidence. Do not fix these incidentally or preserve their defective results as desired behavior.
|
||||
|
||||
## Selected architecture
|
||||
|
||||
Retain React Router inside the Next static SPA, MUI/Emotion, the existing auth/private-tree lifecycle and shared Axios client. Reorganize navigation without changing most paths. Keep a full job page and a focused optional read-only preview. Career Profile remains canonical; CV settings override one derived document; job drafts and frozen packages remain separate resources.
|
||||
|
||||
Use one main brand hue through semantic light/dark tokens; final identity is undecided. Prefer the current mobile drawer over adding a second navigation system. Personal dashboard customization starts with owner-scoped layout metadata; cross-device persistence needs an explicit choice before implementation. New aggregate admin metrics must be server-computed and privacy-bounded.
|
||||
|
||||
## Evidence and limits
|
||||
|
||||
Source validation includes App/AppShell, route helpers, Jobs/table/board, workspace/asset models, Career/CV owners, analytics controller/service/DTOs, account/provider/notification owners and the Phase 1/2 test evidence. [Open decisions](OPEN_DECISIONS.md) records corrections to illustrative requirements and source-backed metric limitations. No user study, fresh visual prototype, provider evaluation or production inspection is claimed.
|
||||
|
||||
The unchanged **Phase 2 executed baseline** is 916 backend and 313 frontend tests passing (Phase 1: 916 / 298). General browser results are **23 actual passes + 1 expected failure**, not 24 successful workflows. B04 HTTP 9, B06 native HTTP 6, PDF admission 1 and Compose validation 3 passed. Standalone TypeScript, lint and Release builds passed there. Those are reused results for unchanged application code, not freshly executed Phase 3 suites. Historical TS2571 is corrected; remote CI/production certification remains outstanding.
|
||||
|
||||
Completion checks and exact commands are recorded in [Phase 4 plan](PHASE4_IMPLEMENTATION_PLAN.md#phase-3-checkpoint-validation). These check document completeness, source/route/PRES references and documentation-only scope. No visual implementation is approved by a document passing validation.
|
||||
|
||||
## Next boundary
|
||||
|
||||
Recommended first implementation slice: **P4-01 semantic state and focus foundation** in the existing theme, with loaded regression fixtures. Keep existing brand identity, routes and page composition. Follow the bounded plan and stop for review before expanding to the shell or representative pages. Production release remains separately gated by CI and F04 evidence.
|
||||
@@ -0,0 +1,44 @@
|
||||
# Responsive strategy and density
|
||||
|
||||
ARC-13; all PRES contracts, particularly PRES-E07, PRES-E08, PRES-J05, PRES-J07, PRES-W01, PRES-C06–PRES-C10, PRES-M04, PRES-S03, PRES-A01. This is an interaction contract, not screenshots or completed visual validation.
|
||||
|
||||
## Breakpoints and content
|
||||
|
||||
Retain current MUI breakpoints (0, 768, 1024, 1266, 1440) as starting tokens. The existing CV two-pane boundary at 900 has a content reason; do not force it to match global navigation without testing. Mobile shell currently changes below 768. Document these two responsibilities rather than changing every media query at once.
|
||||
|
||||
Required viewport samples: 320 CSS px reflow, 390×844 phone, 430 px large phone, 768×1024 portrait tablet, 1024×768 landscape, 1280×800 laptop, 1440×900 desktop, 1920 wide. Also test just below/above 768 and 900. EN/Bokmål, light/dark, long names, missing data, many jobs/custom statuses and multipage CVs matter more than device labels.
|
||||
|
||||
## Task-specific behavior
|
||||
|
||||
| Surface | Narrow / touch | Wider layouts | Preservation condition |
|
||||
|---|---|---|---|
|
||||
| Navigation | Existing modal menu drawer; grouped sections, visible search/bell/account | Collapsible sidebar/rail | Same destinations and active owner; focus return; no duplicate bottom nav by default |
|
||||
| Jobs | Structured cards, essential role/company/status/date/action; filter sheet | Primary table, optional board | Same filters/records/actions; selection never opens row; no functionality removed by density |
|
||||
| Board | Scrollable grouped columns with explicit status menu and keyboard alternative | Same grouping/drag semantics | No mandatory drag or hidden custom/Other status |
|
||||
| Dashboard | Single-column user order; move/hide; no meaningless horizontal resize | Discrete spans and supported resize | Keep saved desktop sizes when phone ignores them |
|
||||
| Job workspace | Header wraps; labelled section selector if tabs overflow; actions easy to reach | Full page, readable tabs and section content | Preserve current section, dirty draft and return context through resize |
|
||||
| CV editor | Edit/Preview toggle; touch/keyboard reorder controls | Editor + scrollable paginated preview | No remount/data loss at 900 boundary; preview keyboard scroll works after transition |
|
||||
| Dialogs/drawers | Long forms full-height with reachable Save/Cancel above virtual keyboard | Bounded modal or side panel | One modal focus trap; no fixed-height clipping of errors |
|
||||
| Commands | Full-width dialog, labelled search and grouped list; keyboard doesn't cover selected result | Bounded dialog | Same command scope, owner clearing and activation behavior |
|
||||
| Filters | Draft filter sheet with Apply/Cancel; existing committed filters retained on cancel | Inline common filters, advanced disclosure | Show active filter count, never change result data before intended apply |
|
||||
| Charts | Short summary + accessible values table, limited visible labels | Chart with legend and comparison | Same period/denominator; no hover-only values |
|
||||
| Correspondence | Message/draft panes as stepwise views with clear Back | List/detail when usable | Unsaved/draft/revision/send attempt unchanged; full content readable |
|
||||
| Settings | Labelled section select/list and single-column fields | Secondary section navigation | Save failure retains draft, account/security/provider separation |
|
||||
| Admin | Label/value rows or labelled horizontal table region, actions explicit | Table and aggregate panels | No omitted permission/last-admin warnings, no leaked private analytics |
|
||||
| Offers | One comparison at a time with accessible labelled alternatives | Recorded offers side-by-side | Same currency/period/source, no invented normalized comparison |
|
||||
|
||||
A read-only job preview may become full height on phone or be omitted in favor of the full page, subject to validation. Existing full job functionality remains. Stacked tabs or tiny icon-only controls are not acceptable substitutes for navigation.
|
||||
|
||||
## Comfortable and Compact
|
||||
|
||||
NEW-14. Comfortable is default. Density changes row/field spacing and secondary metadata layout, never feature visibility, source semantics or font legibility. Propose table body vertical padding 12 px / 8 px, with sufficient control hit area. Compact on touch must retain at least the same target hit regions as Comfortable; it is not permission to shrink every icon.
|
||||
|
||||
Apply to Jobs/company/admin tables and suitable lists first. Do not compress CV document layout, long-form editor text, dialogs or charts globally. Keep a distinct application preference with the existing identity/preference model; scope and migration must be explicit. Old page-size/column preferences and owner-keyed saved filters continue to work.
|
||||
|
||||
## State, scrolling and validation
|
||||
|
||||
Resizing a viewport changes presentation, not component/resource identity. Keep draft text, selected object, filter state, review proposal and save operation. Never keep private state after B02 invalidates the session. Preserve document and page scroll independently; return focus to a meaningful element that is visible in the new mode.
|
||||
|
||||
Avoid global overflow hiding as a “fix.” Data tables/boards/doc previews may have labelled intentional internal scroll; the page at 320 CSS px must not require sideways scrolling to reach ordinary actions. Sticky headers/footers and software keyboards must not obscure focused input/error messages.
|
||||
|
||||
Each migrated surface needs populated/empty/loading/error/locked/dirty checks and manual keyboard, touch, 200%/400% zoom and screen reader evidence. Browser viewport emulation is useful but does not prove touch usability, virtual keyboard behavior or assistive technology compatibility.
|
||||
@@ -0,0 +1,91 @@
|
||||
# Route plan
|
||||
|
||||
ARC-02. This is a future migration plan, not live route configuration. Preserve the SPA/static deployment and current React Router authority. Most current URLs stay canonical: meaningful labels do not require renaming stable paths.
|
||||
|
||||
## All existing route patterns
|
||||
|
||||
“Keep” includes refresh, direct entry, back/forward and owner/role behavior. No existing public or callback URL is removed.
|
||||
|
||||
| Current pattern | Target and disposition | Navigation owner | PRES contracts |
|
||||
|---|---|---|---|
|
||||
| / | Keep public landing and authenticated redirect behavior | Public | PRES-E01 |
|
||||
| /login | Keep | Public/account entry | PRES-E02, PRES-E03, PRES-E04 |
|
||||
| /register | Keep configured registration | Public | PRES-E02 |
|
||||
| /forgot-password | Keep | Public | PRES-E02 |
|
||||
| /reset-password | Keep token query contract | Public | PRES-E02 |
|
||||
| /verify-email | Keep token query contract | Public | PRES-E02 |
|
||||
| /confirm-email-change | Keep pending identity confirmation | Public | PRES-E06 |
|
||||
| /microsoft-legacy-relink | Keep recovery/relink | Public/account | PRES-E03 |
|
||||
| /cv/:slug | Keep published-only page/PDF; never redirect to numeric ID | Public share | PRES-C05, PRES-C12 |
|
||||
| /dashboard | Keep personal dashboard | Dashboard | PRES-S01, PRES-S02 |
|
||||
| /discover | Keep, present as Jobs → Discover | Jobs | PRES-J01, PRES-J02 |
|
||||
| /jobs | Keep; add presentation query view=table or view=board | Jobs → Tracked | PRES-J03, PRES-J05, PRES-J06, PRES-J07 |
|
||||
| /jobs/:id | Keep; staged section plan below | Jobs → job | PRES-W01–PRES-W12, PRES-M01, PRES-M02 |
|
||||
| /reminders | Keep as Jobs → Follow-ups | Jobs | PRES-W11 |
|
||||
| /operations | Keep progress/retry/cancel; utility link | Notifications / user activity | PRES-W12 |
|
||||
| /kanban | Future replace redirect to /jobs?view=board after unified board parity | Jobs → Tracked | PRES-J07 |
|
||||
| /companies | Keep including ?edit=id | Jobs → Companies | PRES-J08, PRES-E07 |
|
||||
| /offers | Keep | Jobs → Offers | PRES-J09 |
|
||||
| /correspondence | Keep inbox/drafts/review workspace | Correspondence | PRES-M01–PRES-M06 |
|
||||
| /correspondence/review | Keep existing alias to /correspondence?view=review | Correspondence | PRES-M05 |
|
||||
| /profile | Keep account identity/security under Settings; no rename to Career Profile | Settings → Account/Security | PRES-E04, PRES-E05, PRES-E06 |
|
||||
| /applications/:id | Keep existing alias to /jobs/:id with query and router state | Jobs → job | PRES-W01 |
|
||||
| /career | Keep | Career Profile | PRES-C01–PRES-C04 |
|
||||
| /career/builder | Keep; label CVs | CVs | PRES-C05 |
|
||||
| /career/builder/:id | Keep identified CV editor | CVs → CV | PRES-C06–PRES-C12 |
|
||||
| /admin/audit | Keep privileged audit/undo | Admin → Audit | PRES-A02 |
|
||||
| /admin/users | Keep privileged user management | Admin → Users | PRES-A01 |
|
||||
| /admin/system | Keep operational diagnostics, configuration and maintenance | Admin → System | PRES-A03 |
|
||||
| /trash | Keep deleted-only semantics as Jobs utility | Jobs → Trash | PRES-J06 |
|
||||
| /settings | Keep; later add validated section query for shared account navigation | Settings | PRES-S03, PRES-S04, PRES-S05, PRES-J10 |
|
||||
| /settings/connected-accounts | Keep; separate login identity from mail/calendar authorization | Settings → Connections | PRES-M06, PRES-E03 |
|
||||
|
||||
31 existing patterns mapped: 29 pages and two existing aliases. /kanban is currently a page, not already an alias. Outer /*, inner * and the inner root redirect stay as routing/error infrastructure. Do not confuse them with user pages.
|
||||
|
||||
## New destinations and readiness
|
||||
|
||||
| Proposed path | Minimum meaningful content / prerequisite |
|
||||
|---|---|
|
||||
| /analytics | Existing analytics charts and definitions; source/sample/period shown. New metrics only after their data contract |
|
||||
| /documents | Owner-scoped artifact index with job/type/state links; cross-job listing/query availability gated in Documents plan |
|
||||
| /notifications | Expanded existing notification centre; read/dismiss actions and operation links, not a new notification store |
|
||||
| /admin | Aggregate dashboard after authorized count endpoints exist; until then keep existing admin children visible with no empty dashboard |
|
||||
|
||||
These routes are not introduced in Phase 4 foundations. No /cvs rename, /account rename or nested Jobs child-URL rewrite is necessary. A future desire for prettier URLs needs its own compatibility proposal.
|
||||
|
||||
## Job section compatibility
|
||||
|
||||
Current accepted keys are overview, analysis, cv, cover-letter, interview. Current legacy keys collapse to analysis or overview in applicationWorkspace.ts. Future mappings must reveal the intended content more precisely without losing current capabilities.
|
||||
|
||||
| Incoming key | Current resolution | Future destination |
|
||||
|---|---|---|
|
||||
| absent, overview, job-details | overview | Overview; details anchor for job-details |
|
||||
| analysis, match | analysis | Match (analysis + profile comparison + strategy) |
|
||||
| cv | cv | Application → CV |
|
||||
| cover-letter | cover-letter | Application → Cover letter |
|
||||
| interview | interview | Interview |
|
||||
| documents | overview | Documents |
|
||||
| timeline | overview | Timeline |
|
||||
| checklist | overview | Notes & tasks → checklist |
|
||||
| communication | overview | Timeline → correspondence/follow-up context |
|
||||
|
||||
Future canonical top sections: overview, match, application, documents, timeline, tasks, interview. application may use sub=cv, letter, answers, submission; timeline may use sub=activity or correspondence. This is a small navigation adapter; do not change API section strings or persistent checklist links in bulk.
|
||||
|
||||
Keep all numeric tab helper inputs: 0 overview; 1 correspondence; 2 attachments; 3 tailored CV; 4 follow-up; 5 candidate fit; 6 focus plan; 7 interview prep; 8 readiness; 9 history. Translate their existing section outputs through the table. Preserve followMode and open its actual compose/follow-up mode; do not silently drop it as current tab switching can. Unknown keys fall back safely to Overview without submitting or mutating data.
|
||||
|
||||
## Query, state and compatibility contract
|
||||
|
||||
- Preserve Jobs q, status, companyId, location, needsFollowUp, readiness, includeDeleted, sortBy, sortDir and page. Keep existing page-number interpretation. view changes only presentation. Board query parity must be tested before /kanban redirects.
|
||||
- Preserve return state from/focusJobId; return to exact filter/list context, restore focus or a safe nearby list heading if the row no longer exists. Only local safe return paths are accepted.
|
||||
- Preserve capture ?add= and ?addtext=, encoding, consumed-once review and optional post-create attachment/CV work. Do not put private draft bodies in new URLs or command history.
|
||||
- Preserve /companies?edit=id and correspondence ?view=review. Draft identity/revision stays with its service; adding a draft deep link must not create/resend a draft.
|
||||
- Preserve /career?section=overview, profile, evidence or import; missing/unknown selects Overview as today. Canonical editing and import-review entry must remain distinct. No CV editor query contract is invented from a test filename.
|
||||
- Keep public token URLs and backend OAuth callback/postMessage origin/state behavior. Do not migrate them through a generic route redirect.
|
||||
- Prefer React Router replace for compatibility aliases so Back does not loop. Preserve relevant query/hash/state; never trust URL account identifiers as authorization.
|
||||
- Keep aliases throughout migration and at least the first completed full rollout. There is **no approved removal date**. Removal requires explicit decision, observed old-link usage without private data, updated extension/bookmarklet/notifications and regression evidence. No redirect chains: every alias targets the canonical resolver directly.
|
||||
|
||||
## Titles, breadcrumbs and route validation
|
||||
|
||||
One h1 per page. Collection title: Jobs / Career Profile / CVs. Detail: role at company or CV name, safely text-rendered; browser title adds section and current Jobjakt name. Public token pages must not copy tokens into titles. Breadcrumbs on detail/Settings/Admin only when they provide navigation, e.g. Jobs → Role, CVs → CV name; status and tabs are not extra breadcrumb ancestors.
|
||||
|
||||
Phase 5 route changes require an actual App browser fixture for every migrated canonical/alias entry, loaded and missing/foreign objects, query retention, capture no-write, browser Back/refresh, dirty Cancel/Discard, focus return and account switch. Existing route-helper tests alone are insufficient. Test real static nginx fallback separately before deployment; F04 remains open.
|
||||
+3
-1
@@ -5,7 +5,9 @@
|
||||
- [x] Read the Astra handoff and required product documents; complete Phase 1 source audit with 31 concrete route patterns, functionality preservation ledger, 266 API call sites, component/test inventory, identity/storage map, responsive/localisation assessment and migration gates. See `docs/redesign/audit/README.md`. No redesign implementation or B07 started.
|
||||
- [x] Finalize Phase 1 separately, 2026-09-10: classify all 57 preservation groups, UX improvements, genuinely new/conditional requirements and baseline defects; retain already-implemented CV drag/fit, custom status values, calendar and other protected workflows. Final summary/contract/test limits/Phase 2 starting point: `docs/redesign/audit/PHASE1_SUMMARY.md`. Documentation only; B06/F04 closure remains open.
|
||||
- [ ] Complete the authorized `main` release through required CI/deploy gates. Main `27657f3` is pushed; run 743 passed 916 backend/298 frontend tests, lint, dependency audits and production builds, then the browser gate failed (worker SIGSEGV, retry timeout and closed-browser errors; 6 passed/12 failed). Deploy skipped; live remains version 299. Stop further release retries pending runner-host diagnostics; exact read-only handoff and evidence are in `docs/audits/2026-09-07/validation/b06-completion.md`. No gate was bypassed.
|
||||
- [ ] Next redesign work: Phase 3 UX architecture/route and workflow plan using the [traceability contract](../redesign/phase-2/TRACEABILITY.md), subject to documented gaps and integrity/recovery/release gates. Not started automatically; no visual implementation authorized by this checkpoint.
|
||||
- [x] Phase 3 from `d6d3dd9` on `codex/ui-redesign-phase3`: [UX architecture package](../redesign/phase-3/README.md), 31 existing route patterns, 57 PRES impact rows, data-qualified personal/admin dashboards, canonical/CV/job/frozen-document distinctions, contextual AI review, responsive/accessibility/component plans and explicit decisions. Documentation only; no Phase 4/visual implementation or B07. F04 remains open.
|
||||
- [ ] Next redesign work, not started: [P4-01 semantic state/focus foundation](../redesign/phase-3/PHASE4_IMPLEMENTATION_PLAN.md) using existing MUI/theme and loaded regression fixtures. Keep current brand/routes/providers; coordinate validated A01. Do not begin broad shell/pages before foundation proof.
|
||||
- [ ] P3-O01/P3-O02 separately scoped presentation debt: accurate analytics population/period labels and navigation/query/error retention when those surfaces migrate. [Source observations and boundaries](../redesign/phase-3/OPEN_DECISIONS.md); no analytics, route or command behavior fixed during Phase 3.
|
||||
|
||||
# Expanded production audit — 2026-09-07
|
||||
|
||||
|
||||
Reference in New Issue
Block a user