Plan: Finances Phase D, native surface rebuild passes¶
URL: https://mkdocs.justinsforge.com/memory/plans/finances-phase-d-surface-passes-2026-07-06/
Date: 2026-07-06
Approved spec: Rebuild the 13 finance surfaces from their Flask-port skin (finances.css + Outfit) into CreatorTrack's native design system: components/ui primitives, app/theme.css tokens, inherited Geist/Geist Mono, charts through the locked wrapper components/Charts/Charts.tsx. One surface per pass; Justin approves each pass live on dev slot :3062 (branch feat/finances-surfaces, worktree ~/forge-suite-wt/feat/finances-surfaces, DB ct_feat_finances_surfaces) before it is committed. Data layer (lib/finance.ts loaders, write routes) stays; presentation is rebuilt. finances.css survives until the final surface pass so unmigrated tabs keep rendering. No new npm deps (shared cross-worktree node_modules). No merge to main, no deploy.
Amendment (2026-07-06, Task 0, commit adfd5d1): the standalone /finances door is RETIRED per Justin (clicks were escaping the workspace). The CreatorTrack finance node is the only door. Surfaces moved to components/finance/surfaces/*; /finances/* page routes are redirect shims (lib/finance-node.ts); all in-surface links are query-relative (?view=...). Surface passes verify on http://100.97.43.104:3062/justin/finances-5421?view=<surface> (not /finances/<surface>), and new links built in passes MUST be query-relative or use TxFilterBar's pathname-merge pattern.
Out of scope: merge/deploy, new ingest logic, PNC SimpleFIN re-auth, legacy forge-finance-* unit and :8096 tunnel cleanup.
Workflow per surface task: implement, verify on http://100.97.43.104:3062/finances/<surface>, Justin approves in chat, then commit exactly feat(finances): <surface> iteration pass.
Progress (2026-07-06, session 2)¶
PHASE D COMPLETE (2026-07-06). Session 2 merged Tasks 0-3+9 + platform work to main (merge 3065fa7, deployed). Session 3 finished the rest on branch feat/finances-surfaces-2 (slot :3062): Tasks 4-8 + 10 (7a2e853..232ae8b), Task 11 Categorize (33174fc, incl. legacy-tid fix: queue now sends PG ids so single-row filing actually writes), Task 12 Receipts capture (2c7d3e9, new upload route + camera form, verified end-to-end), Task 13 Alerts + finances.css deletion (27ad172, alert_feed on top, pills/page-shell ported to native.css, orphan chart components removed, build gate passed, 13 tabs checked), Task 14 docs (this + module reference). Branch NOT yet merged; awaiting Justin's review + single merge. Continuation brief (patterns/gotchas): finances-phase-d-continuation-2026-07-06.
Task list¶
Task 0: Rebuild the finances shell (layout, sidebar, node-face chrome)¶
- Files:
app/finances/layout.tsx,components/finance/FinanceSidebar.tsx(or current sidebar path),components/apps/finance/FinanceApp.tsx,components/apps/finance/FinanceShell.tsx,components/apps/finance/finance.css - What: Drop the Outfit font, render surfaces inside native chrome on theme tokens; rebuild the sidebar/tab nav on
components/ui(NavItem/Tabs); FinanceApp stops importing finances.css once all passes land (keep for now), swapfn-navstyling to tokens. - Verification:
curl -fsS -o /dev/null -w '%{http_code}\n' http://127.0.0.1:3062/financesreturns 200; visual check on :3062. - Commit:
feat(finances): native shell iteration pass
Task 1: Dashboard¶
- Files:
app/finances/page.tsx, new client components undercomponents/finance/ - What: Rebuild overview (net worth headline, spend chart via Charts.tsx, recent transactions, recurring, sync button) natively.
- Verification: 200 on
/finances; visual approval. - Commit:
feat(finances): dashboard iteration pass
Task 2: Net Worth¶
- Files:
app/finances/networth/page.tsx,components/finance/* - What: Native rebuild of sections + NW grid; wire manual value edits to
POST /api/finance/manual-values. - Verification: manual-value edit round-trips (row appears, page reflects new value); visual approval.
- Commit:
feat(finances): networth iteration pass
Task 3: Investments¶
- Files:
app/finances/investments/page.tsx,lib/finance-jobs/holdings.ts(readSsgaXlsx as_of parse, ~lines 319-325) - What: Native rebuild; fix SSGA
as_ofxlsx date-serial parse (guard "Date downloaded" row, UTC handling, reject non-date raw). - Verification:
env -u PGPASSWORD PGDATABASE=ct_feat_finances_surfaces npx tsxsmoke of readSsgaXlsx date branch; visual approval. - Commit:
feat(finances): investments iteration pass
Task 4: Spending¶
- Files:
app/finances/spending/page.tsx,components/finance/* - What: Native rebuild (month nav, category breakdown, Charts.tsx area/donut, transaction drill-down).
- Verification: 200 + visual approval.
- Commit:
feat(finances): spending iteration pass
Task 5: Budget¶
- Files:
app/finances/budget/page.tsx,components/finance/* - What: Native rebuild; wire targets/autoset UI to
POST /api/finance/budgets(upsert, null/0 deletes). - Verification: setting a budget persists across reload in
finance.budgets; visual approval. - Commit:
feat(finances): budget iteration pass
Task 6: Business¶
- Files:
app/finances/business/page.tsx,components/finance/* - What: Restyle only (loader is
@/lib/erpnextgetBusinessData). - Verification: 200 + visual approval.
- Commit:
feat(finances): business iteration pass
Task 7: Recurring¶
- Files:
app/finances/recurring/page.tsx,components/finance/* - What: Native rebuild; keep
recurring/actionwiring; icons keyed byiconKeyonly. - Verification: recurring action round-trips; visual approval.
- Commit:
feat(finances): recurring iteration pass
Task 8: Cash Flow¶
- Files:
app/finances/cashflow/page.tsx,components/finance/* - What: Native rebuild of month flows on Charts.tsx.
- Verification: 200 + visual approval.
- Commit:
feat(finances): cashflow iteration pass
Task 9: Accounts¶
- Files:
app/finances/accounts/page.tsx,components/finance/* - What: Native rebuild; manual-value entry point for
source='manual'accounts (POST /api/finance/manual-values). Amendment (2026-07-06, Justin): add per-account profiles: clicking an account anywhere (dashboard buckets, accounts list) opens that account's profile in the Accounts surface (?view=accounts&acct=<id>): balance history, recent transactions for the account, metadata (institution, kind, scope, icon), manual-value editing for manual accounts. - Verification: manual account edit persists; account click-through from dashboard lands on the right profile; visual approval.
- Commit:
feat(finances): accounts iteration pass
Task 10: Transactions¶
- Files:
app/finances/transactions/page.tsx,components/finance/* - What: Native rebuild; edit/bulk-edit UI wired to
POST /api/finance/transactions(category/scope/note/flags; route exists, no UI yet). - Verification: single + bulk edit persist (
user_category=trueon category edit); visual approval. - Commit:
feat(finances): transactions iteration pass
Task 11: Categorize¶
- Files:
app/finances/categorize/page.tsx,components/finance/* - What: Native rebuild of queue UI; keep
categorize/applywiring. - Verification: apply round-trips; visual approval.
- Commit:
feat(finances): categorize iteration pass
Task 12: Receipts¶
- Files:
app/finances/receipts/page.tsx, newapp/finances/receipts/upload/route.ts,components/finance/* - What: Native capture surface (phone upload to
finance.receipts+ image store; reconcile joblib/finance-jobs/receipts.tsalready matches/attaches). Zero rows, clean slate. - Verification: upload a test image, row lands in
finance.receipts, image served back viareceipts/img; visual approval. - Commit:
feat(finances): receipts iteration pass
Task 13: Alerts + legacy skin deletion¶
- Files:
app/finances/alerts/page.tsx,app/finances/layout.tsx, deleteapp/finances/finances.css, prune orphanedcomponents/finance/*legacy components and unusedlib/finance-ui.tsxexports, drop finances.css/Outfit imports incomponents/apps/finance/FinanceApp.tsx - What: Native rebuild with
finance.alert_feedrendered at top; then delete the Flask skin entirely. - Verification:
grep -r "finances.css\|Outfit" app/ components/ lib/returns nothing;npx next build --webpackpasses; all 13 tabs visual-checked. - Commit:
feat(finances): alerts iteration pass + legacy skin removal
Task 14: Register and document¶
- Files:
/home/justinwieb/forge/memory/general/reference_creatortrack_finance_module.md, this plan (check off), new handoff if session ends mid-list - What: Update module reference (surfaces now native, receipts capture live), note Phase D complete through task N.
- Verification:
grep -q "Phase D" /home/justinwieb/forge/memory/general/reference_creatortrack_finance_module.md - Commit: (forge repo)
docs(finances): Phase D surface passes recorded
[Claude Code, 2026-07-06]