using AdsManagerService.Domain.AggregatesModel.CampaignAggregate;
using MediatR;

namespace AdsManagerService.API.Application.Commands;

/// <summary>
/// EN: Handler for CreateCampaignCommand.
/// VI: Handler cho CreateCampaignCommand.
/// </summary>
public class CreateCampaignCommandHandler : IRequestHandler<CreateCampaignCommand, Guid>
{
    private readonly ICampaignRepository _campaignRepository;

    public CreateCampaignCommandHandler(ICampaignRepository campaignRepository)
    {
        _campaignRepository = campaignRepository ?? throw new ArgumentNullException(nameof(campaignRepository));
    }

    public async Task<Guid> Handle(CreateCampaignCommand request, CancellationToken cancellationToken)
    {
        // Parse objective
        var objective = CampaignObjective.FromName(request.Objective);

        // Create budget
        var budget = request.BudgetType.ToLower() == "daily"
            ? CampaignBudget.Daily(request.BudgetAmount, request.Currency)
            : CampaignBudget.Lifetime(request.BudgetAmount, request.Currency);

        // Create campaign
        var campaign = new Campaign(
            advertiserId: request.AdvertiserId,
            name: request.Name,
            objective: objective,
            budget: budget,
            description: request.Description
        );

        // Set schedule if provided
        if (request.StartDate.HasValue)
        {
            campaign.SetSchedule(request.StartDate.Value, request.EndDate);
        }

        // Add to repository
        _campaignRepository.Add(campaign);

        // Save changes
        await _campaignRepository.UnitOfWork.SaveEntitiesAsync(cancellationToken);

        return campaign.Id;
    }
}
