@fgv/ts-sudoku-ui 5.1.0-2 → 5.1.0-21
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/eslint.config.js +18 -0
- package/lib/tsdoc-metadata.json +1 -1
- package/package.json +22 -21
- package/.test-failures-catalog.md +0 -470
- package/CHANGELOG.md +0 -11
- package/CSS_MODULES_MIGRATION_SUMMARY.md +0 -189
- package/dist/ts-sudoku-ui.d.ts +0 -668
- package/etc/ts-sudoku-ui.api.md +0 -481
- package/lib/test/fixtures/killerSudokuPuzzles.d.ts +0 -36
- package/lib/test/fixtures/killerSudokuPuzzles.d.ts.map +0 -1
- package/lib/test/fixtures/killerSudokuPuzzles.js +0 -57
- package/lib/test/fixtures/killerSudokuPuzzles.js.map +0 -1
- package/lib/test/unit/components/SudokuGridEntry.testHelpers.d.ts +0 -22
- package/lib/test/unit/components/SudokuGridEntry.testHelpers.d.ts.map +0 -1
- package/lib/test/unit/components/SudokuGridEntry.testHelpers.js +0 -116
- package/lib/test/unit/components/SudokuGridEntry.testHelpers.js.map +0 -1
- package/lib-commonjs/components/CageOverlay.js +0 -138
- package/lib-commonjs/components/CageOverlay.js.map +0 -1
- package/lib-commonjs/components/CageSumIndicator.js +0 -71
- package/lib-commonjs/components/CageSumIndicator.js.map +0 -1
- package/lib-commonjs/components/CombinationCard.js +0 -68
- package/lib-commonjs/components/CombinationCard.js.map +0 -1
- package/lib-commonjs/components/CombinationGrid.js +0 -56
- package/lib-commonjs/components/CombinationGrid.js.map +0 -1
- package/lib-commonjs/components/CompactControlRibbon.js +0 -146
- package/lib-commonjs/components/CompactControlRibbon.js.map +0 -1
- package/lib-commonjs/components/DualKeypad.js +0 -142
- package/lib-commonjs/components/DualKeypad.js.map +0 -1
- package/lib-commonjs/components/KillerCombinationsExplorer.js +0 -74
- package/lib-commonjs/components/KillerCombinationsExplorer.js.map +0 -1
- package/lib-commonjs/components/KillerCombinationsModal.js +0 -140
- package/lib-commonjs/components/KillerCombinationsModal.js.map +0 -1
- package/lib-commonjs/components/KillerCombinationsPanel.js +0 -84
- package/lib-commonjs/components/KillerCombinationsPanel.js.map +0 -1
- package/lib-commonjs/components/NumberKeypad.js +0 -186
- package/lib-commonjs/components/NumberKeypad.js.map +0 -1
- package/lib-commonjs/components/SudokuCell.js +0 -245
- package/lib-commonjs/components/SudokuCell.js.map +0 -1
- package/lib-commonjs/components/SudokuControls.js +0 -145
- package/lib-commonjs/components/SudokuControls.js.map +0 -1
- package/lib-commonjs/components/SudokuGrid.js +0 -182
- package/lib-commonjs/components/SudokuGrid.js.map +0 -1
- package/lib-commonjs/components/SudokuGridEntry.js +0 -378
- package/lib-commonjs/components/SudokuGridEntry.js.map +0 -1
- package/lib-commonjs/components/ValidationDisplay.js +0 -100
- package/lib-commonjs/components/ValidationDisplay.js.map +0 -1
- package/lib-commonjs/contexts/DiagnosticLoggerContext.js +0 -104
- package/lib-commonjs/contexts/DiagnosticLoggerContext.js.map +0 -1
- package/lib-commonjs/contexts/index.js +0 -32
- package/lib-commonjs/contexts/index.js.map +0 -1
- package/lib-commonjs/hooks/useCombinationElimination.js +0 -126
- package/lib-commonjs/hooks/useCombinationElimination.js.map +0 -1
- package/lib-commonjs/hooks/useKeyboardShortcut.js +0 -58
- package/lib-commonjs/hooks/useKeyboardShortcut.js.map +0 -1
- package/lib-commonjs/hooks/useKillerCombinations.js +0 -68
- package/lib-commonjs/hooks/useKillerCombinations.js.map +0 -1
- package/lib-commonjs/hooks/useLongPress.js +0 -72
- package/lib-commonjs/hooks/useLongPress.js.map +0 -1
- package/lib-commonjs/hooks/usePuzzleSession.js +0 -401
- package/lib-commonjs/hooks/usePuzzleSession.js.map +0 -1
- package/lib-commonjs/hooks/useResponsiveLayout.js +0 -142
- package/lib-commonjs/hooks/useResponsiveLayout.js.map +0 -1
- package/lib-commonjs/index.browser.js +0 -29
- package/lib-commonjs/index.browser.js.map +0 -1
- package/lib-commonjs/index.js +0 -73
- package/lib-commonjs/index.js.map +0 -1
- package/lib-commonjs/test/fixtures/killerSudokuPuzzles.js +0 -60
- package/lib-commonjs/test/fixtures/killerSudokuPuzzles.js.map +0 -1
- package/lib-commonjs/test/unit/components/SudokuGridEntry.testHelpers.js +0 -125
- package/lib-commonjs/test/unit/components/SudokuGridEntry.testHelpers.js.map +0 -1
- package/lib-commonjs/types/index.js +0 -26
- package/lib-commonjs/types/index.js.map +0 -1
- package/lib-commonjs/utils/CageLookupManager.js +0 -287
- package/lib-commonjs/utils/CageLookupManager.js.map +0 -1
- package/lib-commonjs/utils/CagePatternManager.js +0 -143
- package/lib-commonjs/utils/CagePatternManager.js.map +0 -1
- package/lib-commonjs/utils/puzzleDefinitionHelper.js +0 -103
- package/lib-commonjs/utils/puzzleDefinitionHelper.js.map +0 -1
package/eslint.config.js
ADDED
|
@@ -0,0 +1,18 @@
|
|
|
1
|
+
// ESLint 9 flat config
|
|
2
|
+
const nodeProfile = require('@rushstack/eslint-config/flat/profile/node');
|
|
3
|
+
const packletsPlugin = require('@rushstack/eslint-config/flat/mixins/packlets');
|
|
4
|
+
const tsdocPlugin = require('@rushstack/eslint-config/flat/mixins/tsdoc');
|
|
5
|
+
|
|
6
|
+
module.exports = [
|
|
7
|
+
...nodeProfile,
|
|
8
|
+
packletsPlugin,
|
|
9
|
+
...tsdocPlugin,
|
|
10
|
+
{
|
|
11
|
+
// Override specific rules if needed
|
|
12
|
+
rules: {
|
|
13
|
+
'@rushstack/packlets/mechanics': 'warn',
|
|
14
|
+
// Disable no-new-null rule for React components where null is conventional
|
|
15
|
+
'@rushstack/no-new-null': 'off'
|
|
16
|
+
}
|
|
17
|
+
}
|
|
18
|
+
];
|
package/lib/tsdoc-metadata.json
CHANGED
package/package.json
CHANGED
|
@@ -1,19 +1,9 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@fgv/ts-sudoku-ui",
|
|
3
|
-
"version": "5.1.0-
|
|
3
|
+
"version": "5.1.0-21",
|
|
4
4
|
"description": "React components for interactive Sudoku puzzle entry and display",
|
|
5
5
|
"main": "lib/index.js",
|
|
6
6
|
"types": "lib/index.d.ts",
|
|
7
|
-
"scripts": {
|
|
8
|
-
"build": "heft build --clean",
|
|
9
|
-
"build-docs": "typedoc --options ./config/typedoc.json",
|
|
10
|
-
"build-all": "rushx build && rushx build-docs",
|
|
11
|
-
"clean": "heft clean",
|
|
12
|
-
"test": "heft test --clean",
|
|
13
|
-
"lint": "eslint src --ext .ts,.tsx",
|
|
14
|
-
"fixlint": "eslint src --ext .ts,.tsx --fix",
|
|
15
|
-
"coverage": "jest --coverage"
|
|
16
|
-
},
|
|
17
7
|
"sideEffects": false,
|
|
18
8
|
"keywords": [
|
|
19
9
|
"typescript",
|
|
@@ -31,18 +21,16 @@
|
|
|
31
21
|
},
|
|
32
22
|
"homepage": "https://github.com/ErikFortune/fgv/tree/main/libraries/ts-sudoku-ui#readme",
|
|
33
23
|
"dependencies": {
|
|
34
|
-
"
|
|
35
|
-
"@fgv/ts-
|
|
36
|
-
"@fgv/ts-
|
|
37
|
-
"
|
|
24
|
+
"tslib": "^2.8.1",
|
|
25
|
+
"@fgv/ts-sudoku-lib": "5.1.0-21",
|
|
26
|
+
"@fgv/ts-utils": "5.1.0-21",
|
|
27
|
+
"@fgv/ts-json-base": "5.1.0-21"
|
|
38
28
|
},
|
|
39
29
|
"peerDependencies": {
|
|
40
30
|
"react": ">=18.0.0",
|
|
41
31
|
"react-dom": ">=18.0.0"
|
|
42
32
|
},
|
|
43
33
|
"devDependencies": {
|
|
44
|
-
"@fgv/heft-dual-rig": "workspace:*",
|
|
45
|
-
"@fgv/ts-utils-jest": "workspace:*",
|
|
46
34
|
"@types/react": "~19.2.8",
|
|
47
35
|
"@types/react-dom": "~19.2.3",
|
|
48
36
|
"react": "~19.2.3",
|
|
@@ -64,8 +52,8 @@
|
|
|
64
52
|
"rimraf": "^6.1.2",
|
|
65
53
|
"ts-jest": "^29.4.6",
|
|
66
54
|
"typescript": "5.9.3",
|
|
67
|
-
"@rushstack/heft": "1.2.
|
|
68
|
-
"@rushstack/heft-web-rig": "1.4.
|
|
55
|
+
"@rushstack/heft": "1.2.7",
|
|
56
|
+
"@rushstack/heft-web-rig": "1.4.3",
|
|
69
57
|
"@rushstack/eslint-config": "4.6.4",
|
|
70
58
|
"@rushstack/heft-jest-plugin": "1.2.6",
|
|
71
59
|
"@microsoft/api-documenter": "^7.28.2",
|
|
@@ -75,7 +63,10 @@
|
|
|
75
63
|
"postcss": "~8.5.6",
|
|
76
64
|
"autoprefixer": "~10.4.23",
|
|
77
65
|
"typedoc": "~0.28.16",
|
|
78
|
-
"typedoc-plugin-markdown": "~4.9.0"
|
|
66
|
+
"typedoc-plugin-markdown": "~4.9.0",
|
|
67
|
+
"@fgv/heft-dual-rig": "5.1.0-21",
|
|
68
|
+
"@fgv/typedoc-compact-theme": "5.1.0-21",
|
|
69
|
+
"@fgv/ts-utils-jest": "5.1.0-21"
|
|
79
70
|
},
|
|
80
71
|
"exports": {
|
|
81
72
|
".": {
|
|
@@ -93,5 +84,15 @@
|
|
|
93
84
|
"repository": {
|
|
94
85
|
"type": "git",
|
|
95
86
|
"url": "https://github.com/ErikFortune/fgv.git"
|
|
87
|
+
},
|
|
88
|
+
"scripts": {
|
|
89
|
+
"build": "heft build --clean",
|
|
90
|
+
"build-docs": "typedoc --options ./config/typedoc.json",
|
|
91
|
+
"build-all": "rushx build && rushx build-docs",
|
|
92
|
+
"clean": "heft clean",
|
|
93
|
+
"test": "heft test --clean",
|
|
94
|
+
"lint": "eslint src --ext .ts,.tsx",
|
|
95
|
+
"fixlint": "eslint src --ext .ts,.tsx --fix",
|
|
96
|
+
"coverage": "jest --coverage"
|
|
96
97
|
}
|
|
97
|
-
}
|
|
98
|
+
}
|
|
@@ -1,470 +0,0 @@
|
|
|
1
|
-
# Test Failures Catalog - ts-sudoku-ui
|
|
2
|
-
|
|
3
|
-
**Date**: 2025-01-27
|
|
4
|
-
**Total Tests**: 309
|
|
5
|
-
**Passing**: 262 (84.7%)
|
|
6
|
-
**Failing**: 47 (15.3%)
|
|
7
|
-
|
|
8
|
-
---
|
|
9
|
-
|
|
10
|
-
## Summary by Test Suite
|
|
11
|
-
|
|
12
|
-
| Test Suite | Passing | Failing | Status |
|
|
13
|
-
|------------|---------|---------|--------|
|
|
14
|
-
| usePuzzleSession.test.ts | 30 | 5 | ⚠️ Partial |
|
|
15
|
-
| SudokuGridEntry.test.tsx | 3 | 30 | ❌ Critical |
|
|
16
|
-
| SudokuGridSudokuX.test.tsx | 7 | 12 | ❌ Major |
|
|
17
|
-
| usePuzzleSessionNotes.test.ts | 0 | 0 | ❌ Timeout/OOM |
|
|
18
|
-
|
|
19
|
-
---
|
|
20
|
-
|
|
21
|
-
## 1. usePuzzleSession.test.ts (5 failures)
|
|
22
|
-
|
|
23
|
-
### Issue Type: Async Timing Problems
|
|
24
|
-
|
|
25
|
-
**Root Cause**: Tests expect synchronous hook initialization, but `usePuzzleSession` uses `useEffect` for async initialization.
|
|
26
|
-
|
|
27
|
-
### Failing Tests:
|
|
28
|
-
|
|
29
|
-
#### 1.1 "should update when initial puzzle description changes"
|
|
30
|
-
```typescript
|
|
31
|
-
// Location: Line 93
|
|
32
|
-
// Error: expect(received).toBe(expected)
|
|
33
|
-
// Expected: "simple-puzzle"
|
|
34
|
-
// Received: undefined
|
|
35
|
-
```
|
|
36
|
-
**Problem**: Session.id is undefined because useEffect hasn't completed
|
|
37
|
-
**Fix Needed**: Increase waitFor timeout or add initial render wait
|
|
38
|
-
|
|
39
|
-
#### 1.2 "should show immutable cells for pre-filled puzzle"
|
|
40
|
-
```typescript
|
|
41
|
-
// Location: Line 131
|
|
42
|
-
// Error: expect(received).toBeGreaterThan(expected)
|
|
43
|
-
// Expected: > 0
|
|
44
|
-
// Received: 0
|
|
45
|
-
```
|
|
46
|
-
**Problem**: cellDisplayInfo array is empty before useEffect completes
|
|
47
|
-
**Fix Needed**: Wait for cellDisplayInfo.length > 0 before assertions
|
|
48
|
-
|
|
49
|
-
#### 1.3 "should not allow updates to immutable cells"
|
|
50
|
-
```typescript
|
|
51
|
-
// Location: Line 209
|
|
52
|
-
// Error: expect(received).toBeGreaterThan(expected)
|
|
53
|
-
// Expected: > 0
|
|
54
|
-
// Received: 0
|
|
55
|
-
```
|
|
56
|
-
**Problem**: Same as 1.2 - cellDisplayInfo not populated yet
|
|
57
|
-
**Fix Needed**: Same as 1.2
|
|
58
|
-
|
|
59
|
-
#### 1.4 "should reset puzzle to initial state"
|
|
60
|
-
```typescript
|
|
61
|
-
// Location: Line 451
|
|
62
|
-
// Error: expect(received).toBeGreaterThan(expected)
|
|
63
|
-
// Expected: > 0
|
|
64
|
-
// Received: 0
|
|
65
|
-
```
|
|
66
|
-
**Problem**: Same as 1.2 - cellDisplayInfo not populated yet
|
|
67
|
-
**Fix Needed**: Same as 1.2
|
|
68
|
-
|
|
69
|
-
#### 1.5 "should reset without error when session exists"
|
|
70
|
-
```typescript
|
|
71
|
-
// Location: Line 487
|
|
72
|
-
// Error: expect(received).not.toBeNull()
|
|
73
|
-
// Received: null
|
|
74
|
-
```
|
|
75
|
-
**Problem**: Session is null before useEffect completes
|
|
76
|
-
**Fix Needed**: Wait for session to be non-null
|
|
77
|
-
|
|
78
|
-
### Recommended Solution:
|
|
79
|
-
```typescript
|
|
80
|
-
// Option 1: Add longer timeout to waitFor
|
|
81
|
-
await waitFor(() => {
|
|
82
|
-
expect(result.current.session).not.toBeNull();
|
|
83
|
-
}, { timeout: 5000 });
|
|
84
|
-
|
|
85
|
-
// Option 2: Make hook initialization synchronous
|
|
86
|
-
// Move session creation outside useEffect if possible
|
|
87
|
-
|
|
88
|
-
// Option 3: Use renderHook with initialProps and wait
|
|
89
|
-
const { result } = renderHook(() => usePuzzleSession(puzzle));
|
|
90
|
-
await waitFor(() => result.current.session !== null);
|
|
91
|
-
```
|
|
92
|
-
|
|
93
|
-
---
|
|
94
|
-
|
|
95
|
-
## 2. SudokuGridEntry.test.tsx (30 failures)
|
|
96
|
-
|
|
97
|
-
### Issue Type: Component Not Rendering
|
|
98
|
-
|
|
99
|
-
**Root Cause**: SudokuGridEntry component depends on usePuzzleSession hook, which has async initialization issues. Component doesn't render until session is ready.
|
|
100
|
-
|
|
101
|
-
### Failing Tests: ALL 30 tests
|
|
102
|
-
|
|
103
|
-
**Common Error Pattern**:
|
|
104
|
-
```
|
|
105
|
-
Unable to find an element by: [data-testid="sudoku-grid-entry"]
|
|
106
|
-
|
|
107
|
-
<body id="test-root" />
|
|
108
|
-
```
|
|
109
|
-
|
|
110
|
-
### Test Categories:
|
|
111
|
-
|
|
112
|
-
#### 2.1 Rendering Tests (5 failures)
|
|
113
|
-
- should render loading state initially
|
|
114
|
-
- should render main components after initialization
|
|
115
|
-
- should apply custom className
|
|
116
|
-
- should render with initial puzzle description
|
|
117
|
-
- should render default puzzle when no initial description provided
|
|
118
|
-
|
|
119
|
-
**Problem**: Component body is completely empty
|
|
120
|
-
|
|
121
|
-
#### 2.2 Error Handling Tests (2 failures)
|
|
122
|
-
- should show error state for invalid puzzle
|
|
123
|
-
- should apply className even in error state
|
|
124
|
-
|
|
125
|
-
**Problem**: Error state elements not found (sudoku-grid-entry-error)
|
|
126
|
-
|
|
127
|
-
#### 2.3 Loading State Tests (1 failure)
|
|
128
|
-
- should show loading state when session is null
|
|
129
|
-
|
|
130
|
-
**Problem**: Cannot find sudoku-grid-entry element
|
|
131
|
-
|
|
132
|
-
#### 2.4 Cell Interaction Tests (3 failures)
|
|
133
|
-
- should handle cell selection
|
|
134
|
-
- should handle cell value changes
|
|
135
|
-
- should handle keyboard navigation
|
|
136
|
-
|
|
137
|
-
**Problem**: Cannot find sudoku-grid child elements
|
|
138
|
-
|
|
139
|
-
#### 2.5 Controls Integration Tests (4 failures)
|
|
140
|
-
- should handle undo/redo operations
|
|
141
|
-
- should handle reset operation
|
|
142
|
-
- should handle export operation
|
|
143
|
-
- should handle export with custom puzzle data
|
|
144
|
-
|
|
145
|
-
**Problem**: Cannot find sudoku-controls element
|
|
146
|
-
|
|
147
|
-
#### 2.6 Validation Display Tests (3 failures)
|
|
148
|
-
- should show validation errors for duplicate values
|
|
149
|
-
- should clear validation errors when conflicts resolved
|
|
150
|
-
- should update validation display when cells change
|
|
151
|
-
|
|
152
|
-
**Problem**: Cannot find validation-display element
|
|
153
|
-
|
|
154
|
-
#### 2.7 Puzzle Type Tests (2 failures)
|
|
155
|
-
- should handle standard Sudoku puzzles
|
|
156
|
-
- should handle Sudoku X puzzles
|
|
157
|
-
|
|
158
|
-
**Problem**: Component not rendering
|
|
159
|
-
|
|
160
|
-
#### 2.8 Integration Edge Cases (4 failures)
|
|
161
|
-
- should handle puzzle type changes
|
|
162
|
-
- should handle rapid state updates
|
|
163
|
-
- should maintain state consistency across operations
|
|
164
|
-
- should handle all control operations in sequence
|
|
165
|
-
|
|
166
|
-
**Problem**: Component not rendering
|
|
167
|
-
|
|
168
|
-
#### 2.9 Layout Tests (2 failures)
|
|
169
|
-
- should render components in correct order
|
|
170
|
-
- should apply responsive styling
|
|
171
|
-
|
|
172
|
-
**Problem**: Component not rendering
|
|
173
|
-
|
|
174
|
-
#### 2.10 Additional Tests (4 more failures)
|
|
175
|
-
All with same issue - component not rendering
|
|
176
|
-
|
|
177
|
-
### Recommended Solution:
|
|
178
|
-
|
|
179
|
-
**Immediate**: Fix usePuzzleSession async issues first (dependency blocker)
|
|
180
|
-
|
|
181
|
-
**Then**:
|
|
182
|
-
```typescript
|
|
183
|
-
// Option 1: Update test setup to wait for component
|
|
184
|
-
const customRender = (ui: React.ReactElement) => {
|
|
185
|
-
const result = render(ui);
|
|
186
|
-
return waitFor(() => {
|
|
187
|
-
expect(screen.getByTestId('sudoku-grid-entry')).toBeInTheDocument();
|
|
188
|
-
}).then(() => result);
|
|
189
|
-
};
|
|
190
|
-
|
|
191
|
-
// Option 2: Mock usePuzzleSession hook
|
|
192
|
-
jest.mock('../../../hooks/usePuzzleSession', () => ({
|
|
193
|
-
usePuzzleSession: () => mockSessionData
|
|
194
|
-
}));
|
|
195
|
-
|
|
196
|
-
// Option 3: Fix SudokuGridEntry to show loading state while initializing
|
|
197
|
-
// Add conditional rendering:
|
|
198
|
-
if (!session) {
|
|
199
|
-
return <div data-testid="sudoku-grid-entry-loading">Loading...</div>;
|
|
200
|
-
}
|
|
201
|
-
```
|
|
202
|
-
|
|
203
|
-
---
|
|
204
|
-
|
|
205
|
-
## 3. SudokuGridSudokuX.test.tsx (12 failures)
|
|
206
|
-
|
|
207
|
-
### Issue Type: Missing Sudoku X Visual Features
|
|
208
|
-
|
|
209
|
-
**Root Cause**: Diagonal line rendering and highlighting for Sudoku X puzzles not implemented or not working correctly.
|
|
210
|
-
|
|
211
|
-
### Failing Tests:
|
|
212
|
-
|
|
213
|
-
#### 3.1 Diagonal Line Rendering Tests (2 failures)
|
|
214
|
-
|
|
215
|
-
**Test**: "should render diagonal lines for Sudoku X puzzles"
|
|
216
|
-
```typescript
|
|
217
|
-
// Location: Line 87
|
|
218
|
-
// Error: expect(received).toBeGreaterThan(expected)
|
|
219
|
-
// Expected: > 0
|
|
220
|
-
// Received: 0
|
|
221
|
-
```
|
|
222
|
-
**Problem**: No diagonal line elements found in DOM
|
|
223
|
-
**Looking for**: `[class*="diagonal"]`, `[class*="x-line"]`, `svg line`
|
|
224
|
-
**Fix Needed**: Implement diagonal line rendering in SudokuGrid component
|
|
225
|
-
|
|
226
|
-
**Test**: "should not render diagonal lines for standard Sudoku puzzles"
|
|
227
|
-
- Likely passes if diagonal rendering is properly conditional
|
|
228
|
-
|
|
229
|
-
#### 3.2 Cell Interaction Tests (3 failures)
|
|
230
|
-
|
|
231
|
-
**Test**: "should highlight diagonal cells when cell on diagonal is selected"
|
|
232
|
-
```typescript
|
|
233
|
-
// Location: Line 157
|
|
234
|
-
// Error: expect(received).toBeGreaterThan(expected)
|
|
235
|
-
// Expected: > 0
|
|
236
|
-
// Received: 0
|
|
237
|
-
```
|
|
238
|
-
**Problem**: No cells with diagonal highlight classes found
|
|
239
|
-
**Looking for**: `[class*="diagonal-highlight"]`, `[class*="diagonal-cell"]`
|
|
240
|
-
**Fix Needed**: Add diagonal cell highlighting when cell selected
|
|
241
|
-
|
|
242
|
-
**Test**: "should handle click events on diagonal cells"
|
|
243
|
-
```typescript
|
|
244
|
-
// Error: Unable to find a label with the text of: /A1|cell.*0.*0/i
|
|
245
|
-
```
|
|
246
|
-
**Problem**: Cell aria-label doesn't match expected format
|
|
247
|
-
**Current**: "Row 1, Column 1, empty"
|
|
248
|
-
**Expected**: Pattern includes "A1" or "cell.*0.*0"
|
|
249
|
-
**Fix Needed**: Update test matcher or cell aria-label format
|
|
250
|
-
|
|
251
|
-
**Test**: "should handle keyboard navigation through diagonal cells"
|
|
252
|
-
```typescript
|
|
253
|
-
// Error: expect(jest.fn()).toHaveBeenCalled()
|
|
254
|
-
// Expected: >= 1
|
|
255
|
-
// Received: 0
|
|
256
|
-
```
|
|
257
|
-
**Problem**: onSelect callback not called during navigation
|
|
258
|
-
**Fix Needed**: Verify keyboard navigation triggers onSelect for diagonal cells
|
|
259
|
-
|
|
260
|
-
#### 3.3 Validation Error Display Tests (3 failures)
|
|
261
|
-
|
|
262
|
-
**Test**: "should display validation errors for diagonal cells"
|
|
263
|
-
```typescript
|
|
264
|
-
// Error: expect(received).toBeGreaterThan(expected)
|
|
265
|
-
// Expected: > 0
|
|
266
|
-
// Received: 0
|
|
267
|
-
```
|
|
268
|
-
**Problem**: No error cells found for diagonal conflicts
|
|
269
|
-
**Fix Needed**: Ensure diagonal validation creates visible error indicators
|
|
270
|
-
|
|
271
|
-
**Test**: "should distinguish between different types of validation errors"
|
|
272
|
-
- Similar to above
|
|
273
|
-
|
|
274
|
-
**Test**: "should clear diagonal validation errors when conflict resolved"
|
|
275
|
-
- Similar to above
|
|
276
|
-
|
|
277
|
-
#### 3.4 Accessibility Tests (2 failures)
|
|
278
|
-
|
|
279
|
-
**Test**: "should provide appropriate ARIA labels for diagonal cells"
|
|
280
|
-
```typescript
|
|
281
|
-
// Error: Unable to find a label with specified pattern
|
|
282
|
-
```
|
|
283
|
-
**Problem**: Aria-labels don't indicate diagonal membership
|
|
284
|
-
**Fix Needed**: Add diagonal info to cell aria-labels
|
|
285
|
-
|
|
286
|
-
**Test**: "should announce validation errors for diagonal constraints to screen readers"
|
|
287
|
-
```typescript
|
|
288
|
-
// Error: expect(received).toBeGreaterThan(expected)
|
|
289
|
-
// Expected: > 0
|
|
290
|
-
// Received: 0
|
|
291
|
-
```
|
|
292
|
-
**Problem**: No aria-live regions or error announcements
|
|
293
|
-
**Fix Needed**: Add screen reader announcements for diagonal errors
|
|
294
|
-
|
|
295
|
-
#### 3.5 Responsive Design Test (1 failure)
|
|
296
|
-
|
|
297
|
-
**Test**: "should maintain diagonal line visibility at different zoom levels"
|
|
298
|
-
```typescript
|
|
299
|
-
// Error: expect(received).toBeGreaterThan(expected)
|
|
300
|
-
// Expected: > 0
|
|
301
|
-
// Received: 0
|
|
302
|
-
```
|
|
303
|
-
**Problem**: No diagonal lines to test
|
|
304
|
-
**Fix Needed**: Implement diagonal lines first
|
|
305
|
-
|
|
306
|
-
#### 3.6 Performance Test (1 failure)
|
|
307
|
-
|
|
308
|
-
**Test**: "should not impact performance for standard Sudoku"
|
|
309
|
-
- Dependency on diagonal rendering implementation
|
|
310
|
-
|
|
311
|
-
### Recommended Solution:
|
|
312
|
-
|
|
313
|
-
**Step 1**: Implement diagonal line rendering in SudokuGrid
|
|
314
|
-
```typescript
|
|
315
|
-
// In SudokuGrid component:
|
|
316
|
-
{puzzleType === 'sudoku-x' && (
|
|
317
|
-
<div className="absolute inset-0 pointer-events-none">
|
|
318
|
-
<svg className="w-full h-full">
|
|
319
|
-
<line
|
|
320
|
-
x1="0"
|
|
321
|
-
y1="0"
|
|
322
|
-
x2="100%"
|
|
323
|
-
y2="100%"
|
|
324
|
-
className="diagonal-line"
|
|
325
|
-
stroke="currentColor"
|
|
326
|
-
/>
|
|
327
|
-
<line
|
|
328
|
-
x1="100%"
|
|
329
|
-
y1="0"
|
|
330
|
-
x2="0"
|
|
331
|
-
y2="100%"
|
|
332
|
-
className="diagonal-line"
|
|
333
|
-
stroke="currentColor"
|
|
334
|
-
/>
|
|
335
|
-
</svg>
|
|
336
|
-
</div>
|
|
337
|
-
)}
|
|
338
|
-
```
|
|
339
|
-
|
|
340
|
-
**Step 2**: Add diagonal highlighting to cells
|
|
341
|
-
```typescript
|
|
342
|
-
// In SudokuCell or SudokuGrid:
|
|
343
|
-
const isDiagonalCell = (row, col) => row === col || row + col === 8;
|
|
344
|
-
const isOnSelectedDiagonal = selectedCell && isDiagonalCell(selectedCell.row, selectedCell.col);
|
|
345
|
-
|
|
346
|
-
// Add class: isOnSelectedDiagonal ? 'diagonal-highlight' : ''
|
|
347
|
-
```
|
|
348
|
-
|
|
349
|
-
**Step 3**: Update aria-labels to include diagonal info
|
|
350
|
-
```typescript
|
|
351
|
-
aria-label={`Row ${row + 1}, Column ${col + 1}${
|
|
352
|
-
isDiagonalCell(row, col) ? ', diagonal' : ''
|
|
353
|
-
}, ${value || 'empty'}`}
|
|
354
|
-
```
|
|
355
|
-
|
|
356
|
-
**Step 4**: Ensure validation errors show for diagonal conflicts
|
|
357
|
-
- usePuzzleSession already checks diagonal duplicates (lines 139-150)
|
|
358
|
-
- Verify error rendering in UI
|
|
359
|
-
|
|
360
|
-
---
|
|
361
|
-
|
|
362
|
-
## 4. usePuzzleSessionNotes.test.ts (Timeout/OOM)
|
|
363
|
-
|
|
364
|
-
### Issue Type: Build Error & Memory Exhaustion
|
|
365
|
-
|
|
366
|
-
**Root Cause**: TypeScript compilation error causes infinite loop or memory leak during test execution.
|
|
367
|
-
|
|
368
|
-
### Error Details:
|
|
369
|
-
|
|
370
|
-
**TypeScript Error**:
|
|
371
|
-
```
|
|
372
|
-
src/hooks/usePuzzleSession.ts(258,28):
|
|
373
|
-
error TS2802: Type 'Set<CellId>' can only be iterated through when using
|
|
374
|
-
the '--downlevelIteration' flag or with a '--target' of 'es2015' or higher.
|
|
375
|
-
```
|
|
376
|
-
|
|
377
|
-
**Runtime Error**:
|
|
378
|
-
```
|
|
379
|
-
FATAL ERROR: Ineffective mark-compacts near heap limit
|
|
380
|
-
Allocation failed - JavaScript heap out of memory
|
|
381
|
-
```
|
|
382
|
-
|
|
383
|
-
### Problematic Code:
|
|
384
|
-
```typescript
|
|
385
|
-
// Line 258 in usePuzzleSession.ts:
|
|
386
|
-
for (const cellId of affectedCells) { // affectedCells is a Set<CellId>
|
|
387
|
-
// ...
|
|
388
|
-
}
|
|
389
|
-
```
|
|
390
|
-
|
|
391
|
-
### Recommended Solution:
|
|
392
|
-
|
|
393
|
-
**Option 1**: Update tsconfig.json
|
|
394
|
-
```json
|
|
395
|
-
{
|
|
396
|
-
"compilerOptions": {
|
|
397
|
-
"downlevelIteration": true
|
|
398
|
-
}
|
|
399
|
-
}
|
|
400
|
-
```
|
|
401
|
-
|
|
402
|
-
**Option 2**: Convert Set to Array
|
|
403
|
-
```typescript
|
|
404
|
-
// Before:
|
|
405
|
-
for (const cellId of affectedCells) {
|
|
406
|
-
|
|
407
|
-
// After:
|
|
408
|
-
for (const cellId of Array.from(affectedCells)) {
|
|
409
|
-
```
|
|
410
|
-
|
|
411
|
-
**Option 3**: Use forEach
|
|
412
|
-
```typescript
|
|
413
|
-
affectedCells.forEach((cellId) => {
|
|
414
|
-
// ...
|
|
415
|
-
});
|
|
416
|
-
```
|
|
417
|
-
|
|
418
|
-
---
|
|
419
|
-
|
|
420
|
-
## Priority Ranking
|
|
421
|
-
|
|
422
|
-
### 🔴 Critical (Blocks other tests):
|
|
423
|
-
1. **usePuzzleSession async timing** - Blocks SudokuGridEntry tests
|
|
424
|
-
2. **usePuzzleSessionNotes TypeScript/OOM** - Prevents test suite completion
|
|
425
|
-
|
|
426
|
-
### 🟡 High (Feature incomplete):
|
|
427
|
-
3. **SudokuGridSudokuX diagonal rendering** - Core Sudoku X feature missing
|
|
428
|
-
|
|
429
|
-
### 🟢 Medium (Integration tests):
|
|
430
|
-
4. **SudokuGridEntry component tests** - Depends on #1
|
|
431
|
-
|
|
432
|
-
---
|
|
433
|
-
|
|
434
|
-
## Estimated Fix Complexity
|
|
435
|
-
|
|
436
|
-
| Issue | Lines of Code | Files | Complexity | Est. Time |
|
|
437
|
-
|-------|---------------|-------|------------|-----------|
|
|
438
|
-
| usePuzzleSession timing | ~50 | 1-2 | Medium | 1-2 hours |
|
|
439
|
-
| usePuzzleSessionNotes TS | ~5 | 1 | Low | 15 mins |
|
|
440
|
-
| Sudoku X diagonals | ~100-150 | 2-3 | High | 3-4 hours |
|
|
441
|
-
| SudokuGridEntry tests | ~200 | 1 | Low* | 30 mins* |
|
|
442
|
-
|
|
443
|
-
*After fixing dependencies
|
|
444
|
-
|
|
445
|
-
---
|
|
446
|
-
|
|
447
|
-
## Next Steps
|
|
448
|
-
|
|
449
|
-
1. ✅ Fix TypeScript compilation error (15 mins)
|
|
450
|
-
2. ⏳ Fix usePuzzleSession async timing (1-2 hours)
|
|
451
|
-
3. ⏳ Implement Sudoku X diagonal rendering (3-4 hours)
|
|
452
|
-
4. ⏳ Re-run SudokuGridEntry tests (should auto-fix)
|
|
453
|
-
|
|
454
|
-
**Total Estimated Time**: 5-7 hours
|
|
455
|
-
|
|
456
|
-
---
|
|
457
|
-
|
|
458
|
-
## Test Coverage Impact
|
|
459
|
-
|
|
460
|
-
**Current Coverage**: 78.48% statements, 80.55% branches
|
|
461
|
-
|
|
462
|
-
**After Fixes**: Estimated 95%+ statements, 90%+ branches
|
|
463
|
-
|
|
464
|
-
**Uncovered Areas**:
|
|
465
|
-
- CageOverlay.tsx: 22.68% (Killer Sudoku feature)
|
|
466
|
-
- CageSumIndicator.tsx: 35.95% (Killer Sudoku feature)
|
|
467
|
-
- CageLookupManager.ts: 34.98% (Killer Sudoku utils)
|
|
468
|
-
- CagePatternManager.ts: 62.44% (Killer Sudoku utils)
|
|
469
|
-
|
|
470
|
-
These are separate Killer Sudoku features, not related to current test failures.
|
package/CHANGELOG.md
DELETED