Files
gridpilot.gg/apps/website/lib/services/leagues/LeagueWalletService.ts
2025-12-19 21:58:03 +01:00

71 lines
2.3 KiB
TypeScript

import { WalletsApiClient, LeagueWalletDTO, WithdrawRequestDTO, WithdrawResponseDTO } from '@/lib/api/wallets/WalletsApiClient';
import { LeagueWalletViewModel } from '@/lib/view-models/LeagueWalletViewModel';
import { WalletTransactionViewModel } from '@/lib/view-models/WalletTransactionViewModel';
import { SubmitBlocker, ThrottleBlocker } from '@/lib/blockers';
/**
* League Wallet Service
*
* Orchestrates league wallet operations by coordinating API calls and view model creation.
* All dependencies are injected via constructor.
*/
export class LeagueWalletService {
private readonly submitBlocker = new SubmitBlocker();
private readonly throttle = new ThrottleBlocker(500);
constructor(
private readonly apiClient: WalletsApiClient
) {}
/**
* Get wallet for a league
*/
async getWalletForLeague(leagueId: string): Promise<LeagueWalletViewModel> {
const dto = await this.apiClient.getLeagueWallet(leagueId);
const transactions = dto.transactions.map(t => new WalletTransactionViewModel({
id: t.id,
type: t.type,
description: t.description,
amount: t.amount,
fee: t.fee,
netAmount: t.netAmount,
date: new Date(t.date),
status: t.status,
reference: t.reference,
}));
return new LeagueWalletViewModel({
balance: dto.balance,
currency: dto.currency,
totalRevenue: dto.totalRevenue,
totalFees: dto.totalFees,
totalWithdrawals: dto.totalWithdrawals,
pendingPayouts: dto.pendingPayouts,
transactions,
canWithdraw: dto.canWithdraw,
withdrawalBlockReason: dto.withdrawalBlockReason,
});
}
/**
* Withdraw from league wallet
*/
async withdraw(leagueId: string, amount: number, currency: string, seasonId: string, destinationAccount: string): Promise<WithdrawResponseDTO> {
if (!this.submitBlocker.canExecute() || !this.throttle.canExecute()) {
throw new Error('Request blocked due to rate limiting');
}
this.submitBlocker.block();
this.throttle.block();
try {
const request: WithdrawRequestDTO = {
amount,
currency,
seasonId,
destinationAccount,
};
return await this.apiClient.withdrawFromLeagueWallet(leagueId, request);
} finally {
this.submitBlocker.release();
}
}
}