Files
web-cad/frontend/tests/commandRegistry.test.ts
T
Leopoldadmin 1bcfaffdd4 fix: replace hardcoded localhost:3001 with relative API URL + add canvas mock and integration test
- Fix frontend Network error: API_BASE now defaults to empty string (same-origin)
- Fix 3 files: api.ts, AuthContext.tsx, Dashboard.tsx
- Add Canvas 2D context mock in tests/setup.ts for jsdom
- Fix -0 vs +0 in ZoomPanController.getViewport()
- Add IntegrationWorkflow.test.ts (35 tests, full CAD workflow)
2026-06-26 17:48:24 +02:00

260 lines
7.9 KiB
TypeScript
Raw Blame History

This file contains ambiguous Unicode characters
This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.
/**
* commandRegistry Tests Command lookup, autocomplete, categories
*/
import { describe, it, expect, beforeEach } from 'vitest';
import { CommandRegistry } from '../src/services/commandRegistry';
import type { CommandDefinition } from '../src/services/commandRegistry';
describe('CommandRegistry', () => {
let registry: CommandRegistry;
beforeEach(() => {
registry = new CommandRegistry();
});
describe('lookup by name', () => {
it('should find LINE by name', () => {
const cmd = registry.lookup('LINE');
expect(cmd).not.toBeNull();
expect(cmd!.name).toBe('LINE');
expect(cmd!.toolId).toBe('line');
});
it('should find CIRCLE by name', () => {
const cmd = registry.lookup('CIRCLE');
expect(cmd).not.toBeNull();
expect(cmd!.name).toBe('CIRCLE');
});
it('should find RECT by name', () => {
const cmd = registry.lookup('RECT');
expect(cmd).not.toBeNull();
expect(cmd!.name).toBe('RECT');
});
it('should find UNDO by name', () => {
const cmd = registry.lookup('UNDO');
expect(cmd).not.toBeNull();
expect(cmd!.category).toBe('meta');
});
it('should be case insensitive', () => {
const cmd = registry.lookup('line');
expect(cmd).not.toBeNull();
expect(cmd!.name).toBe('LINE');
});
it('should trim whitespace', () => {
const cmd = registry.lookup(' LINE ');
expect(cmd).not.toBeNull();
expect(cmd!.name).toBe('LINE');
});
});
describe('lookup by alias', () => {
it('should find LINE by alias L', () => {
const cmd = registry.lookup('L');
expect(cmd).not.toBeNull();
expect(cmd!.name).toBe('LINE');
});
it('should find CIRCLE by alias C', () => {
const cmd = registry.lookup('C');
expect(cmd).not.toBeNull();
expect(cmd!.name).toBe('CIRCLE');
});
it('should find RECT by alias R', () => {
const cmd = registry.lookup('R');
expect(cmd).not.toBeNull();
expect(cmd!.name).toBe('RECT');
});
it('should find MOVE by alias M', () => {
const cmd = registry.lookup('M');
expect(cmd).not.toBeNull();
expect(cmd!.name).toBe('MOVE');
});
it('should find ERASE by alias E and DEL', () => {
expect(registry.lookup('E')!.name).toBe('ERASE');
expect(registry.lookup('DEL')!.name).toBe('ERASE');
});
it('should find POLYLINE by alias PL', () => {
const cmd = registry.lookup('PL');
expect(cmd).not.toBeNull();
expect(cmd!.name).toBe('POLYLINE');
});
it('should find German alias LINIE for LINE', () => {
const cmd = registry.lookup('LINIE');
expect(cmd).not.toBeNull();
expect(cmd!.name).toBe('LINE');
});
});
describe('lookup unknown command', () => {
it('should return null for unknown command', () => {
expect(registry.lookup('UNKNOWN')).toBeNull();
});
it('should return null for empty string', () => {
expect(registry.lookup('')).toBeNull();
});
it('should return null for random text', () => {
expect(registry.lookup('XYZABC')).toBeNull();
});
});
describe('getToolId', () => {
it('should return toolId for LINE', () => {
expect(registry.getToolId('LINE')).toBe('line');
});
it('should return toolId for CIRCLE alias C', () => {
expect(registry.getToolId('C')).toBe('circle');
});
it('should return null for meta commands like UNDO', () => {
expect(registry.getToolId('UNDO')).toBeNull();
});
it('should return null for unknown command', () => {
expect(registry.getToolId('UNKNOWN')).toBeNull();
});
});
describe('getLabel', () => {
it('should return label for LINE', () => {
const label = registry.getLabel('LINE');
expect(label).not.toBeNull();
expect(label).toContain('Linie');
});
it('should return label for alias L', () => {
const label = registry.getLabel('L');
expect(label).not.toBeNull();
expect(label).toContain('Linie');
});
it('should return null for unknown command', () => {
expect(registry.getLabel('UNKNOWN')).toBeNull();
});
});
describe('getAllCommands', () => {
it('should return all command definitions', () => {
const all = registry.getAllCommands();
expect(all.length).toBeGreaterThan(10);
});
it('should include LINE, CIRCLE, RECT, MOVE, UNDO', () => {
const all = registry.getAllCommands();
const names = all.map(c => c.name);
expect(names).toContain('LINE');
expect(names).toContain('CIRCLE');
expect(names).toContain('RECT');
expect(names).toContain('MOVE');
expect(names).toContain('UNDO');
});
});
describe('autocomplete', () => {
it('should return exact match first', () => {
const results = registry.autocomplete('L');
expect(results.length).toBeGreaterThan(0);
// Exact alias match 'L' should be LINE (priority 1)
expect(results[0].name).toBe('LINE');
});
it('should return commands starting with input', () => {
const results = registry.autocomplete('LI');
expect(results.length).toBeGreaterThan(0);
const names = results.map(c => c.name);
expect(names).toContain('LINE');
});
it('should return empty for empty input', () => {
expect(registry.autocomplete('')).toEqual([]);
});
it('should return max 10 results', () => {
const results = registry.autocomplete('A');
expect(results.length).toBeLessThanOrEqual(10);
});
it('should match aliases', () => {
const results = registry.autocomplete('PL');
expect(results.length).toBeGreaterThan(0);
const names = results.map(c => c.name);
expect(names).toContain('POLYLINE');
});
it('should match case-insensitively', () => {
const results = registry.autocomplete('line');
expect(results.length).toBeGreaterThan(0);
expect(results[0].name).toBe('LINE');
});
});
describe('getAllNames', () => {
it('should return all names and aliases in uppercase', () => {
const names = registry.getAllNames();
expect(names.length).toBeGreaterThan(10);
expect(names.every(n => n === n.toUpperCase())).toBe(true);
});
it('should include LINE and alias L', () => {
const names = registry.getAllNames();
expect(names).toContain('LINE');
expect(names).toContain('L');
});
});
describe('categories', () => {
it('should have draw category commands', () => {
const all = registry.getAllCommands();
const draw = all.filter(c => c.category === 'draw');
expect(draw.length).toBeGreaterThan(5);
const names = draw.map(c => c.name);
expect(names).toContain('LINE');
expect(names).toContain('CIRCLE');
});
it('should have modify category commands', () => {
const all = registry.getAllCommands();
const modify = all.filter(c => c.category === 'modify');
expect(modify.length).toBeGreaterThan(5);
const names = modify.map(c => c.name);
expect(names).toContain('MOVE');
expect(names).toContain('ROTATE');
});
it('should have view category commands', () => {
const all = registry.getAllCommands();
const view = all.filter(c => c.category === 'view');
expect(view.length).toBeGreaterThan(0);
const names = view.map(c => c.name);
expect(names).toContain('PAN');
expect(names).toContain('ZOOM');
});
it('should have meta category commands', () => {
const all = registry.getAllCommands();
const meta = all.filter(c => c.category === 'meta');
expect(meta.length).toBeGreaterThan(0);
const names = meta.map(c => c.name);
expect(names).toContain('UNDO');
expect(names).toContain('REDO');
});
it('should have special category commands', () => {
const all = registry.getAllCommands();
const special = all.filter(c => c.category === 'special');
expect(special.length).toBeGreaterThan(0);
});
});
});