seubert-claims/ondeck/ARCHITECTURE.md

102 lines
5.4 KiB
Markdown
Raw Permalink Normal View History

# Horizon — Architecture
## Overview
Next.js 15 App Router application. All pages are server or client components under `src/app/(dashboard)/`. Data access goes exclusively through Next.js API route handlers (`src/app/api/`), which use Prisma to talk to Postgres.
## Directory map
```
src/
├── app/
│ ├── (dashboard)/ # Authenticated layout + all pages
│ │ ├── layout.tsx # Shell: sidebar, nav, session guard
│ │ ├── dashboard/ # Home/summary page
│ │ ├── clients/ # Client list + detail ([id]/)
│ │ ├── policies/ # Policy list + detail ([id]/)
│ │ ├── tasks/ # Task list (page-client.tsx) + detail ([id]/)
│ │ ├── admin/ # Admin-only pages (users, roles, designations, sync)
│ │ └── manager/ # Manager pages (templates, metrics)
│ ├── api/ # API route handlers
│ │ ├── auth/ # NextAuth endpoints
│ │ ├── clients/ # CRUD + notes, contacts, members
│ │ ├── tasks/ # CRUD + notes, assignments
│ │ ├── policies/ # CRUD + policy groups
│ │ ├── policy-groups/ # Renewal group management
│ │ ├── sync/ # Shape import sync
│ │ ├── users/ # User management
│ │ ├── roles/ # Role management
│ │ ├── templates/ # Task templates
│ │ ├── designations/ # Client designations
│ │ ├── metrics/ # Dashboard metrics
│ │ ├── cron/ # Scheduled jobs (notifications, etc.)
│ │ └── dashboard/ # Dashboard summary data
│ ├── auth/ # Sign-in / error pages (unauthenticated)
│ └── layout.tsx # Root layout (providers, theme)
├── components/
│ ├── ui/ # shadcn/ui primitives (Button, Dialog, Input, etc.)
│ ├── clients/ # Client-specific components
│ ├── tasks/ # Task card, task edit modal
│ ├── policies/ # Policy components
│ ├── renewal-groups/ # Policy group components
│ ├── notifications/ # Notification bell + panel
│ ├── admin/ # Admin UI components
│ ├── manager/ # Manager UI components
│ ├── layout/ # Sidebar, header, nav
│ └── providers/ # SessionProvider, ThemeProvider
├── lib/
│ ├── auth.ts # NextAuth config (Entra ID + local credentials)
│ ├── db.ts # Prisma client singleton
│ ├── entra.ts # Microsoft Graph API helpers
│ ├── utils.ts # Shared utilities (cn(), formatters)
│ ├── hooks/ # Custom React hooks
│ ├── sync/ # Shape import sync logic
│ ├── shape-import/ # Shape file parsing
│ └── tasks/ # Task business logic helpers
├── middleware.ts # Auth middleware (protects all dashboard routes)
└── types/ # Shared TypeScript types
```
## Data models (key entities)
| Model | Description |
|-------|-------------|
| `User` | Staff accounts; synced from Entra ID |
| `Role` / `UserRole` | RBAC roles (Admin, Manager, AE, Claims, etc.) |
| `Client` | Insurance clients; synced from AMS via Shape import |
| `ClientContact` | Contacts per client |
| `ClientMember` | Which staff are assigned to a client |
| `Designation` | Client classification labels (color-coded) |
| `Policy` | Insurance policies linked to clients |
| `PolicyGroup` | Renewal groups grouping policies |
| `Task` | Work items linked to client/policy/policy group |
| `TaskAssignment` | Which users are assigned to a task |
| `TaskNote` | Notes on tasks with status snapshots |
| `TaskTemplate` | Reusable task templates for automation |
| `SyncLog` | History of Shape import runs |
| `AuditLog` | Field-level change tracking |
| `Notification` | In-app notifications per user |
| `ShapeImportRun` | Shape file import run tracking |
## Auth flow
1. `middleware.ts` checks NextAuth session on every request under `/(dashboard)`.
2. Unauthenticated users are redirected to `/auth/signin`.
3. Production: Microsoft Entra ID OAuth. Entra group memberships map to Horizon roles via `EntraGroupRoleMapping`.
4. Dev: local credentials provider (see `src/lib/auth.ts`).
## Task completion flow
- UI: `src/app/(dashboard)/tasks/page-client.tsx` (task detail page) and `src/components/tasks/task-card.tsx` (list card)
- Dialog collects: completion date, ImageRight filing confirmation, optional reminder date
- `PATCH /api/tasks/[id]` sets `completedAt`, `completedBy`, `imageRightFiled`, `reminderDate`
## Sync / data import
- Client and policy data synced from Zywave/Applied AMS via Shape file import
- Shape import logic: `src/lib/shape-import/` and `src/lib/sync/`
- Triggered manually from Admin UI or via scheduled cron (`src/app/api/cron/`)
- Sync history tracked in `SyncLog` and `AuditLog`
## Deployment
- Production: Docker Compose at `/opt/stacks/horizon`
- Image built from this directory's `Dockerfile` (Next.js standalone output)
- DB: Postgres 17 in `horizon-db` container
- Reverse proxy: Pangolin → https://horizon.seubert.cloud