Unit & Integration Testing
Relevant source files
The following files were used as context for generating this wiki page:
The Dotorixel project employs a comprehensive testing strategy centered around Vitest to ensure the reliability of its 2D pixel art editor logic. The testing suite covers pure TypeScript functions, Svelte 5 reactive state machines, UI components, and WebAssembly (WASM) bindings. Testing is treated as a specification of behavior, prioritizing the defense against regressions in critical areas such as coordinate mathematics, undo/redo state consistency, and cross-platform synchronization.
The architecture separates concerns into a Rust-based core (tested via Rust unit tests and WASM integration tests) and a TypeScript/Svelte UI layer. This separation allows for high-performance logic to be verified independently of the framework while ensuring that the UI correctly feeds into the core logic.
Sources: CLAUDE.md:27-27, CLAUDE.md:214-230, tasks/records/001-pre-workflow-migration.md:12-12
Testing Infrastructure and Configuration
The project uses Vitest as its unified test runner. The configuration is optimized for a SvelteKit environment, utilizing happy-dom for DOM simulation and specialized resolution conditions to handle Svelte 5 client-side components.
Vitest Configuration
The environment is configured to support both pure logic and browser-based component testing.
| Setting | Value | Description |
|---|---|---|
| Environment | happy-dom | Simulates a browser environment for component mounting tests. |
| Setup Files | src/lib/wasm/setup.ts | Automatically initializes the WASM environment before running tests. |
| Resolution Conditions | ['browser'] | Ensures Svelte 5 mount resolves to client-side bundles. |
| Exclusions | Legacy directories | Prevents dead code from triggering false search hits or execution. |
Sources: vitest.config.ts:5-18, issues/011-canvas-size-control.md:120-123, issues/001-remove-legacy-ts-core.md:15-18
Test Environment Flow
The diagram below illustrates how Vitest initializes the testing environment, specifically focusing on the integration of WASM and Svelte components.
The testing workflow ensures WASM is ready before any logic dependent on the Rust core is executed.
Sources: vitest.config.ts:1-20, tasks/records/004-wasm-bindings.md:14-16
WASM Integration Testing
WASM integration tests bridge the gap between the Rust core and the TypeScript environment. These tests verify that wasm-bindgen wrappers correctly expose core functionality such as canvas manipulation, tool application, and history management.
Key Verified Areas
- Canvas Operations: Creation, resizing with anchors, pixel get/set, and clearing.
- Tool Logic: Pencil and eraser application, coordinate transformation, and interpolation.
- History: Snapshot-based undo/redo round-trips and state consistency.
- Viewport: Coordinate mapping (screen to canvas) and zoom/pan logic.
Sources: tasks/records/004-wasm-bindings.md:14-25, src/lib/wasm/wasm-canvas.test.ts:1-50
Verification of the communication between the TypeScript test environment and the compiled Rust core.
Sources: tasks/records/004-wasm-bindings.md:14-25, src/lib/wasm/wasm-canvas.test.ts:40-50
State Machine & Interaction Testing
Dotorixel extracts complex interaction logic (pointer tracking, gesture detection) into standalone Svelte reactive modules (.svelte.ts). These are tested using .svelte.test.ts files to ensure Svelte 5 runes ($state, $derived) behave correctly under various interaction scenarios.
Canvas Interaction State Machine
The CanvasInteraction module manages transitions between idle, drawing, panning, and pinching states.
- Drawing: Validates that
onDrawStart,onDraw, andonDrawEndare triggered by appropriate pointer events. - Panning: Verifies interaction mode changes when the Space key is held or the middle mouse button is used.
- Multi-touch: Tests the transition to 'pinching' state and viewport change callbacks.
Sources: tasks/records/049-extract-canvas-interaction.md:13-60, src/lib/canvas/canvas-interaction.svelte.test.ts:10-50
Logic Verification Example: Drawing
State transitions for the drawing interaction.
Sources: src/lib/canvas/canvas-interaction.svelte.test.ts:25-45, tasks/records/049-extract-canvas-interaction.md:40-50
UI Component Testing
Component testing in Dotorixel focuses on external behavior through the Props and callback boundary. It utilizes @testing-library/svelte to handle Svelte 5's event delegation and lifecycle.
CanvasSizeControl Component Tests
The CanvasSizeControl component is a primary example of integration testing for UI elements, verifying:
- Input Validation: Typing invalid dimensions (e.g., negative or exceeding
MAX_DIMENSION) triggers aValidationAlert. - Callback Execution: Clicking preset buttons or committing input via Enter/Blur correctly calls
onResize. - State Sync: External prop changes correctly reset local input state via
$effect.
Sources: issues/011-canvas-size-control.md:70-95, src/lib/ui-editor/CanvasSizeControl.svelte.test.ts:10-100
Component Test Suites
| Component | Test Focus | Key Utilities |
|---|---|---|
| CanvasSizeControl | Input validation, preset interaction, anchor selection | render, fireEvent, vi.fn() |
| AutoSave | Debounce timing, dirty tracking, selective persistence | vi.useFakeTimers, vi.advanceTimersByTime |
| Workspace | Tab management (add/close/switch), tab state | mount, unmount |
Sources: src/lib/ui-editor/CanvasSizeControl.svelte.test.ts:5-15, src/lib/session/auto-save.test.ts:1-10, issues/011-canvas-size-control.md:130-140
Session & Persistence Testing
Persistence logic is tested for edge cases in asynchronous data flows, such as debounced auto-saving and multi-tab synchronization.
AutoSave Logic
Tests for the AutoSave class use Vitest's fake timers to verify:
- Debouncing: Rapid changes are batched into a single write after a period of inactivity (3–5 seconds).
- Dirty Tracking: Only documents marked as changed are flushed to IndexedDB.
- Safety Nets: The
flush()method correctly handles immediate saves duringbeforeunloadorvisibilitychangeevents.
Sources: src/lib/session/auto-save.test.ts:15-65, issues/010-debounced-auto-save.md:10-35
The debounced auto-save flow ensures performance and data integrity.
Sources: issues/010-debounced-auto-save.md:10-35, src/lib/session/auto-save.test.ts:20-40
Summary of Testing Principles
The Dotorixel testing strategy emphasizes testing behaviors over implementation. By focusing on regressions in core math, interaction states, and persistence, the project maintains a "specification" of how the editor should behave across platforms. The removal of legacy TypeScript modules in favor of fully tested WASM equivalents demonstrates a commitment to maintaining a clean, high-coverage testing suite.
Sources: CLAUDE.md:214-230, issues/001-remove-legacy-ts-core.md:30-45