integration tests
Some checks failed
CI / lint-typecheck (pull_request) Failing after 4m51s
CI / tests (pull_request) Has been skipped
CI / contract-tests (pull_request) Has been skipped
CI / e2e-tests (pull_request) Has been skipped
CI / comment-pr (pull_request) Has been skipped
CI / commit-types (pull_request) Has been skipped
Some checks failed
CI / lint-typecheck (pull_request) Failing after 4m51s
CI / tests (pull_request) Has been skipped
CI / contract-tests (pull_request) Has been skipped
CI / e2e-tests (pull_request) Has been skipped
CI / comment-pr (pull_request) Has been skipped
CI / commit-types (pull_request) Has been skipped
This commit is contained in:
@@ -0,0 +1,88 @@
|
||||
/**
|
||||
* GetRatingLeaderboardUseCase
|
||||
*
|
||||
* Retrieves rating leaderboard for drivers.
|
||||
*/
|
||||
|
||||
import { RatingRepository } from '../../ports/RatingRepository';
|
||||
import { DriverRepository } from '../../../racing/domain/repositories/DriverRepository';
|
||||
import { Rating } from '../../domain/Rating';
|
||||
|
||||
export interface GetRatingLeaderboardUseCasePorts {
|
||||
ratingRepository: RatingRepository;
|
||||
driverRepository: DriverRepository;
|
||||
}
|
||||
|
||||
export interface GetRatingLeaderboardRequest {
|
||||
limit?: number;
|
||||
offset?: number;
|
||||
}
|
||||
|
||||
export interface RatingLeaderboardEntry {
|
||||
driverId: string;
|
||||
driverName: string;
|
||||
rating: number;
|
||||
components: {
|
||||
resultsStrength: number;
|
||||
consistency: number;
|
||||
cleanDriving: number;
|
||||
racecraft: number;
|
||||
reliability: number;
|
||||
teamContribution: number;
|
||||
};
|
||||
}
|
||||
|
||||
export class GetRatingLeaderboardUseCase {
|
||||
constructor(private readonly ports: GetRatingLeaderboardUseCasePorts) {}
|
||||
|
||||
async execute(request: GetRatingLeaderboardRequest): Promise<RatingLeaderboardEntry[]> {
|
||||
const { ratingRepository, driverRepository } = this.ports;
|
||||
const { limit = 50, offset = 0 } = request;
|
||||
|
||||
try {
|
||||
// Get all ratings
|
||||
const allRatings: Rating[] = [];
|
||||
const driverIds = new Set<string>();
|
||||
|
||||
// Group ratings by driver and get latest rating for each driver
|
||||
const driverRatings = new Map<string, Rating>();
|
||||
|
||||
// In a real implementation, this would be optimized with a database query
|
||||
// For now, we'll simulate getting the latest rating for each driver
|
||||
const drivers = await driverRepository.findAll();
|
||||
|
||||
for (const driver of drivers) {
|
||||
const driverRatingsList = await ratingRepository.findByDriver(driver.id);
|
||||
if (driverRatingsList.length > 0) {
|
||||
// Get the latest rating (most recent timestamp)
|
||||
const latestRating = driverRatingsList.reduce((latest, current) =>
|
||||
current.timestamp > latest.timestamp ? current : latest
|
||||
);
|
||||
driverRatings.set(driver.id, latestRating);
|
||||
}
|
||||
}
|
||||
|
||||
// Convert to leaderboard entries
|
||||
const entries: RatingLeaderboardEntry[] = [];
|
||||
for (const [driverId, rating] of driverRatings.entries()) {
|
||||
const driver = await driverRepository.findById(driverId);
|
||||
if (driver) {
|
||||
entries.push({
|
||||
driverId,
|
||||
driverName: driver.name.toString(),
|
||||
rating: rating.rating,
|
||||
components: rating.components,
|
||||
});
|
||||
}
|
||||
}
|
||||
|
||||
// Sort by rating (descending)
|
||||
entries.sort((a, b) => b.rating - a.rating);
|
||||
|
||||
// Apply pagination
|
||||
return entries.slice(offset, offset + limit);
|
||||
} catch (error) {
|
||||
throw new Error(`Failed to get rating leaderboard: ${error}`);
|
||||
}
|
||||
}
|
||||
}
|
||||
Reference in New Issue
Block a user