import { describe, it, expect, vi } from 'vitest';
import { CommandBus } from '@application/handlers/CommandBus';
import { QueryBus } from '@application/handlers/QueryBus';

describe('CommandBus', () => {
  it('dispatches to registered handler', () => {
    const bus = new CommandBus();
    const handler = vi.fn();
    bus.register('start-timer', handler);
    bus.execute({ type: 'start-timer', enclosId: 1 });
    expect(handler).toHaveBeenCalledWith({ type: 'start-timer', enclosId: 1 });
  });

  it('throws on unknown command', () => {
    const bus = new CommandBus();
    expect(() => bus.execute({ type: 'unknown' })).toThrow('No handler for command: unknown');
  });

  it('has returns true for registered', () => {
    const bus = new CommandBus();
    bus.register('test', vi.fn());
    expect(bus.has('test')).toBe(true);
    expect(bus.has('other')).toBe(false);
  });
});

describe('QueryBus', () => {
  it('returns value from handler', () => {
    const bus = new QueryBus();
    bus.register('get-dashboard', () => ({ total: 42 }));
    const result = bus.execute<{ total: number }>({ type: 'get-dashboard' });
    expect(result.total).toBe(42);
  });

  it('throws on unknown query', () => {
    const bus = new QueryBus();
    expect(() => bus.execute({ type: 'unknown' })).toThrow('No handler for query: unknown');
  });

  it('has returns true for registered', () => {
    const bus = new QueryBus();
    bus.register('test', () => null);
    expect(bus.has('test')).toBe(true);
  });
});
