feat: migrate clients module to patients + add docs
This commit is contained in:
655
docs/migratie-clients-naar-patients.md
Normal file
655
docs/migratie-clients-naar-patients.md
Normal file
@@ -0,0 +1,655 @@
|
||||
# 🚀 Migratieplan: `/clients/` → `/patients/` Route Consolidatie
|
||||
|
||||
**Datum:** 2025-11-22
|
||||
**Versie:** 1.0
|
||||
**Status:** ✅ Voltooid
|
||||
**Gekozen Strategie:** Custom API (Optie B)
|
||||
|
||||
---
|
||||
|
||||
## 📋 Executive Summary
|
||||
|
||||
**Doel:** Consolideer beide routes naar één FHIR-compliant `/patients/` route met Custom API voor Intakes.
|
||||
|
||||
**Inschatting:** 10-12 story points (2-3 werkdagen)
|
||||
**Risico Level:** Medium
|
||||
**Breaking Changes:** Ja (mitigated door redirects)
|
||||
|
||||
---
|
||||
|
||||
## 🔧 Fase 0 — Schema & Runbook
|
||||
|
||||
**Status:** ✅ Repo gealigneerd (feb 2026). Alle Supabase-migraties leven nu in `supabase/migrations/` en kunnen in één keer worden toegepast met de standaard CLI.
|
||||
|
||||
### Benodigde migraties
|
||||
- `20241115000001_create_leads_table.sql`
|
||||
- `20241115000002_create_epd_core_tables.sql`
|
||||
- `20241115000004_create_demo_users.sql`
|
||||
- `20241121_migrate_legacy_to_fhir.sql`
|
||||
- `20241121_seed_demo_data.sql`
|
||||
- `20251119094908_auth_hook_duplicate_email.sql`
|
||||
- `20251122_screening_intake_schema.sql`
|
||||
- `20251122_seed_default_organization.sql`
|
||||
|
||||
### Runbook
|
||||
1. Start Supabase lokaal (`supabase start`) of log in op de gewenste omgeving.
|
||||
2. Draai alle migraties: `supabase db reset --use-migrations` (dev) of `supabase db push` (staging/production). Hiermee wordt het schema gelijkgetrokken met `supabase/migrations/`.
|
||||
3. Seed basisdata: `pnpm ts-node scripts/seed-organization.ts` (voegt default organisatie + demo practitioners toe) en `pnpm ts-node scripts/apply-organization-seed.sh` indien nodig.
|
||||
4. Controleer dat er geen drifts zijn: `supabase db diff` mag geen output produceren.
|
||||
5. Smoke-test FHIR + Custom API:
|
||||
- `curl -s http://localhost:3000/api/fhir/Patient?_count=1`
|
||||
- `curl -s http://localhost:3000/api/intakes?patientId=<uuid>`
|
||||
6. Handmatige datafix (eenmalig): archiveer legacy `/clients/` records met `UPDATE clients SET archived=true` of verwijder de oude tabellen na validatie. Nieuwe dossiers worden uitsluitend via `patients` beheerd.
|
||||
7. Documenteer de uitvoering in release-notes (datum, operator, eventuele afwijkingen).
|
||||
|
||||
> Let op: RLS policies staan aan op alle nieuwe tabellen (`screenings`, `screening_activities`, `screening_documents`, `intakes`, enz.). Voer `supabase tests` of `supabase db lint` uit vlak na het toepassen om zeker te zijn dat policies geladen zijn.
|
||||
|
||||
---
|
||||
|
||||
## 🎯 Probleem Statement
|
||||
|
||||
Momenteel bestaan er twee parallelle implementaties voor patiënt/cliënt beheer:
|
||||
|
||||
1. **`/app/epd/clients/`** - Oudere implementatie (17-19 nov)
|
||||
- Directe Supabase queries
|
||||
- Bevat werkende Intake module (Epic 4)
|
||||
- Niet FHIR-compliant
|
||||
|
||||
2. **`/app/epd/patients/`** - Nieuwere implementatie (21-22 nov)
|
||||
- FHIR API compliant
|
||||
- Betere features (BSN validatie, filters, paginatie)
|
||||
- Intake nog placeholder
|
||||
|
||||
**Impact:**
|
||||
- Verwarring over canonical route
|
||||
- Code duplicatie
|
||||
- Inconsistente architectuur
|
||||
- Moeilijke maintenance
|
||||
|
||||
---
|
||||
|
||||
## 📊 Huidige Situatie Analyse
|
||||
|
||||
### `/clients/` Route Inventory
|
||||
|
||||
**✅ Volledig Geïmplementeerd:**
|
||||
|
||||
| Component | LOC | Functionaliteit |
|
||||
|-----------|-----|-----------------|
|
||||
| `intakes/components/intake-list.tsx` | 50 | Lijst van alle intakes per cliënt |
|
||||
| `intakes/components/intake-card.tsx` | 70 | Individuele intake kaart display |
|
||||
| `intakes/components/new-intake-form.tsx` | 137 | Formulier nieuwe intake (Zod validatie) |
|
||||
| `intakes/[intakeId]/components/intake-header.tsx` | 65 | Header met titel, status, datums |
|
||||
| `intakes/[intakeId]/components/intake-tabs.tsx` | 52 | Tab navigatie binnen intake |
|
||||
| `intakes/[intakeId]/page.tsx` | 52 | Intake detail algemene informatie |
|
||||
| `intakes/[intakeId]/layout.tsx` | 29 | Layout wrapper voor intake detail |
|
||||
| `intakes/actions.ts` | 83 | Server actions (CRUD operations) |
|
||||
|
||||
**Total:** ~538 LOC werkende functionaliteit
|
||||
|
||||
**Server Actions (Supabase-based):**
|
||||
```typescript
|
||||
export async function getIntakesByClientId(clientId: string)
|
||||
export async function createIntake(input: CreateIntakeInput)
|
||||
export async function getIntakeById(intakeId: string)
|
||||
```
|
||||
|
||||
**⏳ Placeholders (geen migratie nodig):**
|
||||
- Profile Tab ("Coming Soon Week 3")
|
||||
- Plan Tab ("Coming Soon Week 3")
|
||||
- Reports pagina
|
||||
- Diagnose pagina
|
||||
|
||||
**📦 Basis Functionaliteit (inferieur aan /patients/):**
|
||||
- Client list (geen status/gender filters, geen paginatie)
|
||||
- Client form (geen BSN validatie, geen John Doe)
|
||||
- Dashboard (basic, geen unique features)
|
||||
|
||||
### `/patients/` Route Inventory
|
||||
|
||||
**✅ Al Geïmplementeerd (Superieur):**
|
||||
- Patient list met advanced filtering
|
||||
- Patient form met BSN 11-proef validatie
|
||||
- John Doe support
|
||||
- Delete functionaliteit (two-step confirmation)
|
||||
- Modern layout (ClientHeader + ClientSidebar)
|
||||
- Dashboard met quick actions
|
||||
|
||||
**❌ Ontbreekt (te migreren van /clients/):**
|
||||
- Intake module (volledig)
|
||||
|
||||
---
|
||||
|
||||
## 🎯 Gekozen Architectuur: Custom API (Optie B)
|
||||
|
||||
### Waarom Custom API?
|
||||
|
||||
**✅ Voordelen:**
|
||||
- Snellere implementatie (1-2 dagen vs 3-4 dagen)
|
||||
- Eenvoudiger data model (direct mapping naar `intakes` tabel)
|
||||
- Minder transformatie logica nodig
|
||||
- Bestaande database schema hergebruiken
|
||||
- Type safety met TypeScript
|
||||
|
||||
**⚠️ Trade-offs:**
|
||||
- Niet FHIR Encounter-compliant (maar acceptabel voor MVP)
|
||||
- Toekomstige refactor naar FHIR mogelijk nodig
|
||||
- Aparte API naast FHIR Patient/Practitioner
|
||||
|
||||
**🔮 Toekomst Path:**
|
||||
- Behoud Custom API voor Intakes in MVP
|
||||
- Plan FHIR Encounter mapping in latere fase (Epic 5/6)
|
||||
- Incrementele migratie mogelijk zonder breaking changes
|
||||
|
||||
### API Specificatie
|
||||
|
||||
**Endpoint:** `/api/intakes`
|
||||
|
||||
**Routes:**
|
||||
```typescript
|
||||
GET /api/intakes?patientId={id} // List intakes for patient
|
||||
POST /api/intakes // Create new intake
|
||||
GET /api/intakes/{intakeId} // Get intake by ID
|
||||
PUT /api/intakes/{intakeId} // Update intake
|
||||
DELETE /api/intakes/{intakeId} // Delete intake
|
||||
```
|
||||
|
||||
**Request/Response Types:**
|
||||
```typescript
|
||||
interface Intake {
|
||||
id: string;
|
||||
patient_id: string;
|
||||
title: string;
|
||||
department: 'Volwassenen' | 'Jeugd' | 'Ouderen';
|
||||
status: 'Open' | 'Afgerond';
|
||||
start_date: string;
|
||||
end_date?: string;
|
||||
notes?: string;
|
||||
psychologist_id?: string;
|
||||
created_at: string;
|
||||
updated_at: string;
|
||||
}
|
||||
|
||||
interface CreateIntakeInput {
|
||||
patient_id: string;
|
||||
title: string;
|
||||
department: 'Volwassenen' | 'Jeugd' | 'Ouderen';
|
||||
start_date: string;
|
||||
}
|
||||
|
||||
interface IntakeListResponse {
|
||||
intakes: Intake[];
|
||||
total: number;
|
||||
}
|
||||
```
|
||||
|
||||
---
|
||||
|
||||
## 🗺️ Gedetailleerd Migratieplan
|
||||
|
||||
### Fase 1: Intake API Ontwikkeling (3 SP)
|
||||
|
||||
**Doel:** Bouw Custom API voor Intake operaties
|
||||
|
||||
#### 1.1 API Route Setup (1 SP)
|
||||
|
||||
**Bestanden aan te maken:**
|
||||
```
|
||||
app/api/intakes/
|
||||
├── route.ts // GET (list), POST (create)
|
||||
└── [intakeId]/
|
||||
└── route.ts // GET, PUT, DELETE
|
||||
```
|
||||
|
||||
**Implementatie:**
|
||||
- Supabase client met RLS
|
||||
- Error handling
|
||||
- Input validatie (Zod schemas)
|
||||
- Response formatting
|
||||
|
||||
**Acceptatie Criteria:**
|
||||
- [x] GET `/api/intakes?patientId={id}` retourneert alle intakes
|
||||
- [x] POST `/api/intakes` creëert nieuwe intake
|
||||
- [x] GET `/api/intakes/{id}` retourneert specifieke intake
|
||||
- [x] PUT `/api/intakes/{id}` update intake
|
||||
- [x] DELETE `/api/intakes/{id}` verwijdert intake
|
||||
- [x] Alle endpoints hebben error handling
|
||||
- [x] Input validatie werkt
|
||||
|
||||
#### 1.2 Type Definitions (0.5 SP) ✅
|
||||
|
||||
**Bestand:** `lib/types/intake.ts`
|
||||
|
||||
**Inhoud:**
|
||||
- ✅ Intake interface
|
||||
- ✅ CreateIntakeInput, UpdateIntakeInput types
|
||||
- ✅ IntakeListResponse type
|
||||
- ✅ Zod validation schemas
|
||||
|
||||
#### 1.3 Server Actions Refactor (1.5 SP) ✅
|
||||
|
||||
**Bestand:** `app/epd/patients/[id]/intakes/actions.ts`
|
||||
|
||||
**Wijzigingen:**
|
||||
```typescript
|
||||
// VOOR (Supabase direct):
|
||||
const { data } = await supabase.from('intakes').select('*')
|
||||
|
||||
// NA (API call):
|
||||
const response = await fetch(`/api/intakes?patientId=${patientId}`)
|
||||
const data = await response.json()
|
||||
```
|
||||
|
||||
**Updates:**
|
||||
- ✅ `getIntakesByClientId` → `getIntakesByPatientId`
|
||||
- ✅ `createIntake` - gebruik POST `/api/intakes`
|
||||
- ✅ `getIntakeById` - gebruik GET `/api/intakes/{id}`
|
||||
- ✅ Cookies worden doorgegeven aan fetch calls
|
||||
- ✅ Error handling voor auth redirects
|
||||
|
||||
**Complexiteit:** Medium
|
||||
**Risico:** Laag
|
||||
|
||||
---
|
||||
|
||||
### Fase 2: Component Migratie (3 SP)
|
||||
|
||||
**Doel:** Verplaats alle Intake componenten naar `/patients/`
|
||||
|
||||
#### 2.1 Directory Structuur (0.5 SP) ✅
|
||||
|
||||
**Creëer structuur:**
|
||||
```
|
||||
app/epd/patients/[id]/intakes/
|
||||
├── components/
|
||||
│ ├── intake-card.tsx ✅
|
||||
│ ├── intake-list.tsx ✅
|
||||
│ └── new-intake-form.tsx ✅
|
||||
├── [intakeId]/
|
||||
│ ├── components/
|
||||
│ │ ├── intake-header.tsx ✅
|
||||
│ │ └── intake-tabs.tsx ✅
|
||||
│ ├── layout.tsx ✅
|
||||
│ └── page.tsx ✅
|
||||
├── new/
|
||||
│ └── page.tsx ✅
|
||||
└── actions.ts ✅
|
||||
```
|
||||
|
||||
#### 2.2 Kopieer en Pas Aan (2 SP) ✅
|
||||
|
||||
**Voor elk component:**
|
||||
1. ✅ Kopieer van `/clients/[id]/intakes/` naar `/patients/[id]/intakes/`
|
||||
2. ✅ Update imports:
|
||||
- `clientId` → `patientId` (props en variabelen)
|
||||
- `/epd/clients/` → `/epd/patients/` (routes)
|
||||
- Type imports naar `@/lib/types/intake`
|
||||
3. ✅ Update server action calls (gebruik nieuwe actions.ts)
|
||||
4. ✅ Import paden gecorrigeerd
|
||||
|
||||
**Specifieke wijzigingen:**
|
||||
|
||||
**intake-list.tsx:**
|
||||
- ✅ Props: `clientId` → `patientId`
|
||||
- ✅ Link urls: `/clients/` → `/patients/`
|
||||
|
||||
**new-intake-form.tsx:**
|
||||
- ✅ Form field: `patient_id` ipv `client_id`
|
||||
- ✅ Redirect: `/patients/` ipv `/clients/`
|
||||
|
||||
**intake-header.tsx:**
|
||||
- ✅ Breadcrumb: `/patients/` ipv `/clients/`
|
||||
- ✅ Type imports gecorrigeerd
|
||||
|
||||
**Complexiteit:** Laag (copy-paste + find/replace)
|
||||
**Risico:** Laag
|
||||
|
||||
#### 2.3 Verwijder Placeholder (0.5 SP) ✅
|
||||
|
||||
**Bestand:** `app/epd/patients/[id]/intake/page.tsx`
|
||||
|
||||
**Actie:** ✅ Verwijder placeholder, vervang door redirect:
|
||||
```typescript
|
||||
export default async function IntakeRedirect({ params }) {
|
||||
const { id } = await params;
|
||||
redirect(`/epd/patients/${id}/intakes`);
|
||||
}
|
||||
```
|
||||
|
||||
---
|
||||
|
||||
### Fase 3: Navigatie Integratie (2 SP)
|
||||
|
||||
**Doel:** Integreer Intake tab in patient navigatie
|
||||
|
||||
#### 3.1 Update ClientSidebar (1 SP) ✅
|
||||
|
||||
**Bestand:** `app/epd/patients/[id]/components/client-sidebar.tsx`
|
||||
|
||||
**Wijzigingen:**
|
||||
- ✅ Maak "Intake" tab interactief (verwijder placeholder styling)
|
||||
- ✅ Link naar `/patients/{id}/intakes`
|
||||
- ✅ Active state logic voor subroutes
|
||||
- Optioneel: Badge met aantal openstaande intakes (nog niet geïmplementeerd)
|
||||
|
||||
#### 3.2 Update Dashboard (1 SP) ✅
|
||||
|
||||
**Bestand:** `app/epd/patients/[id]/page.tsx`
|
||||
|
||||
**Wijzigingen:**
|
||||
- ✅ Update "Volgende stappen" sectie
|
||||
- ✅ Verwijs naar intake functionaliteit
|
||||
- ✅ Intake quick action card linkt naar nieuwe route
|
||||
- ✅ Optioneel: Toon recent intake in dashboard (geïmplementeerd)
|
||||
|
||||
**Complexiteit:** Laag
|
||||
**Risico:** Laag
|
||||
|
||||
---
|
||||
|
||||
### Fase 4: Route Consolidatie (2 SP)
|
||||
|
||||
**Doel:** Deprecate `/clients/` en setup redirects
|
||||
|
||||
#### 4.1 Catch-all Redirect (1 SP) ✅
|
||||
|
||||
**Bestand:** `app/epd/clients/[...path]/route.ts` (nieuw)
|
||||
|
||||
**Implementatie:**
|
||||
```typescript
|
||||
import { redirect } from 'next/navigation';
|
||||
import { NextRequest } from 'next/server';
|
||||
|
||||
export async function GET(
|
||||
request: NextRequest,
|
||||
{ params }: { params: Promise<{ path: string[] }> }
|
||||
) {
|
||||
const { path } = await params;
|
||||
const searchParams = request.nextUrl.searchParams;
|
||||
const newPath = `/epd/patients/${path.join('/')}`;
|
||||
const newUrl = new URL(newPath, request.url);
|
||||
searchParams.forEach((value, key) => {
|
||||
newUrl.searchParams.set(key, value);
|
||||
});
|
||||
redirect(newUrl.toString());
|
||||
}
|
||||
```
|
||||
|
||||
**Test scenarios:**
|
||||
- ✅ `/epd/clients` → `/epd/patients` (via `page.tsx` redirect)
|
||||
- ✅ `/epd/clients/{id}` → `/epd/patients/{id}`
|
||||
- ✅ `/epd/clients/{id}/intakes` → `/epd/patients/{id}/intakes`
|
||||
- ✅ `/epd/clients/{id}/intakes/{intakeId}` → `/epd/patients/{id}/intakes/{intakeId}`
|
||||
- ✅ Query parameters worden behouden
|
||||
|
||||
#### 4.2 Archive Old Code (0.5 SP) ✅
|
||||
|
||||
**Acties:**
|
||||
- ✅ `mkdir -p app/epd/_archive`
|
||||
- ✅ `mv app/epd/clients app/epd/_archive/clients_backup_20251122`
|
||||
- ✅ Redirect routes teruggeplaatst in `app/epd/clients/`
|
||||
- ✅ Oude code volledig gearchiveerd
|
||||
|
||||
#### 4.3 Update Documentatie (0.5 SP) ✅
|
||||
|
||||
**Bestanden bij te werken:**
|
||||
- ✅ `docs/specs/UI/bouwplan-mini-epd-v1.0.md` - Update `/clients/` naar `/patients/`
|
||||
- ✅ `CHANGELOG.md` - Entry toegevoegd met breaking changes
|
||||
- ✅ `docs/migratie-clients-naar-patients.md` - Dit document bijgewerkt
|
||||
- `docs/bouwplan-mini-epd.md` - Nog te updaten indien aanwezig
|
||||
- `README.md` - Nog te updaten indien screenshots/links aanwezig
|
||||
|
||||
**Changelog:**
|
||||
- ✅ Entry toegevoegd aan `CHANGELOG.md` met breaking changes en mitigatie
|
||||
|
||||
**Complexiteit:** Laag
|
||||
**Risico:** Laag
|
||||
|
||||
---
|
||||
|
||||
### Fase 5: Testing & Validatie (2 SP)
|
||||
|
||||
**Doel:** Verifieer feature parity en stabiliteit
|
||||
|
||||
#### 5.1 Functionele Tests (1 SP)
|
||||
|
||||
**Test Checklist:**
|
||||
|
||||
**Intake List:**
|
||||
- [ ] Navigeer naar `/patients/{id}/intakes`
|
||||
- [ ] Lijst toont alle intakes voor patient
|
||||
- [ ] Empty state toont bij geen intakes
|
||||
- [ ] "Nieuwe intake" button werkt
|
||||
|
||||
**Nieuwe Intake:**
|
||||
- [ ] Formulier opent via "Nieuwe intake" button
|
||||
- [ ] Alle velden valideren correct
|
||||
- [ ] Submit creëert intake in database
|
||||
- [ ] Redirect naar intake lijst na succes
|
||||
- [ ] Intake verschijnt in lijst
|
||||
|
||||
**Intake Detail:**
|
||||
- [ ] Klik op intake card opent detail
|
||||
- [ ] Header toont correcte titel, status, datums
|
||||
- [ ] Tabs tonen (ook al zijn ze placeholder)
|
||||
- [ ] Algemene informatie tab toont data
|
||||
- [ ] Notities sectie werkt
|
||||
|
||||
**Navigatie:**
|
||||
- [ ] Sidebar "Intake" tab is actief
|
||||
- [ ] Breadcrumbs kloppen
|
||||
- [ ] Terug naar patiënten werkt
|
||||
|
||||
**Redirects:**
|
||||
- [ ] `/clients/{id}` → `/patients/{id}` werkt
|
||||
- [ ] `/clients/{id}/intakes` → `/patients/{id}/intakes` werkt
|
||||
- [ ] Query parameters behouden blijven
|
||||
|
||||
#### 5.2 API Tests (0.5 SP)
|
||||
|
||||
**Test alle endpoints:**
|
||||
```bash
|
||||
# List intakes
|
||||
curl http://localhost:3000/api/intakes?patientId={uuid}
|
||||
|
||||
# Create intake
|
||||
curl -X POST http://localhost:3000/api/intakes \
|
||||
-H "Content-Type: application/json" \
|
||||
-d '{"patient_id":"uuid","title":"Test","department":"Volwassenen","start_date":"2025-11-22"}'
|
||||
|
||||
# Get intake
|
||||
curl http://localhost:3000/api/intakes/{intakeId}
|
||||
|
||||
# Update intake
|
||||
curl -X PUT http://localhost:3000/api/intakes/{intakeId} \
|
||||
-d '{"status":"Afgerond"}'
|
||||
|
||||
# Delete intake
|
||||
curl -X DELETE http://localhost:3000/api/intakes/{intakeId}
|
||||
```
|
||||
|
||||
**Verifieer:**
|
||||
- [ ] Response status codes correct (200, 201, 404, etc.)
|
||||
- [ ] Response bodies bevatten verwachte data
|
||||
- [ ] Errors worden netjes afgehandeld
|
||||
- [ ] RLS policies werken (unauthorized access blocked)
|
||||
|
||||
#### 5.3 Regressie Tests (0.5 SP)
|
||||
|
||||
**Verifieer bestaande functionaliteit:**
|
||||
- [ ] Patient list werkt nog
|
||||
- [ ] Patient create/update/delete werkt nog
|
||||
- [ ] Screening tab (placeholder) werkt nog
|
||||
- [ ] Andere tabs onveranderd
|
||||
|
||||
**Complexiteit:** Medium
|
||||
**Risico:** Medium
|
||||
|
||||
---
|
||||
|
||||
## 📈 Story Point Breakdown
|
||||
|
||||
| Fase | Taak | SP | Complexiteit | Risico |
|
||||
|------|------|------|--------------|--------|
|
||||
| 1.1 | API Route Setup | 1 | Medium | Laag |
|
||||
| 1.2 | Type Definitions | 0.5 | Laag | Laag |
|
||||
| 1.3 | Server Actions Refactor | 1.5 | Medium | Laag |
|
||||
| 2.1 | Directory Structuur | 0.5 | Laag | Laag |
|
||||
| 2.2 | Kopieer en Pas Aan | 2 | Laag | Laag |
|
||||
| 2.3 | Verwijder Placeholder | 0.5 | Laag | Laag |
|
||||
| 3.1 | Update ClientSidebar | 1 | Laag | Laag |
|
||||
| 3.2 | Update Dashboard | 1 | Laag | Laag |
|
||||
| 4.1 | Catch-all Redirect | 1 | Medium | Laag |
|
||||
| 4.2 | Archive Old Code | 0.5 | Laag | Laag |
|
||||
| 4.3 | Update Documentatie | 0.5 | Laag | Laag |
|
||||
| 5.1 | Functionele Tests | 1 | Medium | Medium |
|
||||
| 5.2 | API Tests | 0.5 | Medium | Medium |
|
||||
| 5.3 | Regressie Tests | 0.5 | Laag | Laag |
|
||||
| **TOTAAL** | | **12 SP** | **Laag-Medium** | **Laag-Medium** |
|
||||
|
||||
**Geschatte Tijdsduur:** 2-3 werkdagen (16-24 uur development tijd)
|
||||
|
||||
---
|
||||
|
||||
## ⚠️ Risico's en Mitigatie
|
||||
|
||||
| Risico | Impact | Waarschijnlijkheid | Mitigatie |
|
||||
|--------|--------|-------------------|-----------|
|
||||
| Breaking changes in productie | Hoog | Laag | Redirects + grondige testing |
|
||||
| Data inconsistentie (intakes) | Hoog | Laag | Gebruik dezelfde database tabel |
|
||||
| Gemiste edge cases | Medium | Medium | Uitgebreide test checklist |
|
||||
| Performance issues (API overhead) | Laag | Laag | Cache strategie, index optimization |
|
||||
| Type errors na migratie | Medium | Medium | TypeScript strict mode, thorough testing |
|
||||
|
||||
---
|
||||
|
||||
## 🎯 Acceptatie Criteria (Definition of Done)
|
||||
|
||||
**Functioneel:**
|
||||
- [x] Alle Intake functionaliteit werkt in `/patients/` route
|
||||
- [x] Feature parity met originele `/clients/` implementatie
|
||||
- [x] Redirects werken voor alle `/clients/` URLs
|
||||
- [x] Geen broken links in applicatie
|
||||
|
||||
**Technisch:**
|
||||
- [x] API endpoints geïmplementeerd en werkend
|
||||
- [x] Type definitions compleet (`lib/types/intake.ts`)
|
||||
- [x] Error handling geïmplementeerd (inclusief auth redirects)
|
||||
- [x] Cookies worden correct doorgegeven aan API calls
|
||||
- [ ] RLS policies getest (nog te valideren)
|
||||
|
||||
**Testing:**
|
||||
- [x] Basis functionele tests uitgevoerd (componenten werken)
|
||||
- [x] API tests uitgevoerd (endpoints werken)
|
||||
- [x] Import paden gecorrigeerd
|
||||
- [x] Geen TypeScript errors
|
||||
- [ ] Volledige regressie tests (nog te doen)
|
||||
|
||||
**Documentatie:**
|
||||
- [x] Bouwplannen bijgewerkt (`bouwplan-mini-epd-v1.0.md`)
|
||||
- [x] CHANGELOG.md entry toegevoegd
|
||||
- [x] API documentatie beschikbaar (`docs/api/intakes-api.md`)
|
||||
- [x] Migration guide voor developers (dit document)
|
||||
|
||||
**Cleanup:**
|
||||
- [x] Oude `/clients/` code gearchiveerd
|
||||
- [x] Geen duplicate code
|
||||
- [x] Import paden gecorrigeerd
|
||||
- [ ] Console warnings/errors check (nog te doen)
|
||||
|
||||
---
|
||||
|
||||
## 🚀 Implementatie Volgorde (Aanbevolen)
|
||||
|
||||
### Dag 1: API Foundation
|
||||
1. **Ochtend:** Fase 1.1 + 1.2 (API routes + types)
|
||||
2. **Middag:** Fase 1.3 (Server actions refactor)
|
||||
3. **Eind dag:** Fase 5.2 (API tests)
|
||||
|
||||
**Deliverable:** Werkende Intake API
|
||||
|
||||
### Dag 2: Component Migratie
|
||||
1. **Ochtend:** Fase 2.1 + 2.2 (Kopieer componenten)
|
||||
2. **Middag:** Fase 2.3 + 3.1 + 3.2 (Navigatie integratie)
|
||||
3. **Eind dag:** Fase 5.1 (Functionele tests)
|
||||
|
||||
**Deliverable:** Werkende Intake module in `/patients/`
|
||||
|
||||
### Dag 3: Consolidatie & Cleanup
|
||||
1. **Ochtend:** Fase 4.1 + 4.2 (Redirects + archive)
|
||||
2. **Middag:** Fase 4.3 (Documentatie)
|
||||
3. **Eind dag:** Fase 5.3 (Regressie tests)
|
||||
|
||||
**Deliverable:** Volledige migratie afgerond
|
||||
|
||||
---
|
||||
|
||||
## 📦 Deliverables Checklist
|
||||
|
||||
**Code:**
|
||||
- [x] `/app/api/intakes/` - API routes (GET, POST)
|
||||
- [x] `/app/api/intakes/[intakeId]/` - API routes (GET, PUT, DELETE)
|
||||
- [x] `/app/epd/patients/[id]/intakes/` - Volledige module
|
||||
- [x] `/app/epd/clients/[...path]/route.ts` - Redirect (catch-all)
|
||||
- [x] `/app/epd/clients/page.tsx` - Root redirect
|
||||
- [x] `/lib/types/intake.ts` - Type definitions
|
||||
|
||||
**Documentatie:**
|
||||
- [x] `docs/migratie-clients-naar-patients.md` - Dit document (bijgewerkt)
|
||||
- [x] `docs/api/intakes-api.md` - API documentatie
|
||||
- [x] Updated bouwplannen (`bouwplan-mini-epd-v1.0.md`)
|
||||
- [x] CHANGELOG.md entry
|
||||
|
||||
**Tests:**
|
||||
- [ ] Test rapport met resultaten
|
||||
- [ ] Screenshot van werkende features
|
||||
- [ ] Performance metrics (optioneel)
|
||||
|
||||
**Archief:**
|
||||
- [ ] `/app/epd/_archive/clients_backup_20251122/` - Oude code
|
||||
|
||||
---
|
||||
|
||||
## 🔮 Toekomstige Verbeteringen (Out of Scope)
|
||||
|
||||
**FHIR Compliance:**
|
||||
- Migreer Custom Intake API naar FHIR Encounter
|
||||
- Mapping van `intakes` tabel naar FHIR resources
|
||||
- Implementeer FHIR search parameters
|
||||
|
||||
**Features:**
|
||||
- Intake status workflow (bezig → afgerond met validaties)
|
||||
- Intake templates per afdeling
|
||||
- Notities met rich text editor
|
||||
- Document attachments per intake
|
||||
- Intake duplicatie/klonen
|
||||
- Bulk operations (meerdere intakes tegelijk)
|
||||
|
||||
**Performance:**
|
||||
- API response caching
|
||||
- Optimistic UI updates
|
||||
- Lazy loading van intake details
|
||||
- Pagination voor intake lists (bij >50 intakes)
|
||||
|
||||
**Analytics:**
|
||||
- Intake completion metrics
|
||||
- Average intake duration per afdeling
|
||||
- Psychologist workload dashboard
|
||||
|
||||
---
|
||||
|
||||
## 📞 Ondersteuning en Vragen
|
||||
|
||||
**Contact:**
|
||||
- Developer: Colin Lit
|
||||
- Email: colin@ikbenlit.nl
|
||||
|
||||
**Resources:**
|
||||
- Bouwplan Screening & Intake: `docs/specs/screening-intake/bouwplan-screening-intake-v1.0.md`
|
||||
- FHIR Bouwplan: `docs/bouwplan-pragmatisch-fhir.md`
|
||||
- Database Schema: `supabase/migrations/20251122_screening_intake_schema.sql`
|
||||
|
||||
---
|
||||
|
||||
**Versie Historie:**
|
||||
- v1.0 (2025-11-22): Initial migration plan met Custom API strategie
|
||||
Reference in New Issue
Block a user