wip
This commit is contained in:
@@ -1,33 +1,26 @@
|
||||
/**
|
||||
* Application Query: GetLeagueStatsQuery
|
||||
*
|
||||
* Returns league statistics including average SOF across completed races.
|
||||
* Use Case for retrieving league statistics.
|
||||
* Orchestrates domain logic and delegates presentation to the presenter.
|
||||
*/
|
||||
|
||||
import type { ILeagueRepository } from '../../domain/repositories/ILeagueRepository';
|
||||
import type { IRaceRepository } from '../../domain/repositories/IRaceRepository';
|
||||
import type { IResultRepository } from '../../domain/repositories/IResultRepository';
|
||||
import type { DriverRatingProvider } from '../ports/DriverRatingProvider';
|
||||
import type { ILeagueStatsPresenter } from '../presenters/ILeagueStatsPresenter';
|
||||
import {
|
||||
AverageStrengthOfFieldCalculator,
|
||||
type StrengthOfFieldCalculator,
|
||||
} from '../../domain/services/StrengthOfFieldCalculator';
|
||||
|
||||
export interface GetLeagueStatsQueryParams {
|
||||
export interface GetLeagueStatsUseCaseParams {
|
||||
leagueId: string;
|
||||
}
|
||||
|
||||
export interface LeagueStatsDTO {
|
||||
leagueId: string;
|
||||
totalRaces: number;
|
||||
completedRaces: number;
|
||||
scheduledRaces: number;
|
||||
averageSOF: number | null;
|
||||
highestSOF: number | null;
|
||||
lowestSOF: number | null;
|
||||
}
|
||||
|
||||
export class GetLeagueStatsQuery {
|
||||
/**
|
||||
* Use Case for retrieving league statistics including average SOF across completed races.
|
||||
*/
|
||||
export class GetLeagueStatsUseCase {
|
||||
private readonly sofCalculator: StrengthOfFieldCalculator;
|
||||
|
||||
constructor(
|
||||
@@ -35,17 +28,18 @@ export class GetLeagueStatsQuery {
|
||||
private readonly raceRepository: IRaceRepository,
|
||||
private readonly resultRepository: IResultRepository,
|
||||
private readonly driverRatingProvider: DriverRatingProvider,
|
||||
public readonly presenter: ILeagueStatsPresenter,
|
||||
sofCalculator?: StrengthOfFieldCalculator,
|
||||
) {
|
||||
this.sofCalculator = sofCalculator ?? new AverageStrengthOfFieldCalculator();
|
||||
}
|
||||
|
||||
async execute(params: GetLeagueStatsQueryParams): Promise<LeagueStatsDTO | null> {
|
||||
async execute(params: GetLeagueStatsUseCaseParams): Promise<void> {
|
||||
const { leagueId } = params;
|
||||
|
||||
const league = await this.leagueRepository.findById(leagueId);
|
||||
if (!league) {
|
||||
return null;
|
||||
throw new Error(`League ${leagueId} not found`);
|
||||
}
|
||||
|
||||
const races = await this.raceRepository.findByLeagueId(leagueId);
|
||||
@@ -78,22 +72,12 @@ export class GetLeagueStatsQuery {
|
||||
}
|
||||
}
|
||||
|
||||
// Calculate aggregate stats
|
||||
const averageSOF = sofValues.length > 0
|
||||
? Math.round(sofValues.reduce((a, b) => a + b, 0) / sofValues.length)
|
||||
: null;
|
||||
|
||||
const highestSOF = sofValues.length > 0 ? Math.max(...sofValues) : null;
|
||||
const lowestSOF = sofValues.length > 0 ? Math.min(...sofValues) : null;
|
||||
|
||||
return {
|
||||
this.presenter.present(
|
||||
leagueId,
|
||||
totalRaces: races.length,
|
||||
completedRaces: completedRaces.length,
|
||||
scheduledRaces: scheduledRaces.length,
|
||||
averageSOF,
|
||||
highestSOF,
|
||||
lowestSOF,
|
||||
};
|
||||
races.length,
|
||||
completedRaces.length,
|
||||
scheduledRaces.length,
|
||||
sofValues
|
||||
);
|
||||
}
|
||||
}
|
||||
Reference in New Issue
Block a user