Phase 2: group data model (migration 23 to 24) with colour inheritance - #179
Open
mapgie wants to merge 2 commits into
Open
Phase 2: group data model (migration 23 to 24) with colour inheritance#179mapgie wants to merge 2 commits into
mapgie wants to merge 2 commits into
Conversation
Adds the redesign's only genuinely new table: a category group that owns a colour role and a default input type. Fully additive; no UI changes. - Group entity (table `groups`) + GroupDao; TrackingCategory gains a nullable groupId (no FK: deleting a group unfiles members instead of cascading). MIGRATION_23_24 creates the table and adds the column; existing rows keep groupId NULL and their colorToken, so nothing changes visually after migrating. - Group CRUD, reorder, delete-with-unfile, and assign/unassign methods on TrackingRepository (new nullable groupDao constructor param, wired in GoFloApplication). - Colour inheritance per PLAN.md section 5: new "inherit" colorToken sentinel resolved by TrackingCategory.effectiveColorToken(groups) to the group's colorRole, or neutral surfaceVariant when groupless. Deliberately not a CategoryColor entry so the Phase 1 role picker does not offer it. Existing tokens are untouched (no grey wipe; confirmed with owner against the handover's neutral-by-default). - Migration test (Migration23To24Test): runs the real MIGRATION_23_24 against a real SQLite v23 schema via sqlite-jdbc (test-only dep), routing execSQL through a reflection proxy, and asserts the exact schema Room expects plus data preservation. MigrationTestHelper is unusable here (no instrumented tests, exportSchema = false). - PLAN.md section 7 progress log updated; subsystem map 02 updated for v24; changelog fragment (minor); LESSONS.md entry on JVM-side Room migration testing. Verified: migration SQL executed against a seeded v23 schema in SQLite (PRAGMA output matches the test's expected schema exactly); a11y_check.py and wcag_check.py both clean. Claude-Session: https://claude.ai/code/session_01PZJLynVBkgLtehJFXffnfg Co-authored-by: Claude <noreply@anthropic.com>
mapgie
marked this pull request as ready for review
August 25, 2026 00:51
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
Phase 2 of the logging & category-system redesign (PLAN.md, build guide:
phases/phase-2-group-model.md). Groups now exist in the data layer with colour inheritance. Fully additive: no UI redesign, no existing behaviour changed.What's in here
Groupentity (table`groups`):id,name,colorRole(always aCategoryColorkey, never hex),defaultInputType(aCategoryTypekey),displayOrder. Defaulted columns carry@ColumnInfo(defaultValue = ...)so Room's expected DDL matches the migration SQL exactly.TrackingCategory.groupId: Long?added as the last constructor field (the only constructor call site uses named args). No FK and no cascade:TrackingRepository.deleteGroupunfiles members (groupId = NULL) before deleting the group row, so deleting a group can never touch categories or history.MIGRATION_23_24creates`groups`and adds the nullablegroupIdcolumn. Existing rows:groupId = NULL,colorTokenuntouched.GroupDao+ group methods onTrackingRepository(CRUD, rename, role/input-type update, reorder, delete-with-unfile, assign/unassign), wired via a new nullablegroupDaoconstructor param inGoFloApplication.COLOR_TOKEN_INHERIT("inherit") sentinel.TrackingCategory.effectiveColorToken(groups)resolves it to the group'scolorRole; inherit-without-group renders neutral (surfaceVariant/onSurfaceVariantbranches added to the resolvers)."inherit"is deliberately not aCategoryColorentry, so the Phase 1 role picker does not offer it; the opt-in surface arrives with the Phase 6 management UI.Migration23To24Test): the project has no instrumented tests andexportSchema = false, so Room'sMigrationTestHelperis unusable. Instead a JVM test builds the real v23 schema in in-memory SQLite (sqlite-jdbc, test-only dep mirroring the existingorg.jsonprecedent), seeds representative data, runs the actualMIGRATION_23_24object through a reflection proxy that routesexecSQLto JDBC, and asserts the exact schema Room expects (PRAGMA table_infoincluding DEFAULT clauses) plus full data preservation. The migration SQL was additionally executed against a seeded v23 schema in real SQLite during development; PRAGMA output matches the test's expectations.minor), PLAN.md section 7 progress-log row, subsystem map 02 updated for v24, LESSONS.md entry on JVM-side Room migration testing.Deviation notes
TrackingRepositoryrather than a separateGroupRepository(guide allowed either); assign/unassign is category-side and this avoids cross-repository coordination for delete-with-unfile.Acceptance criteria (phase guide)
MIGRATION_23_24, assert (a)groupsexists, (b)tracking_categories.groupIdexists and is null for all rows, (c) all pre-existing category/value/log data is intact. (JVM test as described above, inapp/src/test.)colorToken = "inherit"assigned to a group renders the group's role colour and re-themes. (effectiveColorTokenreturns the group'scolorRole, which feeds the existing theme-relative resolvers from Phase 1.)surfaceVariant/onSurfaceVariantbranches intoCategoryColor/toCategoryOnColor).colorTokenis modified and non-inherit tokens short-circuit ineffectiveColorToken.Feature-preservation checklist (phase guide)
getActiveCategories,getCategoryById, ...) still compile and return the same data plus the new nullable field (only an appended nullable constructor field; all queries areSELECT *).groupIdyet.deleteGroupunfiles members first; no FK cascade exists).saveLog/ value CRUD untouched.Checks run locally:
a11y_check.pyclean (97 files),wcag_check.pyexit 0 (no colour values changed), changelog fragment validates againstcheck_changelog_fragment.pyrules. DB version after this PR: 24.🤖 Generated with Claude Code
https://claude.ai/code/session_01PZJLynVBkgLtehJFXffnfg
Generated by Claude Code