From f9246d4463d64fd9a881a93b38cfad2998ebf96f Mon Sep 17 00:00:00 2001 From: Urban Modig Date: Sun, 26 Jul 2026 13:03:01 +0200 Subject: [PATCH] docs: establish project documentation baseline --- AGENTS.md | 5 +- README.md | 12 ++ docs/architecture.md | 183 ++++++++++++++++++ docs/decisions/001-monorepo.md | 28 +++ docs/decisions/002-same-origin-api-proxy.md | 32 +++ .../003-central-users-local-active-user.md | 34 ++++ docs/decisions/004-feature-branch-workflow.md | 30 +++ .../005-production-deployment-direction.md | 52 +++++ docs/development.md | 58 ++++++ docs/features/000-project-foundation.md | 76 ++++++++ docs/features/001-user-selection.md | 99 ++++++++++ docs/features/002-task-creation.md | 108 +++++++++++ 12 files changed, 716 insertions(+), 1 deletion(-) create mode 100644 docs/architecture.md create mode 100644 docs/decisions/001-monorepo.md create mode 100644 docs/decisions/002-same-origin-api-proxy.md create mode 100644 docs/decisions/003-central-users-local-active-user.md create mode 100644 docs/decisions/004-feature-branch-workflow.md create mode 100644 docs/decisions/005-production-deployment-direction.md create mode 100644 docs/development.md create mode 100644 docs/features/000-project-foundation.md create mode 100644 docs/features/001-user-selection.md create mode 100644 docs/features/002-task-creation.md diff --git a/AGENTS.md b/AGENTS.md index 048a0f1..3c8be0b 100644 --- a/AGENTS.md +++ b/AGENTS.md @@ -9,4 +9,7 @@ - Affärsregler ska senare säkerställas i backend och inte enbart i frontend. - Kod, tester och dokumentation ska hållas uppdaterade tillsammans. - Större arkitekturella beslut ska diskuteras innan de införs. - +- Aktuell arkitektur, utvecklingsprocess, beslut och featurehistorik dokumenteras + under `docs/`. +- En feature ska uppdatera berörda dokument så att repositoryt förblir projektets + facit även efter att feature-branchen har raderats. diff --git a/README.md b/README.md index 5320d93..b5e7f76 100644 --- a/README.md +++ b/README.md @@ -49,3 +49,15 @@ Frontend: cd frontend pnpm test ``` + +## Dokumentation + +Projektets aktuella arkitektur, utvecklingsprocess, övergripande beslut och +featurehistorik finns i [`docs/`](docs/): + +- [arkitektur](docs/architecture.md) +- [utvecklingsprocess](docs/development.md) +- [arkitekturbeslut](docs/decisions/) +- [implementerade features](docs/features/) + +Dokumentationen ska uppdateras tillsammans med implementation och tester. diff --git a/docs/architecture.md b/docs/architecture.md new file mode 100644 index 0000000..3ee543b --- /dev/null +++ b/docs/architecture.md @@ -0,0 +1,183 @@ +# HemHubs arkitektur + +Detta dokument beskriver den arkitektur som kan verifieras i repositoryts kod, +tester och konfiguration. Historiska implementationssteg finns under +[`features/`](features/) och övergripande beslut under +[`decisions/`](decisions/). + +## Aktuell implementation + +### Monorepo + +HemHub ligger i ett Git-repository med två separata applikationer: + +```text +hemhub/ +├── backend/ +├── frontend/ +└── docs/ +``` + +Applikationerna har egna byggverktyg och beroenden. De delar inte källkod eller +byggprocess. + +### Frontend + +Frontend finns i `frontend/` och använder React 19, TypeScript, Vite och pnpm. +Den ansvarar för: + +- hämtning och presentation av användare och uppgifter; +- lokalt val av aktiv användare; +- formulär för att skapa användare och uppgifter; +- klientnära validering och begripliga felmeddelanden; +- uppgiftsbrädan med kolumnerna Väntande, Pågående och Klart. + +Tillståndet hanteras lokalt i React-komponenter. Ingen router eller separat +global state-lösning används. + +### Backend + +Backend finns i `backend/` och använder Java 21, Spring Boot 4.1.0, Maven, +Spring Web, Spring Data JPA och Flyway. Maven Wrapper ingår i repositoryt. + +Backend ansvarar för API, slutlig validering, skapande av UUID och tidsstämplar, +persistens samt sortering av returnerade användare och uppgifter. + +### Kommunikation + +Alla applikationsendpoints ligger under `/api`. Frontend använder enbart +relativa adresser, exempelvis `/api/users` och `/api/tasks`. + +Vid lokal utveckling kör Vite normalt på port 5173 och proxar `/api` till +`http://localhost:8080`, där Spring Boot körs. Ingen generell +CORS-konfiguration finns i backend. Webbläsaren anropar därmed Vites origin, +och utvecklingsservern vidarebefordrar API-anropen. + +Aktuella endpoints: + +- `GET /api/health` +- `GET /api/users` +- `POST /api/users` +- `GET /api/tasks` +- `POST /api/tasks` + +### Databas och migreringar + +Lokal körning använder en filbaserad H2-databas under `backend/data`. Katalogen +ignoreras av Git. Automatiska backendtester använder en separat H2-databas i +minnet. + +Båda anslutningarna använder H2:s `MODE=PostgreSQL`, +`DATABASE_TO_LOWER=TRUE` och `DEFAULT_NULL_ORDERING=HIGH`. Det är en verifierbar +kompatibilitetsinställning, inte samma sak som att applikationen har verifierats +mot PostgreSQL. + +Flyway kör migreringarna: + +- `V1__create_users.sql` +- `V2__create_tasks.sql` + +Hibernate är konfigurerat med `ddl-auto=validate`; Flyway skapar schemat och +Hibernate validerar entiteterna mot det. + +### Domänmodell + +#### Användare + +En användare lagras i tabellen `app_user` med: + +- `id`: UUID; +- `name`: visningsnamn, högst 50 tecken; +- `normalized_name`: trimmat namn i gemener, internt och unikt; +- `created_at`: en `Instant`, lagrad som `TIMESTAMP WITH TIME ZONE`. + +`normalized_name` exponeras inte via API. Användare returneras alfabetiskt efter +visningsnamn med deterministiska sekundära jämförelser. + +#### Uppgift + +En uppgift lagras i tabellen `task` med: + +- `id`: UUID; +- `title`: obligatorisk titel, högst 100 tecken; +- `description`: valfri beskrivning, högst 500 tecken; +- `status`: `WAITING`, `IN_PROGRESS` eller `COMPLETED`; +- `created_at`: en `Instant`, lagrad som `TIMESTAMP WITH TIME ZONE`. + +Status lagras som enumens textvärde genom `EnumType.STRING`. Nya uppgifter får +alltid status `WAITING`. Det finns ingen relation mellan uppgifter och +användare; alla aktiva användare ser samma uppgiftslista. + +### Aktiv användare + +Användarlistan hämtas från backend. Frontend lagrar endast den valda +användarens UUID i webbläsarens `localStorage` under nyckeln +`hemhub.activeUserId`. + +Vid start verifieras det lagrade id:t mot backendens aktuella användarlista. Ett +giltigt val återanvänds i samma browser. Ett ogiltigt val tas bort. Valet är +lokalt per browser och utgör inte autentisering eller behörighetskontroll. + +### Felhantering + +Backend använder ett litet gemensamt JSON-format med `code` och `message`. +`ApiExceptionHandler` översätter kända valideringsfel till `400 Bad Request` +och dubbletter av användarnamn till `409 Conflict`. + +Frontend skiljer mellan fel vid hämtning och skapande. Hämtfel kan +återförsökas. Formulärfel visas nära formuläret och inmatningen behålls vid +misslyckade API-anrop. + +### Teststrategi + +Backend har JUnit 5-tester: + +- ett fristående MockMvc-test för health-endpointen; +- Spring Boot-integrationstester via MockMvc mot H2 in-memory för användar- och + uppgifts-API. + +Frontend använder Vitest, jsdom och React Testing Library. `fetch` och +`localStorage` ersätts i testerna, så frontendtesterna kräver inte en körande +backend. Produktionsbygget kör TypeScript-kompilering följt av Vite. + +### Produktionsdeployment + +Ingen produktionsdeployment är implementerad i repositoryt. Det finns inga +Dockerfiler, pipelinefiler eller produktionsspecifika Nginx-, Watchtower- eller +databaskonfigurationer. H2 används både lokalt och i automatiska tester; någon +PostgreSQL-konfiguration finns ännu inte. + +## Beslutad planerad riktning + +Repositoryt anger att affärsregler även framöver ska säkerställas i backend och +att större arkitekturella beslut ska diskuteras innan de införs. + +Följande produktionsriktning är beslutad men ännu inte implementerad: + +- PostgreSQL ska användas som produktionsdatabas. +- Frontend och backend ska paketeras som separata Docker-images. +- Källkoden ligger i Gitea. +- Drone ska bygga och publicera images till ett privat registry. +- Watchtower ska uppdatera de körande tjänsterna när nya images publiceras. +- Nginx kan användas som reverse proxy framför tjänsterna. +- Produktionsmiljön ska köras på Ubuntu-servern Biff. + +Den planerade riktningen beskrivs även i +[`005-production-deployment-direction.md`](decisions/005-production-deployment-direction.md). +Punkterna ovan beskriver målbilden och ska inte tolkas som att motsvarande +konfiguration redan finns eller har verifierats. + +## Fortfarande öppna detaljer + +Följande har inte fastställts i dokumentationen och ska beslutas i samband med +att produktionslösningen implementeras: + +- exakt containerstruktur och tjänsteindelning; +- image-namn och taggningsstrategi; +- produktions-URL; +- hantering och distribution av secrets; +- exakt Nginx-konfiguration; +- exakt Drone-, registry-, Watchtower- och deploymentkonfiguration. + +Miljöspecifika adresser, credentials och secrets ska inte lagras i dessa +arkitekturdokument. diff --git a/docs/decisions/001-monorepo.md b/docs/decisions/001-monorepo.md new file mode 100644 index 0000000..7019e3b --- /dev/null +++ b/docs/decisions/001-monorepo.md @@ -0,0 +1,28 @@ +# 001 – Monorepo med separata applikationer + +## Status + +Accepterat + +## Datum + +2026-07-23 + +## Sammanhang + +HemHub behöver en webbläsarklient och ett server-API. Båda delarna utvecklas +inkrementellt och behöver kunna versionshanteras och dokumenteras tillsammans. + +## Beslut + +Frontend och backend ligger i samma Git-repository, i katalogerna `frontend/` +respektive `backend/`. De är separata applikationer med egna byggverktyg, +beroenden och startkommandon. + +## Konsekvenser + +- En feature kan ändra frontend, backend, tester och dokumentation atomärt. +- En gemensam historik beskriver hela systemet. +- Applikationerna kan startas och testas oberoende. +- Repositoryt har ingen gemensam rotbyggprocess; relevanta kommandon körs i + respektive applikationskatalog. diff --git a/docs/decisions/002-same-origin-api-proxy.md b/docs/decisions/002-same-origin-api-proxy.md new file mode 100644 index 0000000..9b500f7 --- /dev/null +++ b/docs/decisions/002-same-origin-api-proxy.md @@ -0,0 +1,32 @@ +# 002 – Relativa API-adresser och lokal utvecklingsproxy + +## Status + +Accepterat + +## Datum + +2026-07-23 + +## Sammanhang + +Frontend körs lokalt med Vite på port 5173 och backend med Spring Boot på port +8080. Frontend behöver nå API:t utan miljöspecifika, hårdkodade backendadresser +i applikationskoden. + +## Beslut + +Frontend använder relativa API-adresser under `/api`. Vites utvecklingsserver +proxar `/api` till `http://localhost:8080`. + +Ingen generell CORS-konfiguration införs i backend så länge webbläsaren anropar +Vites origin och Vite vidarebefordrar anropet. + +## Konsekvenser + +- Frontendkoden innehåller inte en lokal fullständig backend-URL. +- Lokal utveckling kräver att backend är tillgänglig på port 8080 för + API-anrop via proxyn. +- En separat CORS-policy behöver inte underhållas för nuvarande lokala flöde. +- En framtida driftlösning måste ge `/api` en motsvarande same-origin-väg eller + medföra ett nytt dokumenterat beslut. diff --git a/docs/decisions/003-central-users-local-active-user.md b/docs/decisions/003-central-users-local-active-user.md new file mode 100644 index 0000000..cfced37 --- /dev/null +++ b/docs/decisions/003-central-users-local-active-user.md @@ -0,0 +1,34 @@ +# 003 – Centrala användare och lokalt val av aktiv användare + +## Status + +Accepterat + +## Datum + +2026-07-24 + +## Sammanhang + +HemHub behöver veta vem som använder gränssnittet, men har ännu ingen +autentisering. Användarlistan ska vara gemensam medan själva valet kan vara +lokalt för den aktuella browsern. + +## Beslut + +Användare lagras centralt via backend och hämtas från `/api/users`. Frontend +lagrar endast vald användares UUID i `localStorage` med nyckeln +`hemhub.activeUserId`. + +Vid appstart jämförs det lokala id:t med backendens användarlista. Ett giltigt id +återanvänds och ett ogiltigt id tas bort. `Logga ut` tar bort nyckeln och visar +användarvalet igen. + +## Konsekvenser + +- Samma browser kan återanvända sitt senaste giltiga användarval. +- En annan browser eller en rensad browserlagring måste välja användare igen. +- Endast id lagras lokalt; aktuellt namn kommer från backendens lista. +- Valet synkroniseras inte mellan browsers eller enheter. +- Lösningen identifierar en användare i gränssnittet men ger ingen säker + autentisering, session eller behörighetskontroll. diff --git a/docs/decisions/004-feature-branch-workflow.md b/docs/decisions/004-feature-branch-workflow.md new file mode 100644 index 0000000..9d73e8a --- /dev/null +++ b/docs/decisions/004-feature-branch-workflow.md @@ -0,0 +1,30 @@ +# 004 – Kortlivade feature-branches + +## Status + +Accepterat + +## Sammanhang + +HemHub utvecklas inkrementellt med avgränsade ändringar. Historiska +feature-branches ska kunna raderas efter merge utan att projektets motiv och +aktuella läge försvinner. + +## Beslut + +Varje feature eller avgränsad ändring utvecklas på en kortlivad branch som +skapas från uppdaterad `main`. Kod, tester och relevant dokumentation ingår i +samma ändring. + +Commit och push görs först efter uttrycklig instruktion. Merge sker efter +verifiering, och `main` ska representera verifierad kod. Därefter kan branchen +raderas. + +## Konsekvenser + +- Pågående arbete isoleras från `main`. +- En feature kan granskas och verifieras som en sammanhållen ändring. +- Dokumentationen måste uppdateras före merge så att raderade branches inte + behövs för att förstå projektet. +- Övergripande beslut bevaras i `docs/decisions/` och faktisk featurehistorik i + `docs/features/`. diff --git a/docs/decisions/005-production-deployment-direction.md b/docs/decisions/005-production-deployment-direction.md new file mode 100644 index 0000000..0112a97 --- /dev/null +++ b/docs/decisions/005-production-deployment-direction.md @@ -0,0 +1,52 @@ +# 005 – Riktning för produktionsdeployment + +## Status + +Accepterat som planerad riktning, ännu inte implementerat + +## Sammanhang + +HemHub använder i nuläget H2 för lokal utveckling och tester. Repositoryt saknar +fortfarande container-, pipeline- och produktionskonfiguration, men den +övergripande målbilden för byggande och drift behöver vara dokumenterad innan +den implementeras. + +Källkoden ligger i Gitea och den planerade produktionsmiljön är Ubuntu-servern +Biff. + +## Beslut + +- PostgreSQL ska användas som produktionsdatabas. +- Frontend och backend ska paketeras som Docker-images. +- Drone ska bygga och publicera images till ett privat registry. +- Watchtower ska uppdatera tjänsterna när nya images publiceras. +- Nginx kan användas som reverse proxy. + +Detta ADR fastställer komponenterna och ansvarsfördelningen på övergripande +nivå. Det inför inte någon konfiguration och innebär inte att lösningen redan +har driftverifierats. + +## Konsekvenser + +- Kommande produktionsarbete behöver införa och verifiera PostgreSQL-stöd, + Dockerpaketering och en Drone-baserad leveranskedja. +- Images behöver kunna publiceras till ett privat registry som Biff kan nå. +- Uppdateringsflödet behöver utformas så att Watchtower kan hämta och starta nya + images på ett kontrollerat sätt. +- Nginx är ett möjligt reverse proxy-lager, inte en fastställd detaljkonfiguration. +- Lokal utveckling och automatiska tester fortsätter använda H2 tills ett + separat beslut eller en feature ändrar detta. + +## Öppna detaljer + +Följande beslutas först när produktionslösningen implementeras: + +- exakt containerstruktur; +- image-namn och taggningsstrategi; +- produktions-URL; +- secrets och hur de tillförs till pipeline och tjänster; +- exakt Nginx-konfiguration; +- exakt Drone-, registry-, Watchtower- och deploymentkonfiguration. + +IP-adresser, credentials och andra miljöspecifika känsliga värden ska inte +dokumenteras här. diff --git a/docs/development.md b/docs/development.md new file mode 100644 index 0000000..372a6e1 --- /dev/null +++ b/docs/development.md @@ -0,0 +1,58 @@ +# Utvecklingsprocess + +Repositoryt är projektets facit. ChatGPT- eller Codex-dialoger kan användas som +arbetsyta, men implementation, tester och dokumentation ska tillsammans göra +projektets läge begripligt utan tidigare dialoger eller raderade branches. + +## Arbetssätt + +- Använd en kortlivad branch per feature eller annan avgränsad ändring. +- Skapa branchen från en uppdaterad `main`. +- En feature per ChatGPT-dialog är en praktisk arbetsform, inte en + dokumentationskälla. +- Skapa eller uppdatera feature-dokumentet inom samma feature. +- Ge Codex en tydligt avgränsad specifikation. +- Implementera endast uttryckliga krav och undvik spekulativ funktionalitet. +- Kör relevanta tester före commit och gör manuell verifiering när beteendet + motiverar det. +- Commit och push sker först efter uttrycklig instruktion. +- Merge sker först när ändringen har verifierats. +- Uppdatera arkitektur- och beslutsdokument när övergripande beslut förändras. + +`main` ska innehålla verifierad kod. När en feature har mergats ska dess branch +kunna raderas utan att projektkunskap går förlorad. + +## Rekommenderad featureprocess + +1. Uppdatera `main`. +2. Skapa en avgränsad branch. +3. Skapa eller uppdatera feature-dokumentet. +4. Implementera specifikationen. +5. Kör relevanta automatiska tester och bygge. +6. Gör manuell verifiering där det är relevant. +7. Uppdatera dokumentationen så att den beskriver den faktiska lösningen. +8. Commit och push efter uttrycklig instruktion. +9. Merge efter verifiering. +10. Radera den mergade branchen. + +## Verifiering före merge + +För nuvarande projekt bör verifieringen normalt omfatta: + +```bash +cd backend +./mvnw test +``` + +```bash +cd frontend +pnpm test +pnpm build +``` + +Kör även `git diff --check` och granska `git status --short`. Manuell lokal +verifiering av berörda flöden kompletterar, men ersätter inte, automatiska +tester. + +Om ett befintligt test misslyckas av ett skäl utanför ändringens omfattning ska +det rapporteras; produktionskod ska inte ändras enbart för att dölja felet. diff --git a/docs/features/000-project-foundation.md b/docs/features/000-project-foundation.md new file mode 100644 index 0000000..3b068a9 --- /dev/null +++ b/docs/features/000-project-foundation.md @@ -0,0 +1,76 @@ +# Feature 0 – Projektgrund + +## Status + +Färdig och mergad till `main`. + +## Bakgrund + +HemHub behövde en minimal projektgrund för inkrementell utveckling av en +webbapplikation med separat frontend och backend. + +## Mål + +Skapa körbara React- och Spring Boot-applikationer, koppla ihop dem lokalt och +etablera grundläggande tester och dokumentation. + +## Omfattning + +- monorepo med `backend/` och `frontend/`; +- Java 21, Spring Boot och Maven Wrapper; +- React, TypeScript, Vite och pnpm; +- health-endpoint och en tillfällig frontendstatus; +- Vite-proxy och grundtester; +- `README.md`, `AGENTS.md` och `.gitignore`. + +## Avgränsningar + +Feature 0 införde ingen databas, domänmodell, autentisering, deployment, +containerkonfiguration eller produktionskonfiguration. + +## Beslut + +Frontend och backend skapades som separata applikationer i samma repository. +Frontend använder relativa `/api`-adresser, och Vite proxar dem lokalt till +backend på port 8080. Ingen generell CORS-konfiguration infördes. + +## Implementerad lösning + +Backend skapades med Spring Boot 4.1.0, Java 21, Spring Web och Maven Wrapper. +Frontend skapades med React 19, TypeScript, Vite och pnpm. + +Den ursprungliga startsidan anropade health-endpointen och visade backendstatus +eller ett anslutningsfel. Senare features har ersatt denna startsida, men +health-endpointen och dess test finns kvar. + +## API-förändringar + +`GET /api/health` infördes och returnerar: + +```json +{"status":"UP"} +``` + +## Databasförändringar + +Inga. + +## Frontendförändringar + +En minimal startsida visade rubriken HemHub, att frontend hade startat och +resultatet från `/api/health`. Vite konfigurerades att proxya `/api` till +`http://localhost:8080`. + +## Tester och verifiering + +Ett MockMvc-test verifierar status 200 och `status: UP`. Det ursprungliga +frontendtestet verifierade rubriken HemHub med mockat API-anrop. + +## Kända begränsningar + +Projektgrunden innehöll ingen användar- eller uppgiftsfunktionalitet. Den +ursprungliga health-vyn är inte längre appens aktiva vy. + +## Relaterade commits + +- `9957383e88b08dc006d2eaeb2a513c7769bd5705` – `Initialize HemHub project foundation` diff --git a/docs/features/001-user-selection.md b/docs/features/001-user-selection.md new file mode 100644 index 0000000..b233d87 --- /dev/null +++ b/docs/features/001-user-selection.md @@ -0,0 +1,99 @@ +# Feature 1 – Användarval + +## Status + +Färdig och mergad till `main`. + +## Bakgrund + +HemHub behövde centralt lagrade användare och ett enkelt sätt att välja vem som +använder applikationen, utan att införa autentisering. + +## Mål + +Göra det möjligt att lista och skapa användare, välja en aktiv användare, +återanvända valet i samma browser och lämna den aktiva vyn. + +## Omfattning + +- persistens, API och validering för användare; +- startflöden för tom och befintlig användarlista; +- lokalt lagrad aktiv användare; +- användarval, skapande och felhantering; +- automatiserade backend- och frontendtester. + +## Avgränsningar + +Ingen autentisering, lösenord, roll, behörighet, e-post, avatar, +hushållsrelation, redigering eller radering infördes. + +## Beslut + +Backend är slutlig auktoritet för namnvalidering. Namn normaliseras separat för +skiftlägesokänslig unikhet. Frontend lagrar endast UUID under +`hemhub.activeUserId` och verifierar det mot den hämtade användarlistan. + +## Implementerad lösning + +Vid appstart hämtar frontend alltid användarna. En tom lista leder direkt till +formuläret Skapa användare. Om användare finns men inget giltigt lokalt val +finns visas Vem är du?. + +Val eller lyckat skapande sparar användarens id och aktiverar användaren. Ett +ogiltigt lagrat id rensas utan tekniskt fel. Feature 1:s tillfälliga startsida +och kontrollen Byt användare ersattes i Feature 2 av uppgiftsbrädan och +kontrollen Logga ut; lagringsmekanismen är oförändrad. + +## API-förändringar + +- `GET /api/users` returnerar alla användare. +- `POST /api/users` skapar en användare och returnerar `201 Created`. + +API-responsen innehåller `id`, `name` och `createdAt`. `normalizedName` exponeras +inte. + +Tomt namn eller namn längre än 50 Unicode-kodpunkter ger `400` med +`INVALID_USER_NAME`. Ett dubblettnamn utan hänsyn till stora och små bokstäver +ger `409` med `USER_NAME_ALREADY_EXISTS`. + +## Databasförändringar + +Flyway-migreringen `V1__create_users.sql` skapade tabellen `app_user`: + +- UUID som primärnyckel; +- `name VARCHAR(50)`; +- unikt `normalized_name VARCHAR(150)`; +- `created_at TIMESTAMP WITH TIME ZONE`. + +Lokalt används filbaserad H2 och i tester H2 in-memory. Backend genererar UUID +och `createdAt` med en UTC-klocka. + +## Frontendförändringar + +Frontend fick laddnings-, fel-, användarvals- och användarskapandevyer. +Skapandeformuläret trimmar namnet, gör en enkel längdkontroll, blockerar +dubbelsubmit och behåller inmatningen vid fel. + +Nuvarande utloggning tar bort `hemhub.activeUserId`, rensar aktiv användare och +visar Vem är du? även om endast en användare finns. + +## Tester och verifiering + +Backendens integrationstester verifierar tom lista, skapande och listning, +trimning, ogiltiga namn, skiftlägesokänsliga dubbletter och alfabetisk +sortering. + +Frontendtesterna verifierar tom lista, användarval, automatisk aktivering efter +skapande, bevarad inmatning vid fel, hämtfel med återförsök, ogiltigt lagrat id +och utloggning. API-anropen mockas. + +## Kända begränsningar + +Aktiv användare är ett lokalt gränssnittsval, inte säker autentisering. Valet +synkroniseras inte mellan browsers eller enheter. Användare kan inte redigeras +eller raderas. + +## Relaterade commits + +- `1ec7a729085d456d3185a1c74d02f99f40de0e8d` – `feat: add user selection flow` +- `050f248857a01db2dc236a0ca35982fd70dab3d6` – merge till `main` diff --git a/docs/features/002-task-creation.md b/docs/features/002-task-creation.md new file mode 100644 index 0000000..02fcd72 --- /dev/null +++ b/docs/features/002-task-creation.md @@ -0,0 +1,108 @@ +# Feature 2 – Skapa uppgifter + +## Status + +Färdig och mergad till `main`. + +## Bakgrund + +Efter införandet av aktiv användare behövde HemHub en första gemensam +uppgiftsmodell och en enkel bräda för att skapa och visa uppgifter. + +## Mål + +Låta en aktiv användare se tre statuskolumner, skapa en uppgift med titel och +valfri beskrivning samt se den sparade uppgiften efter omladdning. + +## Omfattning + +- persistent uppgiftsmodell och Flyway-migrering; +- API för att skapa och lista uppgifter; +- bräda med Väntande, Pågående och Klart; +- modal för att skapa uppgifter; +- laddnings-, validerings- och felhantering; +- automatiserade backend- och frontendtester. + +## Avgränsningar + +Ingen ändring av status, drag-and-drop, tilldelning, användarrelation, poäng, +deadline, återkommande uppgift, redigering, radering, sökning, filtrering eller +paginering infördes. + +## Beslut + +Alla användare ser samma uppgifter; uppgiftsmodellen har ingen relation till en +användare. Backend väljer alltid status `WAITING` vid skapande. Listningen +sorteras i backend efter `createdAt ASC, id ASC`, och frontend bevarar den +ordningen. + +## Implementerad lösning + +JPA-entiteten `Task` innehåller UUID, titel, valfri beskrivning, status och +skapandetid. Backend genererar UUID och `createdAt` med en UTC-klocka. + +Frontend visar uppgiftsbrädan när ett giltigt aktivt användarval finns. Uppgifter +hämtas vid montering, grupperas efter status och visas med endast titel och +eventuell beskrivning. Tomma kolumner saknar tomlägestext. + +## API-förändringar + +- `GET /api/tasks` returnerar samtliga uppgifter, äldst först och med UUID som + sekundär sorteringsnyckel. +- `POST /api/tasks` skapar en uppgift och returnerar `201 Created`. + +Titel trimmas, är obligatorisk och får omfatta högst 100 Unicode-kodpunkter. +Beskrivning trimmas, får omfatta högst 500 Unicode-kodpunkter och lagras som +`null` om den är tom. Ogiltiga anrop ger `400` med felkoden `INVALID_TASK`. + +## Databasförändringar + +Flyway-migreringen `V2__create_tasks.sql` skapade tabellen `task`: + +- `id UUID PRIMARY KEY`; +- `title VARCHAR(100) NOT NULL`; +- `description VARCHAR(500)`; +- `status VARCHAR(20) NOT NULL`; +- `created_at TIMESTAMP WITH TIME ZONE NOT NULL`. + +Status lagras som text genom `@Enumerated(EnumType.STRING)`. Databasen har ingen +check constraint för enumvärden. + +## Frontendförändringar + +Feature 1:s tillfälliga aktiva vy ersattes med uppgiftsbrädan. Sidhuvudet visar +aktiv användares namn, Logga ut och Ny uppgift. + +Skapandemodalen innehåller titel och valfri beskrivning. Titelfältet får fokus +när modalen öppnas. När inget submit-anrop pågår kan den stängas med kryss, +Escape eller klick på bakgrunden. Normal stängning avmonterar komponenten och +nollställer därmed formuläret. + +Vid submit gör frontend samma grundläggande längdkontroller, skickar trimmade +värden och blockerar uppenbara dubbelsubmit. Vid fel stannar modalen öppen med +bevarad inmatning. Vid framgång läggs API-svaret sist i den befintliga listan, +vilket placerar den nya `WAITING`-uppgiften längst ned i Väntande utan att +sortera om backendens ordning. + +## Tester och verifiering + +Backendens integrationstester verifierar skapande, `WAITING`, trimning, tom +beskrivning som `null`, längdvalidering samt sorteringen `createdAt ASC, id ASC`. + +Frontendtesterna verifierar bräda och statusgruppering, tomma kolumner, +modalöppning och fokus, skapande, ordning efter skapande, bevarad formulärdata +vid API-fel samt utloggning. Parametriserade testfall verifierar också stängning +med kryss, Escape och bakgrundsklick samt att formuläret är rensat när modalen +öppnas igen. + +## Kända begränsningar + +Statusvärden utöver `WAITING` kan visas om de redan finns i databasen, men inget +nuvarande API eller gränssnitt kan flytta en uppgift mellan kolumnerna. Det +finns ingen koppling mellan uppgifter och skapande eller aktiv användare. +Modalen har ingen fokusfälla eller explicit fokusåterställning. + +## Relaterade commits + +- `3f152eecccdd88f840066543bf9321b81b4cead8` – `feat: add task creation board` +- `2f7b99fb21c57c2e9c5f019a2b5073458e41c939` – merge till `main`