# 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.