This commit is contained in:
2025-12-10 18:28:32 +01:00
parent 6d61be9c51
commit 1303a14493
108 changed files with 3366 additions and 1559 deletions

View File

@@ -1,8 +1,9 @@
/**
* Application Query: GetRaceWithSOFQuery
*
* Use Case: GetRaceWithSOFUseCase
*
* Returns race details enriched with calculated Strength of Field (SOF).
* SOF is calculated from participant ratings if not already stored on the race.
* Orchestrates domain logic and delegates presentation to the presenter.
*/
import type { IRaceRepository } from '../../domain/repositories/IRaceRepository';
@@ -13,18 +14,13 @@ import {
AverageStrengthOfFieldCalculator,
type StrengthOfFieldCalculator,
} from '../../domain/services/StrengthOfFieldCalculator';
import type { RaceDTO } from '../dto/RaceDTO';
import type { IRaceWithSOFPresenter } from '../presenters/IRaceWithSOFPresenter';
export interface GetRaceWithSOFQueryParams {
raceId: string;
}
export interface RaceWithSOFDTO extends Omit<RaceDTO, 'strengthOfField'> {
strengthOfField: number | null;
participantCount: number;
}
export class GetRaceWithSOFQuery {
export class GetRaceWithSOFUseCase {
private readonly sofCalculator: StrengthOfFieldCalculator;
constructor(
@@ -32,12 +28,13 @@ export class GetRaceWithSOFQuery {
private readonly registrationRepository: IRaceRegistrationRepository,
private readonly resultRepository: IResultRepository,
private readonly driverRatingProvider: DriverRatingProvider,
public readonly presenter: IRaceWithSOFPresenter,
sofCalculator?: StrengthOfFieldCalculator,
) {
this.sofCalculator = sofCalculator ?? new AverageStrengthOfFieldCalculator();
}
async execute(params: GetRaceWithSOFQueryParams): Promise<RaceWithSOFDTO | null> {
async execute(params: GetRaceWithSOFQueryParams): Promise<void> {
const { raceId } = params;
const race = await this.raceRepository.findById(raceId);
@@ -69,20 +66,20 @@ export class GetRaceWithSOFQuery {
strengthOfField = this.sofCalculator.calculate(driverRatings);
}
return {
id: race.id,
leagueId: race.leagueId,
scheduledAt: race.scheduledAt.toISOString(),
track: race.track,
trackId: race.trackId,
car: race.car,
carId: race.carId,
sessionType: race.sessionType,
status: race.status,
this.presenter.present(
race.id,
race.leagueId,
race.scheduledAt,
race.track,
race.trackId,
race.car,
race.carId,
race.sessionType,
race.status,
strengthOfField,
registeredCount: race.registeredCount ?? participantIds.length,
maxParticipants: race.maxParticipants,
participantCount: participantIds.length,
};
race.registeredCount ?? participantIds.length,
race.maxParticipants,
participantIds.length
);
}
}