using CMSMicroservice.Application.Common.Interfaces;
using CMSMicroservice.Domain.Entities.Club;
using CMSMicroservice.Domain.Enums;
using Microsoft.EntityFrameworkCore;
using Microsoft.Extensions.Configuration;
using Microsoft.Extensions.Logging;
using Polly;

namespace CMSMicroservice.Infrastructure.BackgroundJobs;

/// <summary>
/// Hangfire Job برای فعال‌سازی حساب چتیکا برای اعضای جدید باشگاه
/// این Job کاربرانی که باشگاهشان فعال شده ولی حساب چتیکا ندارند را پیدا کرده و حساب می‌سازد
/// </summary>
public class ChatikaAccountActivationJob
{
    private readonly IApplicationDbContext _context;
    private readonly IChatikaApiService _chatikaApiService;
    private readonly IConfiguration _configuration;
    private readonly ILogger<ChatikaAccountActivationJob> _logger;
    private readonly ResiliencePipeline _retryPipeline;

    /// <summary>
    /// توضیحات فارسی فیچر چتیکا
    /// </summary>
    private const string ChatikaFeatureDescription = 
        "🎉 تبریک! حساب هوش مصنوعی چتیکا شما فعال شد.\n\n" +
        "برای استفاده از امکانات رایگان چتیکا:\n" +
        "1️⃣ به وب‌سایت chatika.ir مراجعه کنید\n" +
        "2️⃣ شماره موبایل خود را وارد کنید\n" +
        "3️⃣ از دستیار هوشمند چتیکا لذت ببرید!\n\n" +
        "🔗 لینک ورود: https://chatika.ir";

    public ChatikaAccountActivationJob(
        IApplicationDbContext context,
        IChatikaApiService chatikaApiService,
        IConfiguration configuration,
        ILogger<ChatikaAccountActivationJob> logger)
    {
        _context = context;
        _chatikaApiService = chatikaApiService;
        _configuration = configuration;
        _logger = logger;

        // Polly Retry: 3 تلاش با فاصله نمایی
        _retryPipeline = new ResiliencePipelineBuilder()
            .AddRetry(new Polly.Retry.RetryStrategyOptions
            {
                MaxRetryAttempts = 3,
                Delay = TimeSpan.FromSeconds(30),
                BackoffType = Polly.DelayBackoffType.Exponential,
                UseJitter = true,
                OnRetry = args =>
                {
                    _logger.LogWarning(
                        "⚠️ Retry attempt {AttemptNumber} for Chatika API. Exception: {ExceptionType}",
                        args.AttemptNumber,
                        args.Outcome.Exception?.GetType().Name ?? "None");
                    return ValueTask.CompletedTask;
                }
            })
            .Build();
    }

    /// <summary>
    /// اجرای Job برای فعال‌سازی حساب چتیکا
    /// </summary>
    public async Task ExecuteAsync(CancellationToken cancellationToken = default)
    {
        // Check if Chatika integration is enabled
        var enabled = _configuration.GetValue<bool>("Chatika:Enabled");
        if (!enabled)
        {
            _logger.LogDebug("Chatika integration is disabled (Chatika:Enabled = false). Skipping job.");
            return;
        }

        var executionId = Guid.NewGuid();
        _logger.LogInformation(
            "🚀 [{ExecutionId}] Starting Chatika account activation job", 
            executionId);

        try
        {
            // پیدا کردن کاربرانی که:
            // 1. باشگاه فعال دارند (ClubMembership.IsActive = true)
            // 2. فیچر چتیکا (Id=1) رو دارند
            // 3. فیچر چتیکاشون هنوز Notes نداره (یعنی حساب ساخته نشده)
            var pendingUsers = await _context.UserClubFeatures
                .Include(ucf => ucf.User)
                .Include(ucf => ucf.ClubMembership)
                .Where(ucf => 
                    ucf.ClubFeatureId == (long)ClubFeatureType.Chatika &&
                    ucf.ClubMembership.IsActive &&
                    !ucf.IsDeleted &&
                    !ucf.IsActive) // حساب هنوز ساخته نشده
                .ToListAsync(cancellationToken);

            if (!pendingUsers.Any())
            {
                _logger.LogInformation(
                    "✅ [{ExecutionId}] No pending users for Chatika activation", 
                    executionId);
                return;
            }

            _logger.LogInformation(
                "📋 [{ExecutionId}] Found {Count} users pending Chatika activation",
                executionId, 
                pendingUsers.Count);

            var successCount = 0;
            var failCount = 0;

            foreach (var userFeature in pendingUsers)
            {
                try
                {
                    // بررسی تکراری نبودن (Double-check)
                    if (userFeature.IsActive)
                    {
                        _logger.LogDebug(
                            "⏭️ Skipping user {UserId} - already processed", 
                            userFeature.UserId);
                        continue;
                    }

                    var user = userFeature.User;
                    var fullName = $"{user.FirstName} {user.LastName}".Trim();
                    if (string.IsNullOrWhiteSpace(fullName)) fullName = user.Mobile;
                    
                    // کال کردن API چتیکا با retry
                    var result = await _retryPipeline.ExecuteAsync(
                        async ct => await _chatikaApiService.CreateAccountAsync(
                            user.Mobile,
                            fullName,
                            ct),
                        cancellationToken);

                    if (result.IsSuccess)
                    {
                        // آپدیت فیچر با توضیحات و URL
                        var description = ChatikaFeatureDescription;
                        if (!string.IsNullOrEmpty(result.AccessUrl))
                        {
                            description = description.Replace(
                                "https://chatika.ir", 
                                result.AccessUrl);
                        }

                        userFeature.Notes = description;
                        userFeature.IsActive = true;
                        userFeature.LastModified = DateTime.Now;

                        await _context.SaveChangesAsync(cancellationToken);

                        _logger.LogInformation(
                            "✅ Chatika account activated for user {UserId}", 
                            userFeature.UserId);
                        successCount++;
                    }
                    else
                    {
                        _logger.LogWarning(
                            "⚠️ Failed to create Chatika account for user {UserId}: {Error}",
                            userFeature.UserId, 
                            result.ErrorMessage);
                        failCount++;
                    }
                }
                catch (Exception ex)
                {
                    _logger.LogError(ex,
                        "❌ Error processing Chatika activation for user {UserId}",
                        userFeature.UserId);
                    failCount++;
                }
            }

            _logger.LogInformation(
                "🏁 [{ExecutionId}] Chatika activation job completed. Success: {Success}, Failed: {Failed}",
                executionId, 
                successCount, 
                failCount);
        }
        catch (Exception ex)
        {
            _logger.LogError(ex,
                "❌ [{ExecutionId}] Chatika activation job failed",
                executionId);
            throw;
        }
    }
}
