import { describe, expect, it, vi } from 'vitest';

import { LeagueScoringConfig } from '@core/racing/domain/entities/LeagueScoringConfig';

import { LeagueScoringConfigOrmEntity } from '../entities/LeagueScoringConfigOrmEntity';
import { TypeOrmPersistenceSchemaError } from '../errors/TypeOrmPersistenceSchemaError';
import { LeagueScoringConfigOrmMapper } from './LeagueScoringConfigOrmMapper';
import { ChampionshipConfigJsonMapper, type SerializedChampionshipConfig } from './ChampionshipConfigJsonMapper';
import { PointsTableJsonMapper } from './PointsTableJsonMapper';

describe('LeagueScoringConfigOrmMapper', () => {
  it('toDomain uses rehydrate semantics (does not call create)', () => {
    const pointsTableMapper = new PointsTableJsonMapper();
    const championshipMapper = new ChampionshipConfigJsonMapper(pointsTableMapper);
    const mapper = new LeagueScoringConfigOrmMapper(championshipMapper);

    const serializedChampionship: SerializedChampionshipConfig = {
      id: 'champ-1',
      name: 'Main Championship',
      type: 'driver',
      sessionTypes: ['main'],
      pointsTableBySessionType: {
        main: { pointsByPosition: { '1': 25, '2': 18 } },
      } as unknown as SerializedChampionshipConfig['pointsTableBySessionType'],
      dropScorePolicy: { strategy: 'none' },
    };

    const entity = new LeagueScoringConfigOrmEntity();
    entity.id = 'scoring-config-season-1';
    entity.seasonId = 'season-1';
    entity.scoringPresetId = null;
    entity.championships = [serializedChampionship];

    const createSpy = vi.spyOn(LeagueScoringConfig, 'create').mockImplementation(() => {
      throw new Error('create-called');
    });

    expect(() => mapper.toDomain(entity)).not.toThrow();
    expect(createSpy).not.toHaveBeenCalled();
  });

  it('toDomain validates schema: non-array championships yields adapter-scoped base schema error type', () => {
    const pointsTableMapper = new PointsTableJsonMapper();
    const championshipMapper = new ChampionshipConfigJsonMapper(pointsTableMapper);
    const mapper = new LeagueScoringConfigOrmMapper(championshipMapper);

    const entity = new LeagueScoringConfigOrmEntity();
    entity.id = 'scoring-config-season-1';
    entity.seasonId = 'season-1';
    entity.scoringPresetId = null;
    entity.championships = { not: 'an-array' } as unknown as never;

    try {
      mapper.toDomain(entity);
      throw new Error('expected-to-throw');
    } catch (error) {
      expect(error).toBeInstanceOf(TypeOrmPersistenceSchemaError);
      expect(error).toMatchObject({
        entityName: 'LeagueScoringConfig',
        fieldName: 'championships',
        reason: 'not_array',
      });
    }
  });
});