/** * Application Use Case: GetEntitySponsorshipPricingUseCase * * Retrieves sponsorship pricing configuration for any entity. * Used by sponsors to see available slots and prices. */ import type { ISponsorshipPricingRepository } from '../../domain/repositories/ISponsorshipPricingRepository'; import type { ISponsorshipRequestRepository } from '../../domain/repositories/ISponsorshipRequestRepository'; import type { ISeasonSponsorshipRepository } from '../../domain/repositories/ISeasonSponsorshipRepository'; import type { SponsorshipPricing, SponsorshipSlotConfig } from '../../domain/value-objects/SponsorshipPricing'; import type { Logger } from '@core/shared/application'; import type { UseCaseOutputPort } from '@core/shared/application/UseCaseOutputPort'; import { Result } from '@core/shared/application/Result'; import type { ApplicationErrorCode } from '@core/shared/errors/ApplicationErrorCode'; import type { SponsorableEntityType } from '../../domain/entities/SponsorshipRequest'; export type SponsorshipEntityType = SponsorableEntityType; export type GetEntitySponsorshipPricingInput = { entityType: SponsorshipEntityType; entityId: string; }; export type SponsorshipPricingTier = { name: string; price: { amount: number; currency: string; }; benefits: string[]; }; export type GetEntitySponsorshipPricingResult = { entityType: SponsorshipEntityType; entityId: string; acceptingApplications: boolean; customRequirements?: string; tiers: SponsorshipPricingTier[]; }; export type GetEntitySponsorshipPricingErrorCode = | 'ENTITY_NOT_FOUND' | 'PRICING_NOT_CONFIGURED' | 'REPOSITORY_ERROR'; export class GetEntitySponsorshipPricingUseCase { constructor( private readonly sponsorshipPricingRepo: ISponsorshipPricingRepository, private readonly sponsorshipRequestRepo: ISponsorshipRequestRepository, private readonly seasonSponsorshipRepo: ISeasonSponsorshipRepository, private readonly logger: Logger, private readonly output: UseCaseOutputPort, ) {} async execute( input: GetEntitySponsorshipPricingInput, ): Promise< Result> > { this.logger.debug( `Executing GetEntitySponsorshipPricingUseCase for entityType: ${input.entityType}, entityId: ${input.entityId}`, ); try { const pricing = await this.sponsorshipPricingRepo.findByEntity( input.entityType, input.entityId, ); if (!pricing) { this.logger.info( `No pricing configured for entityType: ${input.entityType}, entityId: ${input.entityId}`, ); return Result.err({ code: 'PRICING_NOT_CONFIGURED', details: { message: `No sponsorship pricing configured for entityType: ${input.entityType}, entityId: ${input.entityId}`, }, }); } const tiers: SponsorshipPricingTier[] = []; if (pricing.mainSlot) { tiers.push({ name: 'main', price: pricing.mainSlot.price, benefits: pricing.mainSlot.benefits, }); } if (pricing.secondarySlots) { tiers.push({ name: 'secondary', price: pricing.secondarySlots.price, benefits: pricing.secondarySlots.benefits, }); } const result: GetEntitySponsorshipPricingResult = { entityType: input.entityType, entityId: input.entityId, acceptingApplications: pricing.acceptingApplications, ...(pricing.customRequirements !== undefined ? { customRequirements: pricing.customRequirements } : {}), tiers, }; this.logger.info( `Successfully retrieved sponsorship pricing for entityType: ${input.entityType}, entityId: ${input.entityId}`, ); this.output.present(result); return Result.ok(undefined); } catch (error) { this.logger.error( 'Error executing GetEntitySponsorshipPricingUseCase', error instanceof Error ? error : new Error(String(error)), ); return Result.err({ code: 'REPOSITORY_ERROR', details: { message: error instanceof Error ? error.message : 'Failed to load sponsorship pricing', }, }); } } }