Files
2026-03-16 20:12:01 +01:00

145 lines
7.3 KiB
Markdown

---
phase: 02-rooms-and-tasks
plan: 01
subsystem: database
tags: [drift, sqlite, dao, scheduling, templates, domain-models]
# Dependency graph
requires:
- phase: 01-foundation
provides: AppDatabase with schema v1, NativeDatabase.memory() test pattern, project scaffold
provides:
- Drift schema v2 with Rooms, Tasks, TaskCompletions tables
- RoomsDao with CRUD, stream queries, cascade delete, reorder, room stats
- TasksDao with CRUD, stream queries, completeTask transaction, overdue detection
- Pure scheduling utility (calculateNextDueDate, catchUpToPresent)
- Domain enums IntervalType (8 types), EffortLevel (3 levels), FrequencyInterval model
- formatRelativeDate German formatter
- curatedRoomIcons icon list with 25 Material Icons
- TaskTemplate model and roomTemplates for 14 room types
- detectRoomType name-matching utility with alias support
affects: [02-rooms-and-tasks, 03-daily-plan, 04-notifications]
# Tech tracking
tech-stack:
added: []
patterns: [drift-dao-with-stream-queries, pure-scheduling-utility, task-completion-transaction, intEnum-for-enums, cascade-delete-in-transaction, const-template-data]
key-files:
created:
- lib/features/tasks/domain/frequency.dart
- lib/features/tasks/domain/effort_level.dart
- lib/features/tasks/domain/scheduling.dart
- lib/features/tasks/domain/relative_date.dart
- lib/features/rooms/domain/room_icons.dart
- lib/features/rooms/data/rooms_dao.dart
- lib/features/tasks/data/tasks_dao.dart
- lib/features/templates/data/task_templates.dart
- test/features/tasks/domain/scheduling_test.dart
- test/features/rooms/data/rooms_dao_test.dart
- test/features/tasks/data/tasks_dao_test.dart
- test/features/templates/task_templates_test.dart
- drift_schemas/household_keeper/drift_schema_v2.json
modified:
- lib/core/database/database.dart
- lib/core/database/database.g.dart
- test/core/database/database_test.dart
key-decisions:
- "Scheduling functions are top-level pure functions with DateTime today parameter for testability"
- "Calendar-anchored intervals use anchorDay nullable field for month-clamping memory"
- "RoomWithStats computed via asyncMap on watchAllRooms stream, not a custom SQL join"
- "Templates stored as Dart const map, not JSON assets, for type safety"
- "detectRoomType uses contains-based matching with alias map for flexible room name detection"
patterns-established:
- "DAO stream queries with .watch() for reactive UI data"
- "Cascade delete via transaction (completions -> tasks -> room)"
- "Task completion as single DAO transaction (record + calculate + catch-up + update)"
- "intEnum for Dart enum persistence with index stability comments"
- "In-memory database testing with NativeDatabase.memory()"
- "Testable date logic via today parameter injection"
requirements-completed: [ROOM-01, ROOM-02, ROOM-03, ROOM-04, ROOM-05, TASK-01, TASK-02, TASK-03, TASK-04, TASK-05, TASK-06, TASK-07, TASK-08, TMPL-01, TMPL-02]
# Metrics
duration: 8min
completed: 2026-03-15
---
# Phase 2 Plan 01: Data Layer Summary
**Drift schema v2 with Rooms/Tasks/TaskCompletions tables, RoomsDao and TasksDao with stream queries and completion transactions, pure scheduling utility with 8 interval types and anchor memory, and 14-room-type German task template library**
## Performance
- **Duration:** 8 min
- **Started:** 2026-03-15T20:44:07Z
- **Completed:** 2026-03-15T20:52:38Z
- **Tasks:** 2
- **Files modified:** 16
## Accomplishments
- Database schema v2 with three tables (Rooms, Tasks, TaskCompletions), foreign keys enabled via PRAGMA, and v1-to-v2 migration strategy
- RoomsDao with full CRUD, stream-based watchAll and watchWithStats (cleanliness ratio), cascade delete, and sortOrder reorder
- TasksDao with CRUD, due-date-sorted stream queries, atomic completeTask transaction (records completion, calculates next due, catches up to present), and overdue detection
- Pure scheduling utility handling daily, everyNDays, weekly, biweekly, monthly, everyNMonths, quarterly, yearly intervals with calendar-anchored clamping and anchor memory
- Domain models: IntervalType enum (8 values), EffortLevel enum (3 values), FrequencyInterval with German labels, formatRelativeDate German formatter, curatedRoomIcons with 25 Material Icons
- 14 room types with 3-6 German task templates each, plus detectRoomType with alias-based name matching
- 41 data layer unit tests all passing, full suite of 59 tests green
## Task Commits
Each task was committed atomically:
1. **Task 1: Define Drift tables, migration, DAOs, and domain models** - `d2e4526` (feat)
2. **Task 2: Create task template data and template tests** - `da270e5` (feat)
## Files Created/Modified
- `lib/core/database/database.dart` - Drift tables (Rooms, Tasks, TaskCompletions), schema v2, migration strategy, foreign keys PRAGMA
- `lib/features/tasks/domain/frequency.dart` - IntervalType enum (8 values), FrequencyInterval model with German labels
- `lib/features/tasks/domain/effort_level.dart` - EffortLevel enum (low/medium/high) with German labels
- `lib/features/tasks/domain/scheduling.dart` - calculateNextDueDate and catchUpToPresent pure functions
- `lib/features/tasks/domain/relative_date.dart` - formatRelativeDate German formatter (Heute, Morgen, in X Tagen, Uberfaellig)
- `lib/features/rooms/domain/room_icons.dart` - curatedRoomIcons (25 Material Icons) and mapIconName utility
- `lib/features/rooms/data/rooms_dao.dart` - RoomsDao with CRUD, watchAll, watchWithStats, cascade delete, reorder
- `lib/features/tasks/data/tasks_dao.dart` - TasksDao with CRUD, watchInRoom, completeTask, overdue detection
- `lib/features/templates/data/task_templates.dart` - TaskTemplate class, roomTemplates for 14 types, detectRoomType
- `test/features/tasks/domain/scheduling_test.dart` - 17 tests for scheduling and relative date formatting
- `test/features/rooms/data/rooms_dao_test.dart` - 6 tests for rooms DAO operations
- `test/features/tasks/data/tasks_dao_test.dart` - 7 tests for tasks DAO operations
- `test/features/templates/task_templates_test.dart` - 11 tests for templates and detectRoomType
## Decisions Made
- Scheduling functions are top-level pure functions (not in a class) with DateTime today parameter for testability
- Calendar-anchored intervals use a nullable anchorDay field on Tasks table for month-clamping memory
- RoomWithStats computed via asyncMap on the watchAllRooms stream rather than a complex SQL join
- Templates stored as Dart const map for type safety and zero parsing overhead
- detectRoomType uses contains-based matching with an alias map for flexible room name detection
## Deviations from Plan
None - plan executed exactly as written.
## Issues Encountered
None
## User Setup Required
None - no external service configuration required.
## Next Phase Readiness
- All data layer contracts ready for Room CRUD UI (02-02), Task CRUD UI (02-03), and Template selection (02-04)
- Stream-based DAO queries ready for Riverpod stream providers
- Scheduling utility ready to be called from TasksDao.completeTask
- Template data ready for template picker bottom sheet
- All existing Phase 1 tests continue to pass
## Self-Check: PASSED
All 13 key files verified present. Both task commits (d2e4526, da270e5) verified in git log. 59 tests passing. dart analyze clean.
---
*Phase: 02-rooms-and-tasks*
*Completed: 2026-03-15*