website refactor

This commit is contained in:
2026-01-16 16:46:57 +01:00
parent 37b1aa626c
commit 2f53727702
445 changed files with 1160 additions and 1150 deletions
@@ -71,7 +71,7 @@ class MockRatingEventRepository {
return Array.from(this.events.values()).filter(e => e.userId === userId);
}
async findEventsPaginated(userId: string, options?: import('@core/identity/domain/repositories/IRatingEventRepository').PaginatedQueryOptions): Promise<import('@core/identity/domain/repositories/IRatingEventRepository').PaginatedResult<RatingEvent>> {
async findEventsPaginated(userId: string, options?: import('@core/identity/domain/repositories/RatingEventRepository').PaginatedQueryOptions): Promise<import('@core/identity/domain/repositories/RatingEventRepository').PaginatedResult<RatingEvent>> {
const allEvents = await this.findByUserId(userId);
// Apply filters
@@ -105,7 +105,7 @@ class MockRatingEventRepository {
const hasMore = offset + limit < total;
const nextOffset = hasMore ? offset + limit : undefined;
const result: import('@core/identity/domain/repositories/IRatingEventRepository').PaginatedResult<RatingEvent> = {
const result: import('@core/identity/domain/repositories/RatingEventRepository').PaginatedResult<RatingEvent> = {
items,
total,
limit,
@@ -8,8 +8,8 @@ import { UserRating } from '../../domain/value-objects/UserRating';
import { RatingEventId } from '../../domain/value-objects/RatingEventId';
describe('AppendRatingEventsUseCase', () => {
let mockEventRepo: Partial<IRatingEventRepository>;
let mockRatingRepo: Partial<IUserRatingRepository>;
let mockEventRepo: Partial<RatingEventRepository>;
let mockRatingRepo: Partial<UserRatingRepository>;
beforeEach(() => {
mockEventRepo = {
@@ -24,16 +24,16 @@ describe('AppendRatingEventsUseCase', () => {
it('should be constructed with repositories', () => {
const useCase = new AppendRatingEventsUseCase(
mockEventRepo as IRatingEventRepository,
mockRatingRepo as IUserRatingRepository,
mockEventRepo as RatingEventRepository,
mockRatingRepo as UserRatingRepository,
);
expect(useCase).toBeInstanceOf(AppendRatingEventsUseCase);
});
it('should handle empty input (no events)', async () => {
const useCase = new AppendRatingEventsUseCase(
mockEventRepo as IRatingEventRepository,
mockRatingRepo as IUserRatingRepository,
mockEventRepo as RatingEventRepository,
mockRatingRepo as UserRatingRepository,
);
const input: AppendRatingEventsInput = {
@@ -50,8 +50,8 @@ describe('AppendRatingEventsUseCase', () => {
it('should create and save events from direct input', async () => {
const useCase = new AppendRatingEventsUseCase(
mockEventRepo as IRatingEventRepository,
mockRatingRepo as IUserRatingRepository,
mockEventRepo as RatingEventRepository,
mockRatingRepo as UserRatingRepository,
);
const input: AppendRatingEventsInput = {
@@ -79,8 +79,8 @@ describe('AppendRatingEventsUseCase', () => {
it('should create events from race results using factory', async () => {
const useCase = new AppendRatingEventsUseCase(
mockEventRepo as IRatingEventRepository,
mockRatingRepo as IUserRatingRepository,
mockEventRepo as RatingEventRepository,
mockRatingRepo as UserRatingRepository,
);
const input: AppendRatingEventsInput = {
@@ -108,8 +108,8 @@ describe('AppendRatingEventsUseCase', () => {
it('should handle multiple race results', async () => {
const useCase = new AppendRatingEventsUseCase(
mockEventRepo as IRatingEventRepository,
mockRatingRepo as IUserRatingRepository,
mockEventRepo as RatingEventRepository,
mockRatingRepo as UserRatingRepository,
);
const input: AppendRatingEventsInput = {
@@ -129,8 +129,8 @@ describe('AppendRatingEventsUseCase', () => {
it('should handle DNF status', async () => {
const useCase = new AppendRatingEventsUseCase(
mockEventRepo as IRatingEventRepository,
mockRatingRepo as IUserRatingRepository,
mockEventRepo as RatingEventRepository,
mockRatingRepo as UserRatingRepository,
);
const input: AppendRatingEventsInput = {
@@ -159,8 +159,8 @@ describe('AppendRatingEventsUseCase', () => {
};
const useCase = new AppendRatingEventsUseCase(
mockEventRepo as IRatingEventRepository,
mockRatingRepo as IUserRatingRepository,
mockEventRepo as RatingEventRepository,
mockRatingRepo as UserRatingRepository,
);
const input: AppendRatingEventsInput = {
@@ -42,8 +42,8 @@ export interface AppendRatingEventsOutput {
*/
export class AppendRatingEventsUseCase {
constructor(
private readonly ratingEventRepository: IRatingEventRepository,
private readonly userRatingRepository: IUserRatingRepository,
private readonly ratingEventRepository: RatingEventRepository,
private readonly userRatingRepository: UserRatingRepository,
) {}
async execute(input: AppendRatingEventsInput): Promise<AppendRatingEventsOutput> {
@@ -11,7 +11,7 @@ import { CastAdminVoteInput, CastAdminVoteOutput } from '../dtos/AdminVoteSessio
*/
export class CastAdminVoteUseCase {
constructor(
private readonly adminVoteSessionRepository: IAdminVoteSessionRepository,
private readonly adminVoteSessionRepository: AdminVoteSessionRepository,
) {}
async execute(input: CastAdminVoteInput): Promise<CastAdminVoteOutput> {
@@ -23,9 +23,9 @@ import { CloseAdminVoteSessionInput, CloseAdminVoteSessionOutput } from '../dtos
*/
export class CloseAdminVoteSessionUseCase {
constructor(
private readonly adminVoteSessionRepository: IAdminVoteSessionRepository,
private readonly ratingEventRepository: IRatingEventRepository,
private readonly userRatingRepository: IUserRatingRepository,
private readonly adminVoteSessionRepository: AdminVoteSessionRepository,
private readonly ratingEventRepository: RatingEventRepository,
private readonly userRatingRepository: UserRatingRepository,
private readonly appendRatingEventsUseCase: any, // Will be typed properly in integration
) {}
@@ -42,9 +42,9 @@ describe('ForgotPasswordUseCase', () => {
} as unknown as Logger;
useCase = new ForgotPasswordUseCase(
authRepo as unknown as IAuthRepository,
magicLinkRepo as unknown as IMagicLinkRepository,
notificationPort as unknown as IMagicLinkNotificationPort,
authRepo as unknown as AuthRepository,
magicLinkRepo as unknown as MagicLinkRepository,
notificationPort as unknown as MagicLinkNotificationPort,
logger,
);
});
@@ -4,7 +4,8 @@ import { MagicLinkRepository } from '../../domain/repositories/MagicLinkReposito
import { MagicLinkNotificationPort } from '../../domain/ports/MagicLinkNotificationPort';
import { Result } from '@core/shared/domain/Result';
import type { ApplicationErrorCode } from '@core/shared/errors/ApplicationErrorCode';
import type { Logger, UseCase } from '@core/shared/application';
import type { Logger } from '@core/shared/domain/Logger';
import type { UseCase } from '@core/shared/application/UseCase';
import { randomBytes } from 'crypto';
export type ForgotPasswordInput = {
@@ -29,9 +30,9 @@ export type ForgotPasswordApplicationError = ApplicationErrorCode<ForgotPassword
*/
export class ForgotPasswordUseCase implements UseCase<ForgotPasswordInput, ForgotPasswordResult, ForgotPasswordErrorCode> {
constructor(
private readonly authRepo: IAuthRepository,
private readonly magicLinkRepo: IMagicLinkRepository,
private readonly notificationPort: IMagicLinkNotificationPort,
private readonly authRepo: AuthRepository,
private readonly magicLinkRepo: MagicLinkRepository,
private readonly notificationPort: MagicLinkNotificationPort,
private readonly logger: Logger,
) {}
@@ -30,7 +30,7 @@ describe('GetCurrentSessionUseCase', () => {
error: vi.fn(),
} as unknown as Logger;
useCase = new GetCurrentSessionUseCase(
mockUserRepo as IUserRepository,
mockUserRepo as UserRepository,
logger,
);
});
@@ -25,7 +25,7 @@ export type GetCurrentSessionApplicationError = ApplicationErrorCode<
*/
export class GetCurrentSessionUseCase {
constructor(
private readonly userRepo: IUserRepository,
private readonly userRepo: UserRepository,
private readonly logger: Logger,
) {}
@@ -22,7 +22,7 @@ describe('GetUserUseCase', () => {
} as unknown as Logger;
useCase = new GetUserUseCase(
userRepo as unknown as IUserRepository,
userRepo as unknown as UserRepository,
logger,
);
});
@@ -2,7 +2,8 @@ import { User } from '../../domain/entities/User';
import { UserRepository } from '../../domain/repositories/UserRepository';
import { Result } from '@core/shared/domain/Result';
import type { ApplicationErrorCode } from '@core/shared/errors/ApplicationErrorCode';
import type { Logger, UseCase } from '@core/shared/application';
import type { Logger } from '@core/shared/domain/Logger';
import type { UseCase } from '@core/shared/application/UseCase';
export type GetUserInput = {
userId: string;
@@ -21,7 +22,7 @@ export type GetUserApplicationError = ApplicationErrorCode<
export class GetUserUseCase implements UseCase<GetUserInput, GetUserResult, GetUserErrorCode> {
constructor(
private readonly userRepo: IUserRepository,
private readonly userRepo: UserRepository,
private readonly logger: Logger,
) {}
@@ -32,8 +32,8 @@ describe('LoginUseCase', () => {
} as unknown as Logger;
useCase = new LoginUseCase(
authRepo as unknown as IAuthRepository,
passwordService as unknown as IPasswordHashingService,
authRepo as unknown as AuthRepository,
passwordService as unknown as PasswordHashingService,
logger,
);
});
@@ -4,7 +4,8 @@ import { AuthRepository } from '../../domain/repositories/AuthRepository';
import { PasswordHashingService } from '../../domain/services/PasswordHashingService';
import { Result } from '@core/shared/domain/Result';
import type { ApplicationErrorCode } from '@core/shared/errors/ApplicationErrorCode';
import type { Logger, UseCase } from '@core/shared/application';
import type { Logger } from '@core/shared/domain/Logger';
import type { UseCase } from '@core/shared/application/UseCase';
export type LoginInput = {
email: string;
@@ -26,8 +27,8 @@ export type LoginApplicationError = ApplicationErrorCode<LoginErrorCode, { messa
*/
export class LoginUseCase implements UseCase<LoginInput, LoginResult, LoginErrorCode> {
constructor(
private readonly authRepo: IAuthRepository,
private readonly passwordService: IPasswordHashingService,
private readonly authRepo: AuthRepository,
private readonly passwordService: PasswordHashingService,
private readonly logger: Logger,
) {}
@@ -40,7 +40,7 @@ describe('LoginWithEmailUseCase', () => {
} as unknown as Logger;
useCase = new LoginWithEmailUseCase(
userRepository as unknown as IUserRepository,
userRepository as unknown as UserRepository,
sessionPort as unknown as IdentitySessionPort,
logger,
);
@@ -37,7 +37,7 @@ export type LoginWithEmailApplicationError = ApplicationErrorCode<
export class LoginWithEmailUseCase {
constructor(
private readonly userRepository: IUserRepository,
private readonly userRepository: UserRepository,
private readonly sessionPort: IdentitySessionPort,
private readonly logger: Logger,
) {}
@@ -1,7 +1,8 @@
import type { IdentitySessionPort } from '../ports/IdentitySessionPort';
import { Result } from '@core/shared/domain/Result';
import type { ApplicationErrorCode } from '@core/shared/errors/ApplicationErrorCode';
import type { Logger, UseCase } from '@core/shared/application';
import type { Logger } from '@core/shared/domain/Logger';
import type { UseCase } from '@core/shared/application/UseCase';
export type LogoutInput = {};
@@ -12,7 +12,7 @@ import { OpenAdminVoteSessionInput, OpenAdminVoteSessionOutput } from '../dtos/A
*/
export class OpenAdminVoteSessionUseCase {
constructor(
private readonly adminVoteSessionRepository: IAdminVoteSessionRepository,
private readonly adminVoteSessionRepository: AdminVoteSessionRepository,
) {}
async execute(input: OpenAdminVoteSessionInput): Promise<OpenAdminVoteSessionOutput> {
@@ -10,8 +10,8 @@ import { RatingDimensionKey } from '../../domain/value-objects/RatingDimensionKe
import { RatingDelta } from '../../domain/value-objects/RatingDelta';
describe('RecomputeUserRatingSnapshotUseCase', () => {
let mockEventRepo: Partial<IRatingEventRepository>;
let mockRatingRepo: Partial<IUserRatingRepository>;
let mockEventRepo: Partial<RatingEventRepository>;
let mockRatingRepo: Partial<UserRatingRepository>;
beforeEach(() => {
mockEventRepo = {
@@ -25,16 +25,16 @@ describe('RecomputeUserRatingSnapshotUseCase', () => {
it('should be constructed with repositories', () => {
const useCase = new RecomputeUserRatingSnapshotUseCase(
mockEventRepo as IRatingEventRepository,
mockRatingRepo as IUserRatingRepository,
mockEventRepo as RatingEventRepository,
mockRatingRepo as UserRatingRepository,
);
expect(useCase).toBeInstanceOf(RecomputeUserRatingSnapshotUseCase);
});
it('should compute snapshot from empty event list', async () => {
const useCase = new RecomputeUserRatingSnapshotUseCase(
mockEventRepo as IRatingEventRepository,
mockRatingRepo as IUserRatingRepository,
mockEventRepo as RatingEventRepository,
mockRatingRepo as UserRatingRepository,
);
const result = await useCase.execute({ userId: 'user-1' });
@@ -64,8 +64,8 @@ describe('RecomputeUserRatingSnapshotUseCase', () => {
mockEventRepo.getAllByUserId = vi.fn().mockResolvedValue(events);
const useCase = new RecomputeUserRatingSnapshotUseCase(
mockEventRepo as IRatingEventRepository,
mockRatingRepo as IUserRatingRepository,
mockEventRepo as RatingEventRepository,
mockRatingRepo as UserRatingRepository,
);
const result = await useCase.execute({ userId: 'user-1' });
@@ -78,8 +78,8 @@ describe('RecomputeUserRatingSnapshotUseCase', () => {
it('should return proper DTO format', async () => {
const useCase = new RecomputeUserRatingSnapshotUseCase(
mockEventRepo as IRatingEventRepository,
mockRatingRepo as IUserRatingRepository,
mockEventRepo as RatingEventRepository,
mockRatingRepo as UserRatingRepository,
);
const result = await useCase.execute({ userId: 'user-1' });
@@ -117,8 +117,8 @@ describe('RecomputeUserRatingSnapshotUseCase', () => {
mockRatingRepo.save = vi.fn().mockResolvedValue(updated);
const useCase = new RecomputeUserRatingSnapshotUseCase(
mockEventRepo as IRatingEventRepository,
mockRatingRepo as IUserRatingRepository,
mockEventRepo as RatingEventRepository,
mockRatingRepo as UserRatingRepository,
);
const result = await useCase.execute({ userId: 'user-1' });
@@ -28,8 +28,8 @@ export interface RecomputeUserRatingSnapshotOutput {
*/
export class RecomputeUserRatingSnapshotUseCase {
constructor(
private readonly ratingEventRepository: IRatingEventRepository,
private readonly userRatingRepository: IUserRatingRepository,
private readonly ratingEventRepository: RatingEventRepository,
private readonly userRatingRepository: UserRatingRepository,
) {}
async execute(input: RecomputeUserRatingSnapshotInput): Promise<RecomputeUserRatingSnapshotOutput> {
@@ -24,9 +24,9 @@ import { RecordRaceRatingEventsInput, RecordRaceRatingEventsOutput } from '../dt
*/
export class RecordRaceRatingEventsUseCase {
constructor(
private readonly raceResultsProvider: IRaceResultsProvider,
private readonly ratingEventRepository: IRatingEventRepository,
private readonly userRatingRepository: IUserRatingRepository,
private readonly raceResultsProvider: RaceResultsProvider,
private readonly ratingEventRepository: RatingEventRepository,
private readonly userRatingRepository: UserRatingRepository,
private readonly appendRatingEventsUseCase: AppendRatingEventsUseCase,
) {}
@@ -43,9 +43,9 @@ describe('ResetPasswordUseCase', () => {
} as unknown as Logger;
useCase = new ResetPasswordUseCase(
authRepo as unknown as IAuthRepository,
magicLinkRepo as unknown as IMagicLinkRepository,
passwordService as unknown as IPasswordHashingService,
authRepo as unknown as AuthRepository,
magicLinkRepo as unknown as MagicLinkRepository,
passwordService as unknown as PasswordHashingService,
logger,
);
});
@@ -5,7 +5,8 @@ import { EmailAddress } from '../../domain/value-objects/EmailAddress';
import { PasswordHash } from '../../domain/value-objects/PasswordHash';
import { Result } from '@core/shared/domain/Result';
import type { ApplicationErrorCode } from '@core/shared/errors/ApplicationErrorCode';
import type { Logger, UseCase } from '@core/shared/application';
import type { Logger } from '@core/shared/domain/Logger';
import type { UseCase } from '@core/shared/application/UseCase';
export type ResetPasswordInput = {
token: string;
@@ -28,9 +29,9 @@ export type ResetPasswordApplicationError = ApplicationErrorCode<ResetPasswordEr
*/
export class ResetPasswordUseCase implements UseCase<ResetPasswordInput, ResetPasswordResult, ResetPasswordErrorCode> {
constructor(
private readonly authRepo: IAuthRepository,
private readonly magicLinkRepo: IMagicLinkRepository,
private readonly passwordService: IPasswordHashingService,
private readonly authRepo: AuthRepository,
private readonly magicLinkRepo: MagicLinkRepository,
private readonly passwordService: PasswordHashingService,
private readonly logger: Logger,
) {}
@@ -42,9 +42,9 @@ describe('SignupSponsorUseCase', () => {
} as unknown as Logger;
useCase = new SignupSponsorUseCase(
authRepo as unknown as IAuthRepository,
companyRepo as unknown as ICompanyRepository,
passwordService as unknown as IPasswordHashingService,
authRepo as unknown as AuthRepository,
companyRepo as unknown as CompanyRepository,
passwordService as unknown as PasswordHashingService,
logger,
);
});
@@ -7,7 +7,8 @@ import { CompanyRepository } from '../../domain/repositories/CompanyRepository';
import { PasswordHashingService } from '../../domain/services/PasswordHashingService';
import { Result } from '@core/shared/domain/Result';
import type { ApplicationErrorCode } from '@core/shared/errors/ApplicationErrorCode';
import type { Logger, UseCase } from '@core/shared/application';
import type { Logger } from '@core/shared/domain/Logger';
import type { UseCase } from '@core/shared/application/UseCase';
export type SignupSponsorInput = {
email: string;
@@ -33,9 +34,9 @@ export type SignupSponsorApplicationError = ApplicationErrorCode<SignupSponsorEr
*/
export class SignupSponsorUseCase implements UseCase<SignupSponsorInput, SignupSponsorResult, SignupSponsorErrorCode> {
constructor(
private readonly authRepo: IAuthRepository,
private readonly companyRepo: ICompanyRepository,
private readonly passwordService: IPasswordHashingService,
private readonly authRepo: AuthRepository,
private readonly companyRepo: CompanyRepository,
private readonly passwordService: PasswordHashingService,
private readonly logger: Logger,
) {}
@@ -34,8 +34,8 @@ describe('SignupUseCase', () => {
} as unknown as Logger;
useCase = new SignupUseCase(
authRepo as unknown as IAuthRepository,
passwordService as unknown as IPasswordHashingService,
authRepo as unknown as AuthRepository,
passwordService as unknown as PasswordHashingService,
logger,
);
});
@@ -6,7 +6,8 @@ import { PasswordHashingService } from '../../domain/services/PasswordHashingSer
import { PasswordHash } from '../../domain/value-objects/PasswordHash';
import { Result } from '@core/shared/domain/Result';
import type { ApplicationErrorCode } from '@core/shared/errors/ApplicationErrorCode';
import type { Logger, UseCase } from '@core/shared/application';
import type { Logger } from '@core/shared/domain/Logger';
import type { UseCase } from '@core/shared/application/UseCase';
export type SignupInput = {
email: string;
@@ -29,8 +30,8 @@ export type SignupApplicationError = ApplicationErrorCode<SignupErrorCode, { mes
*/
export class SignupUseCase implements UseCase<SignupInput, SignupResult, SignupErrorCode> {
constructor(
private readonly authRepo: IAuthRepository,
private readonly passwordService: IPasswordHashingService,
private readonly authRepo: AuthRepository,
private readonly passwordService: PasswordHashingService,
private readonly logger: Logger,
) {}
@@ -32,7 +32,7 @@ describe('SignupWithEmailUseCase', () => {
} as unknown as Logger;
useCase = new SignupWithEmailUseCase(
userRepository as unknown as IUserRepository,
userRepository as unknown as UserRepository,
sessionPort as unknown as IdentitySessionPort,
logger,
);
@@ -33,7 +33,7 @@ export type SignupWithEmailApplicationError = ApplicationErrorCode<
export class SignupWithEmailUseCase {
constructor(
private readonly userRepository: IUserRepository,
private readonly userRepository: UserRepository,
private readonly sessionPort: IdentitySessionPort,
private readonly logger: Logger,
) {}
@@ -10,7 +10,7 @@ import { vi, describe, it, expect, beforeEach } from 'vitest';
describe('UpsertExternalGameRatingUseCase', () => {
let useCase: UpsertExternalGameRatingUseCase;
let mockRepository: IExternalGameRatingRepository;
let mockRepository: ExternalGameRatingRepository;
beforeEach(() => {
mockRepository = {
@@ -23,7 +23,7 @@ import { UpsertExternalGameRatingInput, UpsertExternalGameRatingOutput } from '.
*/
export class UpsertExternalGameRatingUseCase {
constructor(
private readonly externalGameRatingRepository: IExternalGameRatingRepository
private readonly externalGameRatingRepository: ExternalGameRatingRepository
) {}
async execute(input: UpsertExternalGameRatingInput): Promise<UpsertExternalGameRatingOutput> {
@@ -1,6 +1,6 @@
import type { Logger } from '@core/shared/domain/Logger';
import { describe, expect, it, vi, type Mock } from 'vitest';
import { CreateAchievementUseCase, type IAchievementRepository } from './CreateAchievementUseCase';
import { CreateAchievementUseCase, type AchievementRepository } from './CreateAchievementUseCase';
describe('CreateAchievementUseCase', () => {
let achievementRepository: {
@@ -24,7 +24,7 @@ describe('CreateAchievementUseCase', () => {
} as unknown as Logger;
useCase = new CreateAchievementUseCase(
achievementRepository as unknown as IAchievementRepository,
achievementRepository as unknown as AchievementRepository,
logger,
);
});
@@ -23,7 +23,7 @@ export type CreateAchievementApplicationError = ApplicationErrorCode<
export class CreateAchievementUseCase {
constructor(
private readonly achievementRepository: IAchievementRepository,
private readonly achievementRepository: AchievementRepository,
private readonly logger: Logger,
) {}