# UI_EDIT_V1_DESIGN.md

## 1. Scope

`Edit v1` is een eenvoudige teksteditor in de webui, gekoppeld aan de functiebalkactie `Edit`.

In scope:
- alleen tekstbestanden
- alleen files, geen directories
- openen, wijzigen en opslaan van tekstinhoud
- eenvoudige modal-editor

Out of scope:
- geen binary files
- geen PDF
- geen rich text
- geen collaborative editing
- geen autosave

---

## 2. Ondersteunde bestandstypen in v1

Voorstel v1:

- `txt`: ja
- `log`: ja
- `md`: ja
- `yml` / `yaml`: ja
- `json`: ja
- `js`: ja
- `css`: ja
- `html`: ja
- `Dockerfile`: ja
- `Containerfile`: ja

De allowlist blijft gelijk aan `View v1`, zodat `View` en `Edit` inhoudelijk consistent zijn.

---

## 3. UI/UX

### Openen
- `Edit` opent via de functiebalk
- alleen geldig bij exact 1 geselecteerde file
- alleen bij ondersteund teksttype

### Modal
- openen in modal boven de bestaande dual-pane UI
- modal bevat:
  - titel/header
  - bestandsnaam
  - volledig pad
  - bewerkbaar tekstgebied
  - `Save`
  - `Cancel`
  - rechtsboven `X`

### Sluiten
- `Cancel` sluit zonder opslaan
- `X` sluit zonder opslaan
- `Escape`:
  - als geen onopgeslagen wijzigingen: direct sluiten
  - als wel onopgeslagen wijzigingen: waarschuwing/bevestiging tonen

### Inhoud
- scrollbaar tekstgebied
- monospace presentatie
- selecteerbaar en bewerkbaar
- geen syntax highlighting als dat extra dependencies vraagt

### Dirty state
- modal houdt een eenvoudige `isDirty` status bij
- verschil tussen originele inhoud en huidige inhoud bepaalt of waarschuwing nodig is

---

## 4. Backend

### Nieuwe endpoint(s)

Voorstel:
- hergebruik `GET /api/files/view?path=...` voor initial read
- nieuw write-endpoint:
  - `POST /api/files/save`

Voorstel request shape:
- `path`
- `content`
- `expected_modified` of vergelijkbare timestamp/hash alleen als conflictcheck in v1 wordt gekozen

Voorstel response shape:
- `path`
- `size`
- `modified`

### Relatie met bestaand view-model

`Edit` gebruikt dezelfde type-allowlist en dezelfde padvalidatie als `View`.

Pragmatische lijn:
- `View` blijft read-only preview
- `Edit` leest initieel via `View` of een gedeelde servicefunctie
- `Save` schrijft alleen naar hetzelfde pad binnen whitelist

### Validatie

- alle paden via bestaand `path_guard`
- directories afwijzen
- unsupported types afwijzen
- write alleen binnen whitelisted roots

### Grote bestanden

Voorstel:
- dezelfde leeslimiet als `View` is **niet** voldoende voor edit
- `Edit v1` moet alleen openen tot een veilige editorlimiet, bijvoorbeeld `256 KiB` of `512 KiB`
- boven die limiet:
  - openen blokkeren met duidelijke foutmelding
  - geen partial edit voor grote bestanden in v1

Reden:
- partial content bewerken zonder volledige file-context is onveilig en verwarrend

---

## 5. Veiligheid en conflictgedrag

### Wijziging intussen op schijf

Voorstel v1:
- **wel** eenvoudige optimistic locking / modified timestamp check

Mechaniek:
- read-response bevat `modified`
- save-request stuurt `expected_modified`
- backend vergelijkt actuele `mtime`
- mismatch geeft conflictfout

Voordeel:
- beperkt risico op stil overschrijven
- technisch klein genoeg voor v1

### Readonly/permissieproblemen

Bij save:
- permissieprobleem of readonly file -> `io_error` of specifieker `permission_denied` als we die foutcode toevoegen

Voorstel:
- als bestaande foutset compact moet blijven, map dit in v1 naar `io_error` met duidelijke boodschap

### Foutmodel

Minimaal:
- `path_not_found`
- `path_traversal_detected`
- `invalid_root_alias`
- `type_conflict`
- `unsupported_type`
- `conflict`
- `io_error`

`conflict` wordt gebruikt voor modified-timestamp mismatch.

---

## 6. Scopebeperking

Niet in v1:
- geen syntax highlighting als dat extra dependencies vraagt
- geen undo/redo systeem buiten browser-native textarea gedrag
- geen find/replace
- geen multi-file edit
- geen directory edit
- geen split view diff

---

## 7. Impactanalyse

Waarschijnlijk te wijzigen backendbestanden:
- `webui/backend/app/api/routes_files.py`
- `webui/backend/app/api/schemas.py`
- `webui/backend/app/services/file_ops_service.py`
- `webui/backend/app/fs/filesystem_adapter.py`
- nieuwe golden tests voor save/edit flow

Waarschijnlijk te wijzigen frontendbestanden:
- `webui/html/index.html`
- `webui/html/app.js`
- `webui/html/style.css`
- `webui/backend/tests/golden/test_ui_smoke_golden.py`

### Regressierisico

- `Edit` enabled/disabled toestand kan verkeerd meelopen met huidige selectie
- modal-keyboardgedrag kan botsen met paneelnavigatie
- save-conflict of dirty-state kan leiden tot onduidelijk UX-gedrag
- onveilige overschrijving zonder conflictcheck moet vermeden worden

Mitigatie:
- dezelfde selectievoorwaarden als `View`
- keyboard shortcuts blokkeren zolang editor open is
- expliciete dirty-state en save-conflict handling

---

## 8. Teststrategie

### Golden tests

Voor backend:
- edit/open success voor ondersteund tekstbestand
- save success
- unsupported type
- directory -> type conflict
- path not found
- traversal attempt
- conflict bij gewijzigde file
- io_error bij write failure

### UI smoke/regressietests

Aanpassen:
- `Edit` knop aanwezig in functiebalk
- edit-modal container aanwezig in HTML
- save/cancel controls aanwezig

### Handmatige validatie

- `Edit` enabled bij exact 1 ondersteunde file
- `Edit` disabled bij:
  - geen selectie
  - meerdere selectie
  - directoryselectie
  - unsupported filetype
- modal opent met juiste inhoud
- `Save` schrijft wijziging correct weg
- `Cancel` sluit zonder opslaan
- `Escape` sluit alleen veilig volgens dirty-state regel
- conflictmelding bij tussentijdse externe wijziging
