using Microsoft.AspNetCore.Components;
using Microsoft.AspNetCore.Components.Server.ProtectedBrowserStorage;
using System;
using System.Collections.Generic;
using System.Linq;
using System.Threading;
using System.Threading.Tasks;
using WK5.Core;
using WK5.Core.Basis;
using WK5.Core.Basis.Filter;
using WK5.Core.Models;
using WK5.Core.Services;

namespace WK5_Blazor.Pages.Verkauf
{
    public class BelegÜbersichtBase : AlertPageBase, IHasPageFilter, IAsyncDisposable
    {
        public List<BelegÜbersicht> Übersicht { get; set; } = new List<BelegÜbersicht>();

        public BelegÜbersichtFilter Filter { get; set; } = new BelegÜbersichtFilter();

        private CancellationTokenSource _cts = new CancellationTokenSource();

        public Beleg? SelectedBeleg { get; set; }
        public Beleg? SelectedDetailsBeleg { get; set; }
        protected Dictionary<BelegTyp, List<int>> _subBelege = new Dictionary<BelegTyp, List<int>>();
        protected bool _showBelegInformationenModal;

        private int _seite = 1;

        [Parameter]
        public int Seite
        {
            get => _seite;
            set
            {
                if (value <= 0)
                {
                    value = 1;
                }

                _seite = value;
            }
        }

        public int TotalItems { get; set; }

        public bool _lädt { get; set; } = false;
        protected bool _isLoadingBeleg;
        protected bool _isLoadingBelegDetails;
#nullable disable
        [Inject] public BelegService belegService { get; set; }
        [Inject] public ProtectedLocalStorage LocalStorage { get; set; }
#nullable enable

        public string LocalStorageFilterKey => $"{Filter.Belegtyp}Übersicht.Filter";
        protected List<W4Paket> _pakete = new List<W4Paket>();

        protected Task CloseBelegDetails()
        {
            _showBelegInformationenModal = false;
            SelectedDetailsBeleg = null;
            _pakete.Clear();
            return Task.CompletedTask;
        }
        protected async Task ShowBelegDetails(BelegÜbersicht übersichtBeleg)
        {
            _pakete.Clear();
            _isLoadingBelegDetails = true;
            _showBelegInformationenModal = true;
            using FbController2 fbController = new FbController2();
            SelectedDetailsBeleg = Filter.Belegtyp switch
            {
                BelegTyp.Angebot => await Angebot.GetAngebotAsync(übersichtBeleg.BELU_N_NR, fbController),
                BelegTyp.Auftrag => await Auftrag.GetAuftragAsync(übersichtBeleg.BELU_N_NR, fbController),
                BelegTyp.Lieferschein => await Lieferschein.GetLieferscheinAsync(übersichtBeleg.BELU_N_NR, fbController),
                BelegTyp.Rechnung => await Rechnung.GetRechnungAsync(übersichtBeleg.BELU_N_NR, fbController),
                BelegTyp.Gutschrift => await Gutschrift.GetGutschriftAsync(übersichtBeleg.BELU_N_NR, fbController),
                _ => null
            };

            if (SelectedDetailsBeleg is not null)
            {
                _pakete = await W4Paket.GetVorgangsPakete(EnumHelper.GetBelegTyp(SelectedDetailsBeleg.Belegtyp), SelectedDetailsBeleg.Belegnummer).ToListAsync();
            }

            _isLoadingBelegDetails = false;
        }
        protected async Task OnBelegSelected(BelegÜbersicht übersichtBeleg)
        {
            _isLoadingBeleg = true;
            using FbController2 fbController = new FbController2();
            if (SelectedBeleg is not null && SelectedBeleg.Belegnummer == übersichtBeleg.BELU_N_NR)
            {
                SelectedBeleg = null;
                SelectedÜbersicht = null;
                _subBelege.Clear();
            }
            else
            {
                SelectedBeleg = Filter.Belegtyp switch
                {
                    BelegTyp.Angebot => await Angebot.GetAngebotAsync(übersichtBeleg.BELU_N_NR, fbController),
                    BelegTyp.Auftrag => await Auftrag.GetAuftragAsync(übersichtBeleg.BELU_N_NR, fbController),
                    BelegTyp.Lieferschein => await Lieferschein.GetLieferscheinAsync(übersichtBeleg.BELU_N_NR, fbController),
                    BelegTyp.Rechnung => await Rechnung.GetRechnungAsync(übersichtBeleg.BELU_N_NR, fbController),
                    BelegTyp.Gutschrift => await Gutschrift.GetGutschriftAsync(übersichtBeleg.BELU_N_NR, fbController),
                    _ => null
                };
                SelectedÜbersicht = übersichtBeleg;
                if (SelectedBeleg is not null)
                {
                    _subBelege = await belegService.GetSubBelege(Filter.Belegtyp, SelectedBeleg.Belegnummer, fbController);
                }
                else
                {
                    _subBelege.Clear();
                }
            }

            _isLoadingBeleg = false;

        }
        protected async Task ResetFilter()
        {
            Filter = new BelegÜbersichtFilter { Belegtyp = Filter.Belegtyp };
            await LadeÜbersicht();
        }

        protected override async Task OnParametersSetAsync()
        {


            try
            {
                var localStorageResult = await LocalStorage.GetAsync<BelegÜbersichtFilter>(LocalStorageFilterKey);
                if (localStorageResult.Success)
                {
                    if (localStorageResult.Value is not null)
                    {
                        Filter = localStorageResult.Value;
                    }
                }
            }
            catch (Exception)
            {


            }


            await LadeÜbersicht();
            await SetAlerts();
        }

        public async Task LadeÜbersicht(bool navigateToPage1 = false)
        {
            if (_lädt)
            {
                return;
            }

            _lädt = true;
            if (navigateToPage1)
            {
                Seite = 1;
            }

            _cts.Cancel();
            _cts.Dispose();
            _cts = new CancellationTokenSource();
            Filter.Seite = Seite;
            Übersicht.Clear();
            await LocalStorage.SetAsync(LocalStorageFilterKey, Filter);
            var token = _cts.Token;
            try
            {
                await foreach (var item in belegService.GetBelegÜbersichtAsync(Filter, token))
                {
                    Übersicht.Add(item);
                    StateHasChanged();
                }

                TotalItems = await belegService.GetBelegÜbersichtAnzahlAsync(Filter, token);
            }
            catch (ObjectDisposedException)
            {
                // Tritt auf, wenn die Seite gewechselt wird, aber noch Daten geladen werden
            }
            catch (Exception)
            {
                Filter = new BelegÜbersichtFilter()
                {
                    Belegtyp = Filter.Belegtyp
                };
                await LocalStorage.SetAsync(LocalStorageFilterKey, Filter);
                throw;
            }




            _lädt = false;
        }





        public string GetRowClass(BelegÜbersicht übersicht)
        {
            if (übersicht.BELU_L_PAUSIERT)
            {
                return "bg-warning";
            }
            else
            {
                return String.Empty;
            }
        }



        public override ValueTask DisposeAsync()
        {
            _cts.Cancel();
            _cts.Dispose();
            return base.DisposeAsync();
        }

        public BelegÜbersicht? SelectedÜbersicht { get; set; }
    }
}
