--- title: Domain Model created: 2026-04-08 updated: 2026-04-08 status: evolving tags: [domain, models, relationships, lifecycle] sources: [app/Models/, app/Enums/, database/migrations/] --- # Domain Model 21 Eloquent models organized in 8 layers, with 14 enums for type safety. ## Entity Relationship Overview ``` Thema (strategic theme) └── Speerpunt (focus area) └── Project (innovation project) ├── Fase (lifecycle phase) ├── Risico (risk) ├── Commitment → Actie (action) ├── Besluit (decision) → Commitment ├── Budget → Besteding (expenditure) ├── Document ← Tag (M:N) ├── LessonLearned ├── Afhankelijkheid (dependency, Project ↔ Project) ├── Overdrachtsplan (handover plan) │ ├── Criterium │ └── Acceptatie └── ProjectUser (team membership, pivot) User ──── Role (M:N) AuditLog (append-only, all mutations) KennisArtikel ← Tag (M:N) ``` ## Layer Details ### Strategic Layer | Model | Key Fields | Relationships | |---|---|---| | **Thema** | naam, beschrijving, prioriteit, periode | has many Speerpunten | | **Speerpunt** | naam, beschrijving, eigenaar, status | belongs to Thema, has many Projects | | **RoadmapItem** | titel, start, eind, type, status | belongs to Thema | ### Project Layer | Model | Key Fields | Relationships | |---|---|---| | **Project** | naam, beschrijving, eigenaar_id, status, prioriteit, startdatum, streef_einddatum | SoftDeletes, belongs to Speerpunt + User (eigenaar), has many of everything | | **Fase** | type (enum), status (enum), startdatum, einddatum, opmerkingen | belongs to Project | | **Risico** | beschrijving, impact, kans, mitigatie, eigenaar | belongs to Project | | **Afhankelijkheid** | type, beschrijving, status | self-referential N:M between Projects | ### Commitment Layer | Model | Key Fields | Relationships | |---|---|---| | **Commitment** | beschrijving, eigenaar_id, deadline, status, bron | belongs to Project + Besluit, has many Acties | | **Actie** | beschrijving, eigenaar_id, deadline, status, prioriteit | belongs to Commitment | ### Governance Layer | Model | Key Fields | Relationships | |---|---|---| | **Besluit** | titel, beschrijving, datum, type, status, onderbouwing | belongs to Project, has many Commitments | | **Budget** | bedrag, type, periode, status | belongs to Project, has many Bestedingen | | **Besteding** | bedrag, beschrijving, datum, categorie | belongs to Budget | ### Knowledge Layer | Model | Key Fields | Relationships | |---|---|---| | **Document** | titel, type, inhoud, versie, auteur, datum, **embedding** (vector) | belongs to Project + Fase, M:N Tags | | **KennisArtikel** | titel, inhoud, tags, auteur, datum, **embedding** (vector) | M:N Tags | | **LessonLearned** | titel, inhoud, project, fase, tags | belongs to Project + Fase | | **Tag** | naam, categorie | M:N with Documents, KennisArtikels | ### Handover Layer | Model | Key Fields | Relationships | |---|---|---| | **Overdrachtsplan** | type, status, eigenaar_rnd, eigenaar_ontvanger | belongs to Project, has many Criteria + Acceptaties | | **Criterium** | beschrijving, status, verificatie | belongs to Overdrachtsplan | | **Acceptatie** | datum, door, opmerkingen, status | belongs to Overdrachtsplan | ### Auth Layer | Model | Key Fields | Relationships | |---|---|---| | **User** | name, email, password, phone, afdeling, functie, 2FA fields | has many ProjectUsers, can own Projects/Commitments/Risicos | | **Role** | naam, beschrijving, permissies | M:N with Users | | **ProjectUser** | project_id, user_id, rol (enum) | pivot table | ### System Layer | Model | Key Fields | Relationships | |---|---|---| | **AuditLog** | user_id, action, entity_type, entity_id, payload (JSON) | append-only | ## Innovation Lifecycle Phases (FaseType enum) ``` signaal → verkenning → concept → experiment → pilot → besluitvorming → overdracht_bouwen → overdracht_beheer → evaluatie ``` Special statuses (ProjectStatus only, not FaseType): - `geparkeerd` — temporarily halted - `gestopt` — permanently stopped - `afgerond` — completed ## Key Design Decisions 1. **Dutch naming** — all models, fields, enums use Dutch names to match domain language 2. **Soft deletes on Project only** — projects are never hard-deleted 3. **Embedding vectors on Document + KennisArtikel** — pgvector columns for semantic search 4. **ProjectUser pivot with role** — team membership is role-typed (Eigenaar, Lid, Reviewer, Stakeholder) 5. **FaseType maps 1:1 to first 9 ProjectStatus values** — `FaseType::tryFrom($projectStatus->value)` is used for phase transitions