using ecoDMS.Library;
using Serilog;
using System;
using System.Collections.Generic;
using System.Linq;
using System.Threading.Tasks;

namespace WK5.Core
{
    /// <summary>
    /// Stellt ecoDMS Funktionen speziell für Karley zur Verfügung.
    /// </summary>
    public class KarleyEcoDmsController : EcoDmsController
    {
        protected KarleyEcoDmsController(Uri basisUrl, string anmeldeDaten, ILogger logger) : base(basisUrl, anmeldeDaten, logger)
        {

        }
        /// <summary>
        /// Erstellt einen neuen <see cref="KarleyEcoDmsController"/>
        /// </summary>
        /// <param name="basisUrl"></param>
        /// <param name="anmeldeDaten"></param>
        /// <param name="logger"></param>
        /// <returns></returns>
        public static async Task<KarleyEcoDmsController> CreateAsync(Uri basisUrl, string anmeldeDaten, ILogger logger)
        {
            KarleyEcoDmsController controller = new KarleyEcoDmsController(basisUrl, anmeldeDaten, logger);
            await controller.InitializeAsync();
            return controller;
        }
        /// <summary>
        /// Sucht nach Belegen in ecoDMS ab einem bestimmten Datum
        /// </summary>
        /// <param name="datum"></param>
        /// <param name="belegtyp"></param>
        /// <returns></returns>
        public async Task<HashSet<int>> GetAlleBelegNummernFromDatumGroesserAsync(DateTime datum, string belegtyp = "RE")
        {
            HashSet<int> _ergebnis = new HashSet<int>();
            EcoSearchFilters.Clear();
            EcoSearchFilter ecoSearchFilter = new EcoSearchFilter
            {
                ClassifyAttribut = "cdate",
                SearchOperator = SuchOperator.Groessergleich,
                SearchValue = datum.ToString("yyyy-MM-dd")
            };
            EcoSearchFilter ecoSearchFilter1 = new EcoSearchFilter();
            if (belegtyp == "RE" || belegtyp == "MM-")
            {
                ecoSearchFilter1 = new EcoSearchFilter
                {
                    ClassifyAttribut = "docart",
                    SearchOperator = SuchOperator.Gleich,
                    SearchValue = Dokumentenarten["Rechnungsausgang"].Id.ToString()
                };

            }
            else
            {
                ecoSearchFilter1 = new EcoSearchFilter
                {
                    ClassifyAttribut = "docart",
                    SearchOperator = SuchOperator.Gleich,
                    SearchValue = Dokumentenarten["Gutschrift"].Id.ToString()
                };
            }
            if (belegtyp == "MM-" || belegtyp == "MMG-" || belegtyp == "MMPG-")
            {
                EcoSearchFilters.Add(new EcoSearchFilter
                {
                    ClassifyAttribut = ClassifyAttributes.GetKeyByValue("Belegnummer"),
                    SearchOperator = SuchOperator.Ilike,
                    SearchValue = belegtyp
                });
            }

            EcoSearchFilters.Add(ecoSearchFilter);
            EcoSearchFilters.Add(ecoSearchFilter1);
            EcoDmsdocInfoCLs = await EcoSucheDoksAsync(EcoSearchFilters);

            string myKey = ClassifyAttributes.FirstOrDefault(x => x.Value == "Belegnummer").Key;
            // Rechnungsnummer in : dyn_1_1482499244364 bei Karley .. aber holen wir über den Key, so sind wir global
            foreach (EcoDMSdocInfoCL ecoDMSdocInfo in EcoDmsdocInfoCLs)
            {
                string parserString = ecoDMSdocInfo.ClassifyAttributes[myKey];
                //Wir müssen die Prefixe raus nehmen!
                if (belegtyp == "MM-" || belegtyp == "MMG-")
                {
                    parserString = parserString.Replace(belegtyp, String.Empty);
                }
                _ = int.TryParse(parserString, out int Zahl);
                if (Zahl > 0)
                {
                    _ergebnis.Add(Zahl);
                }
            }
            return _ergebnis;
        }

        public async Task<List<int>> GetAlleKarleyRechnungenFromDatumAsync(DateTime datum)
        {
            List<int> ergebnis = new List<int>();
            EcoSearchFilters.Clear();
            EcoSearchFilter ecoSearchFilter = new EcoSearchFilter { ClassifyAttribut = "cdate", SearchOperator = SuchOperator.Gleich, SearchValue = datum.ToString("yyyy-MM-dd") };
            EcoSearchFilter ecoSearchFilter1 = new EcoSearchFilter { ClassifyAttribut = "docart", SearchOperator = SuchOperator.Gleich, SearchValue = Dokumentenarten["Rechnungsausgang"].Id.ToString() };
            EcoSearchFilters.Add(ecoSearchFilter);
            EcoSearchFilters.Add(ecoSearchFilter1);
            EcoDmsdocInfoCLs = await EcoSucheDoksAsync(EcoSearchFilters);


            string myKey = ClassifyAttributes.FirstOrDefault(x => x.Value == "Belegnummer").Key;
            // Rechnungsnummer in : dyn_1_1482499244364 bei Karley .. aber holen wir über den Key, so sind wir global
            foreach (EcoDMSdocInfoCL ecoDMSdocInfo in EcoDmsdocInfoCLs)
            {
                _ = int.TryParse(ecoDMSdocInfo.ClassifyAttributes[myKey], out int Zahl);
                ergebnis.Add(Zahl);
            }
            return ergebnis;
        }


        /// <summary>
        /// Sucht ein Dokument in ecoDMS und gibt zurück ob es gefunden wurde.
        /// </summary>
        /// <param name="belegnummer">String weil ecoDMS Stringsuche</param>
        /// <param name="belegTyp">String weil ecoDMS Stringsuche</param>
        /// <param name="kontonummer">String weil ecoDMS Stringsuche</param>
        /// <returns></returns>
        public async Task<bool> IstDokumentArchiviertAsync(string belegnummer, string belegTyp, string kontonummer = "")
        {

            string myKey = ClassifyAttributes.FirstOrDefault(x => x.Value == "Belegnummer").Key;
            EcoSearchFilters.Clear();
            EcoSearchFilter ecoSearchFilter = new EcoSearchFilter
            {
                ClassifyAttribut = myKey,
                SearchOperator = SuchOperator.Gleich,
                SearchValue = belegnummer
            };
            EcoSearchFilter docArt = new EcoSearchFilter();

            docArt = belegTyp switch
            {
                "RE" => new EcoSearchFilter
                {
                    ClassifyAttribut = "docart",
                    SearchOperator = SuchOperator.Gleich,
                    SearchValue = Dokumentenarten["Rechnungsausgang"].Id.ToString()
                },
                "GU" => new EcoSearchFilter
                {
                    ClassifyAttribut = "docart",
                    SearchOperator = SuchOperator.Gleich,
                    SearchValue = Dokumentenarten["Gutschrift"].Id.ToString()
                },
                "AU" => new EcoSearchFilter
                {
                    ClassifyAttribut = "docart",
                    SearchOperator = SuchOperator.Gleich,
                    SearchValue = Dokumentenarten["Bestellung"].Id.ToString()
                },
                "LS" => new EcoSearchFilter
                {
                    ClassifyAttribut = "docart",
                    SearchOperator = SuchOperator.Gleich,
                    SearchValue = Dokumentenarten["Lieferschein"].Id.ToString()
                },
                "MM-" => new EcoSearchFilter
                {
                    ClassifyAttribut = "docart",
                    SearchOperator = SuchOperator.Gleich,
                    SearchValue = Dokumentenarten["Rechnungsausgang"].Id.ToString()
                },
                "MMG-" => docArt = new EcoSearchFilter
                {
                    ClassifyAttribut = "docart",
                    SearchOperator = SuchOperator.Gleich,
                    SearchValue = Dokumentenarten["Gutschrift"].Id.ToString()
                },
                "MMPG-" =>
                docArt = new EcoSearchFilter
                {
                    ClassifyAttribut = "docart",
                    SearchOperator = SuchOperator.Gleich,
                    SearchValue = Dokumentenarten["Gutschrift"].Id.ToString()
                },
                _ => throw new ArgumentException($"Belegtyp {belegTyp} kann nicht verarbeitet werden", nameof(belegTyp))
            };


            if (belegTyp == "MM-")
            {
                ecoSearchFilter = new EcoSearchFilter
                {
                    ClassifyAttribut = myKey,
                    SearchOperator = SuchOperator.Gleich,
                    SearchValue = $"{(belegnummer.StartsWith("MM-") ? String.Empty : "MM-")}{belegnummer}"
                };
            }
            else if (belegTyp == "MMG-")
            {
                ecoSearchFilter = new EcoSearchFilter
                {
                    ClassifyAttribut = myKey,
                    SearchOperator = SuchOperator.Gleich,
                    SearchValue = $"{(belegnummer.StartsWith("MMG-") ? String.Empty : "MMG-")}{belegnummer}"
                };

            }


            EcoSearchFilters.Add(ecoSearchFilter);
            EcoSearchFilters.Add(docArt);
            if (kontonummer != string.Empty)
            {
                EcoSearchFilter ecoSearchFilterKonto = new EcoSearchFilter
                {
                    ClassifyAttribut = ClassifyAttributes.FirstOrDefault(x => x.Value == "Kontonummer").Key,
                    SearchOperator = SuchOperator.Gleich,
                    SearchValue = kontonummer
                };
                EcoSearchFilters.Add(ecoSearchFilterKonto);
            }
            EcoDmsdocInfoCLs = await EcoSucheDoksAsync(EcoSearchFilters);
            return EcoDmsdocInfoCLs.Any();
        }

    }
}
