App web familiar de rutinas visuales para niños con TDAH: muestra cada día el material del cole y las rutinas de tarde, con gamificación por monedas y tienda de recompensas. Multi-niño y bilingüe ES/CA. Uso doméstico/homelab. Backend (Spring Boot 3.5 / Java 21 / Gradle): - Dominio por capas, PostgreSQL + Liquibase, datos semilla. - API REST con DTOs: /today, toggle con monedas y bonos de bloque/día, monedero, tienda/canje, ajustes y CRUD del panel de padres. - Seguridad ligera por PIN (BCrypt + sesion en memoria), sin Keycloak. - Tests JUnit: generacion del dia, monedas/bonos con reversion, canje, seguridad. Frontend (Angular 19, standalone + signals): - Perfiles, Home (Tablero y Foco), Tienda y panel de padres (5 pestañas). - Tipografia OpenDyslexic conmutable (accesibilidad), i18n ES/CA, TTS y sonido. - Tokens de diseño fieles al handoff (paleta, animaciones, monedas voladoras). Empaquetado: - Docker multi-stage + docker-compose (PostgreSQL + backend + Nginx). - Decisiones de arquitectura documentadas en docs/adr.
52 lines
2.4 KiB
Markdown
52 lines
2.4 KiB
Markdown
# ADR 0003 — Decisiones de dominio y seguridad (Fase 2 backend)
|
|
|
|
- **Estado:** aceptada
|
|
- **Fecha:** 2026-06-21
|
|
- **Fase:** 2 (dominio + API + seguridad)
|
|
|
|
## Contexto
|
|
|
|
El contrato de backend deja varias decisiones "a tu criterio". Se documentan aquí
|
|
las tomadas al implementar el dominio, la lógica de negocio y la seguridad.
|
|
|
|
## Decisiones
|
|
|
|
1. **i18n por columnas embebidas** `label_es` / `label_ca` (no tabla de
|
|
traducciones). Encaja con el shape de los DTOs y simplifica las consultas.
|
|
|
|
2. **Capas, sin hexagonal completa.** Entidad JPA como modelo de dominio (con
|
|
comportamiento donde aporta: monedero en `Child`, marcado en `DailyTask`), DTOs
|
|
tipo `record` en el borde. **Nunca se exponen entidades**.
|
|
|
|
3. **Mañana vs. tarde.** La mañana se modela con `Activity` (catálogo) +
|
|
`WeeklyTemplateEntry` (asignación por día). La tarde con `AfternoonRoutine`
|
|
directa por día. Se evita una FK polimórfica.
|
|
|
|
4. **Eventos = banner, no tareas.** Los `SpecialEvent` (examen/deberes) se muestran
|
|
en el banner informativo del día (`specialEvents[]`), NO se materializan como
|
|
`DailyTask` marcables (coherente con el prototipo). El enum `TaskOrigin.EVENT`
|
|
queda disponible por si se decide lo contrario más adelante.
|
|
|
|
5. **Bonos reconciliables.** El bono de bloque y el de día se modelan como
|
|
transacciones de monedas con el mismo motivo: +importe al otorgar, -importe al
|
|
revertir. "Suma neta > 0" indica bono activo. Hace el marcar/desmarcar robusto
|
|
ante cualquier secuencia.
|
|
|
|
6. **Seguridad ligera.** PIN de padres con hash BCrypt; al validarlo se abre una
|
|
sesión en memoria identificada por un valor opaco (cabecera `X-Parent-Session`).
|
|
`/api/parents/**` exige rol PARENT; el resto (kiosko del niño) es abierto. Todo
|
|
encapsulado en el paquete `security` para poder sustituirlo por Keycloak.
|
|
|
|
7. **Semilla por `DataSeeder`** (ApplicationRunner, solo si la BD está vacía), no
|
|
por Liquibase. Más mantenible y tipado. Desactivable con
|
|
`recordalexia.seed.enabled=false` (lo usan los tests).
|
|
|
|
8. **Tests sobre H2** (modo PostgreSQL) con Liquibase. Se valorará Testcontainers
|
|
en una iteración posterior para fidelidad total con PostgreSQL.
|
|
|
|
## Consecuencias
|
|
|
|
- Los textos visibles siempre viajan en ES y CA; el frontend elige idioma.
|
|
- Cambiar a Keycloak no afecta a controladores ni servicios de negocio.
|
|
- La zona horaria del negocio (Europe/Madrid) se centraliza en un `Clock` inyectable.
|