using RenovationWorkBusinessLogic.OfficePackage.HelperModels;
using RenovationWorkBusinessLogic.OfficePackage;
using RenovationWorkContracts.BindingModels;
using RenovationWorkContracts.BusinessLogicsContracts;
using RenovationWorkContracts.SeatchModels;
using RenovationWorkContracts.StorageContracts;
using RenovationWorkContracts.ViewModels;
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;

namespace RenovationWorkBusinessLogic.BusinessLogic
{
    public class ReportLogic : IReportLogic
    {
        private readonly IComponentStorage _componentStorage;

        private readonly IRepairStorage _RepairStorage;

        private readonly IOrderStorage _orderStorage;

        private readonly AbstractSaveToExcel _saveToExcel;

        private readonly AbstractSaveToWord _saveToWord;

        private readonly AbstractSaveToPdf _saveToPdf;

        public ReportLogic(IRepairStorage RepairStorage, IComponentStorage componentStorage, IOrderStorage orderStorage,
            AbstractSaveToExcel saveToExcel, AbstractSaveToWord saveToWord, AbstractSaveToPdf saveToPdf)
        {
            _RepairStorage = RepairStorage;
            _componentStorage = componentStorage;
            _orderStorage = orderStorage;

            _saveToExcel = saveToExcel;
            _saveToWord = saveToWord;
            _saveToPdf = saveToPdf;
        }

        /// <summary>
        /// Получение списка компонент с указанием, в каких изделиях используются
        /// </summary>
        /// <returns></returns>
        public List<ReportRepairComponentViewModel> GetRepairComponent()
        {
            var components = _componentStorage.GetFullList();

            var Repairs = _RepairStorage.GetFullList();

            var list = new List<ReportRepairComponentViewModel>();

            foreach (var Repair in Repairs)
            {
                var record = new ReportRepairComponentViewModel
                {
                    RepairName = Repair.RepairName,
                    Components = new List<(string Component, int Count)>(),
                    TotalCount = 0
                };
                foreach (var component in components)
                {
                    if (Repair.RepairComponents.ContainsKey(component.Id))
                    {
                        record.Components.Add(new(component.ComponentName, Repair.RepairComponents[component.Id].Item2));
                        record.TotalCount += Repair.RepairComponents[component.Id].Item2;
                    }
                }

                list.Add(record);
            }

            return list;
        }

        /// <summary>
        /// Получение списка заказов за определенный период
        /// </summary>
        /// <param name="model"></param>
        /// <returns></returns>
        public List<ReportOrdersViewModel> GetOrders(ReportBindingModel model)
        {
            return _orderStorage.GetFilteredList(new OrderSearchModel { DateFrom = model.DateFrom, DateTo = model.DateTo })
                    .Select(x => new ReportOrdersViewModel
                    {
                        Id = x.Id,
                        DateCreate = x.DateCreate,
                        RepairName = x.RepairName,
                        Status = x.Status.ToString(),
                        Sum = x.Sum
                    })
                    .ToList();
        }

        /// <summary>
        /// Сохранение компонент в файл-Word
        /// </summary>
        /// <param name="model"></param>
        public void SaveRepairsToWordFile(ReportBindingModel model)
        {
            _saveToWord.CreateDoc(new WordInfo
            {
                FileName = model.FileName,
                Title = "Список ремонтных работ",
                Repairs = _RepairStorage.GetFullList()
            });
        }
        

        /// <summary>
        /// Сохранение компонент с указаеним продуктов в файл-Excel
        /// </summary>
        /// <param name="model"></param>
        public void SaveRepairComponentToExcelFile(ReportBindingModel model)
        {
            _saveToExcel.CreateReport(new ExcelInfo
            {
                FileName = model.FileName,
                Title = "Список компонент",
                RepairComponents = GetRepairComponent()
            });
        }

        /// <summary>
        /// Сохранение заказов в файл-Pdf
        /// </summary>
        /// <param name="model"></param>
        public void SaveOrdersToPdfFile(ReportBindingModel model)
        {
            _saveToPdf.CreateDoc(new PdfInfo
            {
                FileName = model.FileName,
                Title = "Список заказов",
                //DateFrom = model.DateFrom!.Value,
                //DateTo = model.DateTo!.Value,
                DateFrom = DateTime.SpecifyKind(model.DateFrom!.Value, DateTimeKind.Utc),
                DateTo = DateTime.SpecifyKind(model.DateTo!.Value, DateTimeKind.Utc),
                Orders = GetOrders(model)
            });
        }
    }
}
