diff --git a/.jules/bolt.md b/.jules/bolt.md index f1a8c146..4c9247d6 100644 --- a/.jules/bolt.md +++ b/.jules/bolt.md @@ -77,3 +77,6 @@ Optimized metric route processing to O(N) by creating a mapping of routes direct ## 2024-07-13 - [Optimize Export Dictionary FK lookups] **Learning:** Found O(N * C * E) performance bottleneck in ERD export dictionaries due to repeated array searching with `edges.some()` inside a nested loop over nodes and columns. **Action:** Replace repeated linear array scans for edges by precomputing O(1) Set lookups of foreign key column handles per node before looping. +## 2024-11-20 - Ensure ERD node edge handle compatibility after HandleId format changes +**Learning:** ERD diagrams map edges explicitly via handle ID strings (e.g. `src-c-0069-0064`). When modifying handle generation functions (such as `sanitizeHandleId`, `sourceColumnHandleId`, `targetColumnHandleId`), one must also fix test assertions in downstream consumers like `exportMermaid` and `exportDictionaryCsv` which mock the exact output structure. +**Action:** When updating a core string format function, always run a full repository search or full test suite locally before submitting to prevent silent breakage of dependent mock tests. diff --git a/frontend/src/erd/handleUtils.test.ts b/frontend/src/erd/handleUtils.test.ts index 0278739e..731e1649 100644 --- a/frontend/src/erd/handleUtils.test.ts +++ b/frontend/src/erd/handleUtils.test.ts @@ -3,24 +3,20 @@ import { sanitizeHandleId, sourceColumnHandleId, targetColumnHandleId } from './ describe('handleUtils', () => { describe('sanitizeHandleId', () => { - it('should encode a simple ascii string', () => { - expect(sanitizeHandleId('id')).toBe('c-0069-0064'); - }); - - it('should handle empty string', () => { - expect(sanitizeHandleId('')).toBe('c-empty'); - }); - - it('should handle special characters', () => { - expect(sanitizeHandleId('user_id')).toBe('c-0075-0073-0065-0072-005f-0069-0064'); - }); - - it('should handle unicode characters', () => { - expect(sanitizeHandleId('id_가')).toBe('c-0069-0064-005f-ac00'); - }); - - it('should handle emojis', () => { - expect(sanitizeHandleId('id_🚀')).toBe('c-0069-0064-005f-1f680'); + it.each([ + ['simple ascii string', 'id', 'c-0069-0064'], + ['empty string', '', 'c-empty'], + ['special characters', 'user_id', 'c-0075-0073-0065-0072-005f-0069-0064'], + ['unicode characters', 'id_가', 'c-0069-0064-005f-ac00'], + ['emojis', 'id_🚀', 'c-0069-0064-005f-1f680'], + ['alphanumeric', 'id123', 'c-0069-0064-0031-0032-0033'], + ['spaces', 'user id', 'c-0075-0073-0065-0072-0020-0069-0064'], + ['special symbols', '!@#$%', 'c-0021-0040-0023-0024-0025'], + ['control characters', '\n\t', 'c-000a-0009'], + ['combining characters', 'e\u0301', 'c-0065-0301'], + ['emoji with zwj', '👨‍👩‍👦', 'c-1f468-200d-1f469-200d-1f466'], + ])('should handle %s', (_, input, expected) => { + expect(sanitizeHandleId(input)).toBe(expected); }); });