seubert-claims/dev/horizon-issues-implementation-2026-05-28.md
lorentz 01ecfacd04 feat(imageright): finalize two-pass audit engine and task-audit UI polish
Uncommitted work-in-progress from 2026-07-08, carried forward:
- audit-engine: refine two-pass metadata + content-inspection audit model
- audit-matching, content-inspector, shape-audit-spec: supporting matching
  and spec updates for the two-pass model
- task-audit route/panel: UI and API polish
- add @napi-rs/canvas dependency, Dockerfile/next.config adjustments for it
- test updates and additions (audit-engine, audit-decision-logic,
  run-task-audit)
- add loose dev notes (clone runbook, issues implementation, overdue filter
  bug report, shared count helper plan)
2026-07-16 22:52:41 +00:00

151 lines
7.1 KiB
Markdown
Raw Blame History

This file contains ambiguous Unicode characters

This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.

# Horizon Issues Implementation — May 28, 2026
**Commit:** `20f7ec1`
**Deployed:** May 28, 2026 ~11:50 PM UTC
**Container rebuild:** Yes — `horizon-app` recreated and restarted
---
## What Was Implemented
### 1. Tasks Disappearing (High — Bug Fix)
**Symptom:** Mimi's IN_PROGRESS task and other open tasks were vanishing from task lists.
**Root cause:** The task visibility filter included `policyGroup: { renewalDate: { gte: cutoff } }` with no exemption for open tasks. Any task on a renewal group whose date was older than 7 days was hidden — even if the task was `IN_PROGRESS` or `NOT_STARTED`.
**Fix:** Added `{ status: { notIn: TERMINAL_STATUSES } }` as a third OR branch so open tasks always show regardless of group renewal date. Only terminal (`COMPLETED`, `CANCELLED`, `NA`) tasks on old groups are filtered out.
**Files changed:**
- `src/app/(dashboard)/tasks/page.tsx`
- `src/app/(dashboard)/clients/[id]/page.tsx`
- `src/app/api/clients/[id]/tasks/route.ts`
**Data impact:** None. No task records were modified. The fix only changes what the query returns.
---
### 2. Star Date Change Doesn't Update Task Due Dates (High — Bug Fix)
**Symptom:** When a manager changed the renewal date on a policy group, all open tasks retained their old due dates.
**Root cause:** `PATCH /api/policy-groups/[id]` saved the new `renewalDate` but never recalculated `dueDate` on existing tasks. Since `dueDate = renewalDate + daysOffset`, the dates silently became wrong.
**Fix:** After saving the group, the API now fetches all open (`NOT_STARTED`, `IN_PROGRESS`, `BLOCKED`) template-generated tasks in the group and recalculates their `dueDate`. The count of rescheduled tasks is included in the audit log entry and the API response.
**Files changed:**
- `src/app/api/policy-groups/[id]/route.ts`
**Data impact:** Future — will update task due dates whenever a manager changes a group's renewal date going forward. Did not retroactively update any existing tasks.
---
### 3. Auto Task Assignment Not Working (BEK, Noor) (High — Feature)
**Symptom:** BEK and Noor were set up 3 days ago but had zero tasks. The auto-generate cron requires all policies to be ≥20 days old before generating tasks.
**Fix:** When a manager clicks "Save & Complete" in the setup wizard, it now automatically calls `POST /api/policy-groups/[id]/generate-tasks` for every saved group. A loading toast ("Generating tasks…") shows during this step, and the success toast confirms completion.
**Files changed:**
- `src/app/api/clients/[id]/setup/route.ts` — now returns `groups` array with IDs
- `src/components/renewal-groups/setup-wizard.tsx` — calls generate-tasks after non-draft save
**Data impact:** BEK and Noor still need to have their setup wizard re-saved (or re-completed) to trigger task generation for existing groups, since the fix only fires on new completions going forward. Alternative: generate tasks manually via the existing group detail page.
---
### 4. Manual Sync Hardcoded Date Range (Medium — Bug Fix)
**Symptom:** The Manual Sync panel defaulted to `2026-01-01` `2026-12-31`, silently skipping policies outside that window.
**Fix:** Defaults are now dynamic: start = January 1 of the prior year, end = December 31 two years out. This auto-adjusts every calendar year.
**Files changed:**
- `src/components/admin/sync-trigger.tsx`
**Data impact:** None.
---
### 5. Setup Queue Showing Inactive Clients (Medium — Bug Fix)
**Symptom:** 26 clients were showing in the setup queue, including many with only cancelled/expired/non-renewed policies that don't need setup.
**Fix:** The queue now filters to clients with at least one active (non-dead) policy. A note in the subtitle shows how many clients were excluded so managers have full visibility.
Dead statuses filtered: `Cancelled`, `Expired`, `Non-Renewed`, `Rewritten`, `Not taken`.
**Files changed:**
- `src/app/(dashboard)/manager/setup/page.tsx`
**Data impact:** None. Queue count will be lower — that's correct.
---
### 6. Audit Logging Gap — Notes Route (Medium — Bug Fix)
**Symptom:** When a user added a note and simultaneously changed task status, the audit log recorded `TASK_NOTE_ADDED` with only the new status. The old status was never captured, making it impossible to know what a task was before the change.
**Fix:** When a status change accompanies a note, the route now also emits a dedicated `TASK_STATUS_CHANGED` audit entry with `oldValues.status` and `newValues.status`. The existing `TASK_NOTE_ADDED` entry was also updated to include `oldValues.status`.
**Files changed:**
- `src/app/api/tasks/[id]/notes/route.ts`
**Data impact:** No historical backfill. New entries going forward will be complete. Verification query:
```sql
SELECT action, old_values->>'status' AS old, new_values->>'status' AS new, created_at
FROM audit_logs WHERE action = 'TASK_STATUS_CHANGED'
ORDER BY created_at DESC LIMIT 10;
```
---
### 7. Renewal Warnings Not Showing on Policy Cards (Low — Enhancement)
**Symptom:** Day-count warning badges (e.g. "26d", "34d") appeared on client-level cards and lists but not on individual policy cards inside the client detail view.
**Fix:** Each policy card in the client detail tab now shows:
- Red badge `Xd` if renewal is within 30 days
- Grey badge `Xd` if renewal is within 90 days
**Files changed:**
- `src/components/clients/client-detail.tsx`
---
### 8. Client Notes — No Save Attribution (Low — Enhancement)
**Symptom:** The Client Notes section had no indication of when notes were last saved or by whom.
**Fix:** After saving notes, a "Saved [timestamp]" label appears next to the Save button for the duration of the session.
**Note:** A persistent "last saved by" tracker would require a DB migration (adding `notesUpdatedAt` / `notesUpdatedBy` to the `clients` table). This was not added. If persistent tracking is desired, a migration can be written.
**Files changed:**
- `src/components/clients/client-detail.tsx`
---
## Verification — User Task Counts (Post-Deploy)
Queried immediately after deploy. No tasks were modified by the code changes.
| User | NOT_STARTED | IN_PROGRESS | COMPLETED | NA |
|---|---|---|---|---|
| Luke Billman | 236 | 7 | 164 | 43 |
| Mimi Rawlings | 516 | 5 | 602 | 38 |
| Christine Gove | 1,722 | — | 2,087 | 96 |
All status changes since May 21 were made by the users themselves (no system reversions).
---
## Deployment
No database migrations were required. All changes are application-layer only.
```
git commit: 20f7ec1
git push: main → forgejo.wulfconsulting.cloud/lorentz/seubert-claims
docker: horizon-app Recreated → Started (Up as of ~11:50 PM UTC May 28)
```
---
## Still Pending
- **SHAPE import audit logging** — The import directly creates/updates tasks with `COMPLETED`/`NA` status but emits no per-task audit entries. Low risk (admin-only, rare operation). Plan documented in `dev/audit-logging-fix-plan.md`.
- **BEK/Noor task generation** — Needs manual trigger via group detail page, or re-completing setup, since they were set up before this fix.
- **Client notes persistent attribution** — Requires a DB migration to add `notesUpdatedAt` / `notesUpdatedBy` columns.