# Circuit List Editor Migration ## Goal Migrate legacy row-first consumers into the circuit-first model without deleting legacy data. ## Legacy Mapping Legacy `Consumer` rows map into: - `Circuit` for shared circuit identity and circuit-level technical fields - `CircuitDeviceRow` for per-device load rows Multiple legacy consumers can map into one circuit when they share normalized circuit identity. ## Grouping Strategy (`circuitNumber`) Migration groups legacy rows by normalized `circuitNumber`: - valid/normalizable values become one target circuit per normalized value - duplicates are grouped under that circuit (multiple `CircuitDeviceRow`s) - missing/invalid values trigger generated identifiers and may fall back to `unassigned` section ## Default Section Backfill Before migration, default sections are created/backfilled per circuit list. This guarantees a valid target section space, including `unassigned` when no section can be inferred. ## Migration Commands Run in this order for local database workflows: 1. Backup: - `npm run db:backup` 2. Migrate schema: - `npm run db:migrate` 3. Verify circuit schema: - `npm run db:verify:circuit-schema` 4. Backfill missing sections: - `npm run db:backfill:sections` 5. Migrate legacy consumers: - `npm run db:migrate:legacy-consumers` ## Validation Checks After migration, verify: - tree endpoint returns sections/circuits/rows - grouped duplicate circuit numbers are reported - generated identifiers are reported where expected - migrated rows include `legacyConsumerId` traceability - no duplicate BMKs exist inside one circuit list ## If Tree Endpoint Returns Empty Sections Likely causes: - circuit-first tables missing (migration not run) - sections not backfilled yet - migrated dataset genuinely empty for selected list Actions: 1. Run schema migration and verification commands. 2. Run section backfill command. 3. Run legacy-consumer migration command. 4. Retry tree endpoint. ## Legacy Data Retention Do not delete legacy consumers yet. - legacy endpoints/views may still depend on them - migration trace tables reference old/new mapping - keeping legacy rows allows comparison and rollback validation during transition