using FrontOffice.Main.Utilities;
using FrontOffice.Main.Shared;
using Microsoft.AspNetCore.Components;
using MudBlazor;

namespace FrontOffice.Main.Pages.Commission;

public partial class WeeklyBalancePage : ComponentBase
{
    [Inject] private CommissionService CommissionService { get; set; } = default!;
    [Inject] private PackageService PackageService { get; set; } = default!;
    [Inject] private ISnackbar SnackbarService { get; set; } = default!;

    [Parameter]
    [SupplyParameterFromQuery(Name = "week")]
    public string? QueryWeekNumber { get; set; }

    private WeekSelector? _weekSelector;
    private WeekDefinitionDto? _selectedWeekDefinition;
    private WeeklyBalanceDto? _weeklyBalance;
    private List<PackageDto> _packages = new();
    private long? _filterPackageId;
    private bool _isLoading = true;
    private bool _hasError = false;

    private readonly ChartOptions _chartOptions = new()
    {
        ChartPalette = new[]
        {
            "#2196F3", // Info (Left)
            "#4CAF50", // Success (Right)
            "#FF9800"  // Warning (Min)
        }
    };

    protected override async Task OnAfterRenderAsync(bool firstRender)
    {
        if (firstRender)
        {
            await LoadPackagesAsync();

            // Wait for WeekSelector to initialize and load its cached weeks
            if (_weekSelector != null)
            {
                await _weekSelector.EnsureLoadedAsync();
                
                // Handle query parameter ?week=7 (WeekDefinitionId)
                if (!string.IsNullOrEmpty(QueryWeekNumber))
                {
                    // Try to parse as WeekDefinitionId first (most common from dashboard links)
                    if (long.TryParse(QueryWeekNumber, out long id))
                    {
                        _selectedWeekDefinition = _weekSelector.FindById(id);
                        
                        // Fallback: try as WeekOrder if not found by Id
                        if (_selectedWeekDefinition == null && int.TryParse(QueryWeekNumber, out int weekOrder))
                        {
                            _selectedWeekDefinition = _weekSelector.FindByWeekOrder(weekOrder);
                        }
                        
                        // If still not found in cache, create a temporary definition with just the Id
                        // so we can still query the balance from BFF
                        if (_selectedWeekDefinition == null)
                        {
                            _selectedWeekDefinition = new WeekDefinitionDto { Id = id, DisplayName = $"هفته {id}" };
                        }
                    }
                }
                
                // If no week selected and no query param, select current week
                if (_selectedWeekDefinition == null)
                {
                    _selectedWeekDefinition = _weekSelector.GetCurrentWeek();
                }
                
                await LoadWeeklyBalanceAsync();
                StateHasChanged();
            }
        }
    }

    protected override void OnInitialized()
    {
        _isLoading = true;
    }

    private async Task LoadWeeklyBalanceAsync()
    {
        try
        {
            _isLoading = true;
            _hasError = false;
            
            long? weekDefinitionId = _selectedWeekDefinition?.Id;
            
            _weeklyBalance = await CommissionService.GetMyWeeklyBalanceAsync(weekDefinitionId, _filterPackageId);
            
            // Update week display name from selected definition if available
            if (_selectedWeekDefinition != null && _weeklyBalance != null)
            {
                _weeklyBalance.WeekDisplayName = _selectedWeekDefinition.DisplayName;
                return;
            }

            _weeklyBalance = new WeeklyBalanceDto()
            {

            };
        }
        catch (Exception ex)
        {
            _hasError = true;
            SnackbarService.Add($"خطا در دریافت تعادل: {ex.Message}", Severity.Error);
        }
        finally
        {
            _isLoading = false;
        }
    }

    private async Task LoadPackagesAsync()
    {
        try
        {
            _packages = await PackageService.GetAllPackagesAsync();
        }
        catch
        {
            _packages = new();
        }
    }

    private async Task LoadCurrentWeekAsync()
    {
        if (_weekSelector != null)
        {
            await _weekSelector.SelectCurrentWeekAsync();
        }
        _selectedWeekDefinition = _weekSelector?.GetCurrentWeek();
        await LoadWeeklyBalanceAsync();
    }

    private double GetLeftPercentage()
    {
        if (_weeklyBalance is null)
            return 0;
        var total = _weeklyBalance.LeftBalance + _weeklyBalance.RightBalance;
        if (total == 0)
            return 0;
        return (_weeklyBalance.LeftBalance / (double)total) * 100;
    }

    private double GetRightPercentage()
    {
        if (_weeklyBalance is null)
            return 0;
        var total = _weeklyBalance.LeftBalance + _weeklyBalance.RightBalance;
        if (total == 0)
            return 0;
        return (_weeklyBalance.RightBalance / (double)total) * 100;
    }
}
