## Legacy Porting TODOs

Purpose: Track features and workflows from legacy Paradox (.SC) scripts to port into the modern app. Each item includes a clear example to guide implementation and testing.

### Cross-cutting platform and data
- [x] Data model: create relational tables and relations
  - Example: Create tables `Rolodex`, `Phone`, `Files`, `Ledger`, `Deposits`, `Payments`, `Printers`, `Setup`, `Footers`, `FileStat`, `FileType`, `TrnsLkup`, `TrnsType`, `GrupLkup`, `PlanInfo`, `Pensions`, `Results`, `Output`, `Schedule`, `Separate`, `Death`, `Marriage`, `States`, `LifeTabl`, `NumberAl`. Foreign keys: `Phone.id -> Rolodex.id`, `Files.id -> Rolodex.id`, `Ledger.file_no -> Files.file_no`.

- [x] CSV import: one-time and repeatable import from legacy CSVs
  - Example: Import `old-database/Office/FILES.csv` into `files` table; validate required fields and normalize dates; log row count and any rejects.

- [x] Answer table pattern for query results
  - Example: After searching `Rolodex`, show a paginated results view with bulk actions (reports, document assembly, return to full dataset).

- [x] Field prompts/help (tooltips or side panel)
  - Example: When focusing `Files.File_Type`, show: "F1 to select area of law" as inline help text.

- [x] Structured logging/audit trail
  - Example: On `Ledger` create/update/delete, log user, action, record keys, and pre/post balance totals for the related file.

- [ ] Reporting infrastructure (screen preview, PDF, CSV)
  - Example: Provide a common reporting service to render a "Statements - Unbilled (Itemized)" report to PDF and preview in-browser.

### Main navigation (legacy Main Menu)
- [ ] Dashboard linking modules
  - Example: Home shows links to Rolodex, File Cabinet, Pensions, Plan Info, Deposits, Utilities, Printers/Customize, Tally Accounts.

### Rolodex (names/addresses/phones)
- [x] CRUD for `Rolodex` and child `Phone` entries
  - Example: Add a phone number with `Location = Office` and format validation (e.g., `1-555-555-1234`).

- [x] Advanced search dialog joining `Phone`
  - Example: Search by `Last = "Smith"` and `Phone contains "555-12"`; results include records linked by `Phone.Id -> Rolodex.Id`.

- [ ] Reports: Envelope, Phone Book (2 variants), Rolodex Info
  - Example: Generate "Phone Book - Address & Phone" PDF for current results set (min. 1 page output).

- [ ] Document assembly hook from results
  - Example: Select one or more contacts, choose a form, and produce a merged document with their address data.

### File Cabinet (client files and billing)
- [x] Master-detail UI for `Files` with `Ledger` detail
  - Example: Selecting a file shows ledger entries inline; adding a ledger line updates file totals.

- [ ] Ask/Search dialog over `Files`
  - Example: Filter by `Status = SEND` and `Empl_Num = 101` and `Opened in 2024`; render answer-table results.

- [ ] Close/Reopen account actions
  - Example: Close account with `Amount_Owing = 250.00` auto-posts a `Ledger` payment entry (T_Code `PMT`, Billed `Y`) and sets `Files.Status = INACTIVE` and `Closed = today`.

- [ ] Summarize Accounts view (billed/unbilled/total)
  - Example: For a file, show three columns (Billed, Not Billed, Total) for Trust, Hours, Hourly Fees, Flat Fees, Disbursements, Credits, Balance Due, and Transferable.

- [ ] Timekeeper ticker (optional v1)
  - Example: Start timer; upon stop, prefill an hourly ledger `Quantity` from elapsed hours; allow edit before save.

- [ ] Locate Record utility
  - Example: Search by `Regarding contains "QDRO"` jumps to matching file in the master grid.

- [ ] Reports from results (envelope, phone, file info, accounts, statements, credit/payment history)
  - Example: From a filtered set, generate "Account Balances - Short" grouped by employee and file status.

- [ ] Bulk mark billed and recompute
  - Example: Mark all displayed unbilled `Ledger` entries as `Billed = Y`; recompute `Files` billed/unbilled totals.

- [ ] SEND/HOLD status filtering semantics via `FileStat`
  - Example: When selecting `Status = HOLD`, exclude from default statement print runs.

### Ledger (file transactions)
- [ ] Validations and defaults
  - Example: Require `Date`, `T_Code`, `Empl_Num`, `Amount`, `Billed`; if `T_Type = 2 (Hourly)`, default `Rate` from `Employee.Rate_Per_Hour` for the selected employee.

- [x] Auto-compute `Amount = Quantity * Rate`
  - Example: Enter `Quantity = 2`, `Rate = 150.00` auto-sets `Amount = 300.00` when either field changes.

- [x] Unique posting for `Item_No`
  - Example: On save, if `(File_No, Date, Item_No)` conflicts, increment `Item_No` until unique, then persist.

- [ ] Recompute file totals (Tally_Ledger) on change
  - Example: After delete of a credit, `Files.Amount_Owing` updates immediately and `Transferable` recalculates.

- [ ] Quick toggles and date nudge
  - Example: Keyboard toggle to set `Billed` Y/N; buttons to shift `Date` ±1 day.

### Deposits / Payments
- [x] Payments search (date range, File_No, Id, Regarding)
  - Example: `From_Date=2025-01-01`, `To_Date=2025-03-31` shows all payments in Q1 2025 with optional filters for file or id.

- [ ] Reports: Summary and Detailed payments
  - Example: Generate a "Payments - Detailed" PDF grouped by deposit date.

- [ ] Deposit `Total` = sum of linked payment amounts
  - Example: On save of a deposit with three payments (50, 75, 25), set `Deposits.Total = 150.00`.

### Plan Info
- [ ] CRUD for plan catalog
  - Example: Add a plan with `Plan_Id = "ABC-123"`, `Plan_Type = DB`, and memo details; searchable in Pensions and QDRO.

### Pensions (annuity evaluator)
- [ ] Life Expectancy Method (uses `LifeTabl`)
  - Example: Given `Valu` (valuation date) and `Birth`, compute `Age`, `Start_Age`, `Payments = int(LE*12)`, `Mortality`, `PV`, `PV_AM`, `PV_AMT`, apply death benefit and marriage factor, then write results.

- [ ] Actuarial Method (uses `NumberAl` monthly mortality)
  - Example: Build monthly survival probabilities; apply COLA (capped by `Max_COLA`) annually after 12 months; discount pre/post; compute `TEP`, `PV_TEP`, `PV_TEP_NOW`, then marriage factor and results.

- [ ] Save Results and Output
  - Example: Copy computed result fields into `Results`; populate `Output` with human-readable fields (e.g., `Last's` possessive formatting) for document generation.

- [ ] Ask for Output (document assembly)
  - Example: Open current `Output` record for the selected pension and pass it to the Forms/assembly workflow.

### Document assembly (Forms)
- [ ] Forms library management (list, descriptions, selection)
  - Example: List files from a configured forms directory; show description from `Forms/Form_Lst` when a file is selected.

- [ ] Save/Run merge configurations
  - Example: Save selected forms set as a reusable config; run merge to produce DOCX/PDF via templating.

- [ ] Forms search with index keywords
  - Example: Search by `Status = Active` and keywords `["QDRO", "Envelope"]` to narrow the list.

- [ ] Form List report
  - Example: Print a report listing matching forms (name + memo/description).

### Utilities / Setup / Printers
- [ ] CRUD for code tables (`FileType`, `Employee`, `TrnsType`, `TrnsLkup`, `Footers`, `GrupLkup`, `FileStat`, `States`, `PlanInfo`, `Printers`, `RVarLkup`, `FVarLkup`, `Inx_Lkup`)
  - Example: Add `TrnsLkup` with `T_Code = PMT`, `T_Type = 5`, `T_Type_L = C`, `Description = Payment`.

- [ ] Customize Setup (title and 10-line letterhead)
  - Example: Update organization title and letterhead; persist in `Setup`; reflect in statement/report headers.

- [ ] Printers / Output profiles
  - Example: Define output profile (e.g., A4/PDF) that maps legacy "setup strings" to modern render options; set as default.

- [ ] Tally Accounts (batch recompute)
  - Example: Button runs recompute across all `Files` and shows confirmation of N updated.

- [ ] Organize (archive rotation)
  - Example: Move `Files` with `Status = ARCHIVE` and their `Ledger` entries to archive tables or mark `archived = true`.

- [ ] Calendar maintenance (low priority)
  - Example: Archive `Calndr`/`Apoint` entries older than 30 days into `*_x` tables (or mark archived).

### Reporting (consolidated list)
- [ ] Implement reports used across modules
  - Example: Provide templates/endpoints for: Payments (summary/detailed), Phone Book (2), Envelope, Rolodex Info, File Cabinet Info (detailed/short), Account Balances (detailed/short), Statements (all/unbilled/billed; total vs itemized), Credit/Payment History, Form List.

### UX polish and accessibility
- [ ] Keyboard shortcuts for common actions
  - Example: Map F2=Save, F8=Clear form, F9=Toggle edit, provide alternatives for accessibility.

- [ ] Memo editor for long text fields
  - Example: Open modal to edit `Files.Memo` with character count and autosave warning.

### Data integrity and computations
- [ ] Rollups and derived fields on `Files`
  - Example: Maintain `Hours`, `Hourly_Fees`, `Flat_Fees`, `Disbursements`, `Credit_Bal`, `Total_Charges`, `Amount_Owing`, `Transferable` in sync with `Ledger`.

- [ ] Duplicate/uniqueness safeguards
  - Example: Prevent duplicate `Pensions (File_No + Version)`; ensure `Ledger (File_No + Date + Item_No)` is unique; show friendly error.

### Staging / Not included yet
- [ ] QDRO Screen and templates (scoped separately)
  - Example: Define schema and UI for QDRO; integrate with Forms for drafting; out of this immediate milestone.

- [ ] Timecard/Trust/Calendar (defer unless requested)
  - Example: Keep placeholders; implement only if explicitly prioritized.

### Decisions required (product/tech)
- [ ] Which reports are must-have for v1?
  - Example: If only Statements and Phone Book are needed initially, defer other reports.

- [ ] Output strategy: PDF-only vs printer integration
  - Example: Prefer PDF preview + download; printer selection as future enhancement.

- [ ] Document assembly target
  - Example: Choose DOCX templating (Jinja-in-Docx) vs HTML-to-PDF for merge outputs.

- [ ] Archival approach
  - Example: Use `archived_at` flag and views instead of physical `*_x` tables.

---

Notes
- Keep implementations modular with explicit config via environment variables.
- Add structured debug logging around imports, computes, and reports.
- Ensure Docker images and compose are updated if new dependencies are added.


