using TakeoutSaaS.Application.App.Coupons.FlashSale.Dto;
using TakeoutSaaS.Domain.Coupons.Entities;
using TakeoutSaaS.Domain.Coupons.Enums;

namespace TakeoutSaaS.Application.App.Coupons.FlashSale;

/// <summary>
/// 限时折扣 DTO 映射工厂。
/// </summary>
internal static class FlashSaleDtoFactory
{
    /// <summary>
    /// 构建列表项 DTO。
    /// </summary>
    public static FlashSaleListItemDto ToListItemDto(
        PromotionCampaign campaign,
        FlashSaleRulesDto rules,
        DateTime nowUtc)
    {
        var displayStatus = FlashSaleMapping.ResolveDisplayStatus(campaign, rules, nowUtc);
        return new FlashSaleListItemDto
        {
            Id = campaign.Id,
            Name = campaign.Name,
            Status = FlashSaleMapping.ToStatusText(campaign.Status),
            DisplayStatus = displayStatus,
            IsDimmed = FlashSaleMapping.IsDimmed(displayStatus),
            UpdatedAt = campaign.UpdatedAt ?? campaign.CreatedAt,
            Rules = rules
        };
    }

    /// <summary>
    /// 构建详情 DTO。
    /// </summary>
    public static FlashSaleDetailDto ToDetailDto(
        PromotionCampaign campaign,
        FlashSaleRulesDto rules,
        DateTime nowUtc)
    {
        return new FlashSaleDetailDto
        {
            Id = campaign.Id,
            Name = campaign.Name,
            Status = FlashSaleMapping.ToStatusText(campaign.Status),
            DisplayStatus = FlashSaleMapping.ResolveDisplayStatus(campaign, rules, nowUtc),
            UpdatedAt = campaign.UpdatedAt ?? campaign.CreatedAt,
            Rules = rules
        };
    }

    /// <summary>
    /// 构建统计 DTO。
    /// </summary>
    public static FlashSaleStatsDto ToStatsDto(IReadOnlyCollection<FlashSaleListItemDto> items)
    {
        if (items.Count == 0)
        {
            return new FlashSaleStatsDto();
        }

        var participatingProductCount = items
            .SelectMany(item => item.Rules.Products)
            .Select(item => item.ProductId)
            .Distinct()
            .Count();

        var monthlyDiscountSalesCount = items.Sum(item => item.Rules.Metrics.MonthlyDiscountSalesCount);

        return new FlashSaleStatsDto
        {
            TotalCount = items.Count,
            OngoingCount = items.Count(item => string.Equals(item.DisplayStatus, "ongoing", StringComparison.Ordinal)),
            ParticipatingProductCount = participatingProductCount,
            MonthlyDiscountSalesCount = monthlyDiscountSalesCount
        };
    }

    /// <summary>
    /// 构建默认新增活动实体。
    /// </summary>
    public static PromotionCampaign CreateNewCampaign(
        string name,
        DateTime startAt,
        DateTime endAt,
        string rulesJson)
    {
        return new PromotionCampaign
        {
            Name = name,
            PromotionType = PromotionType.FlashSale,
            Status = PromotionStatus.Active,
            StartAt = startAt,
            EndAt = endAt,
            RulesJson = rulesJson,
            AudienceDescription = null,
            Budget = null,
            BannerUrl = null
        };
    }
}

