
using MTWorkHR.Application.Models;
using MTWorkHR.Core.UnitOfWork;
using MTWorkHR.Application.Services.Interfaces;
using MTWorkHR.Core.Entities;
using Microsoft.AspNetCore.Identity;
using MTWorkHR.Application.Mapper;
using MTWorkHR.Core.Global;
using MTWorkHR.Infrastructure.Entities;
using MTWorkHR.Infrastructure.Repositories;
using MTWorkHR.Infrastructure.UnitOfWorks;
using MTWorkHR.Core.IRepositories.Base;
using Microsoft.AspNetCore.Http;
using System.IO;
using System.Linq.Dynamic.Core;
using Microsoft.EntityFrameworkCore;
using MTWorkHR.Application.Identity;


namespace MTWorkHR.Application.Services
{
    public class UserTaskAttachmentService : BaseService<UserTaskAttachment, AttachmentDto, AttachmentDto>, IUserTaskAttachmentService
    {
        private readonly IUnitOfWork _unitOfWork;
        private readonly IUserService _userService;
        private readonly IFileService _fileService;
        private readonly GlobalInfo _globalInfo;

        public UserTaskAttachmentService(IUnitOfWork unitOfWork, IFileService fileService, GlobalInfo globalInfo, IUserService userService) : base(unitOfWork)
        {
            _unitOfWork = unitOfWork;
            _fileService = fileService;
            _globalInfo = globalInfo;
            _userService = userService;
        }


        public override async Task<AttachmentDto> GetById(long id)
        {
            var entity = await _unitOfWork.UserTaskAttachment.GetByIdAsync(id);
            var response = MapperObject.Mapper.Map<AttachmentDto>(entity);
            return response;
        }

        public override async Task<PagingResultDto<AttachmentDto>> GetAll(PagingInputDto PagingInputDto)
        {
            var res = await _unitOfWork.UserTaskAttachment.GetAllWithChildrenAsync();
            var query = res.Item1;
          
            if (PagingInputDto.Filter != null)
            {
                var filter = PagingInputDto.Filter;
                query = query.Where(u => u.FileName.Contains(filter));
            }

            var order = query.OrderBy(PagingInputDto.OrderByField + " " + PagingInputDto.OrderType);

            var page = order.Skip((PagingInputDto.PageNumber * PagingInputDto.PageSize) - PagingInputDto.PageSize).Take(PagingInputDto.PageSize);

            var total = await query.CountAsync();

            var list = MapperObject.Mapper
                .Map<IList<AttachmentDto>>(await page.ToListAsync());
            // Fetch user data for all employees
            foreach (var attach in list)
            {
                var user = await _userService.GetUserNameEmail(attach.CreateUser);
                attach.ProfileImage = user.ProfileImage;
                attach.CreatedUserName = user.FullName;
            }
            var response = new PagingResultDto<AttachmentDto>
            {
                Result = list,
                Total = total
            };

            return response;
        }

        public override async Task<AttachmentDto> Create(AttachmentDto input)
        {
            //if (input.FileData != null)
            //{
            //   // input.FilePath = await _fileService.UploadFile(input.FileData);
            //    input.OriginalName = input.FileData.FileName;
            //    List<AttachmentDto> attachs = new List<AttachmentDto>();
            //    attachs.Add(input);
            //    _fileService.CopyFileToCloud(ref attachs);

            //}
            
            var entity = MapperObject.Mapper.Map<UserTaskAttachment>(input);
            if (entity is null)
            {
                throw new AppException(ExceptionEnum.MapperIssue);
            }

            var attach = await _unitOfWork.UserTaskAttachment.AddAsync(entity);
            await _unitOfWork.CompleteAsync();

            var response = MapperObject.Mapper.Map<AttachmentDto>(attach);
            var user = await _userService.GetUserNameEmail(attach.CreateUser);
            response.ProfileImage = user.ProfileImage;
            response.CreatedUserName = user.FullName;
            return response;
        }


        public override async Task<AttachmentDto> Update(AttachmentDto input)
        {
            var attach = await _unitOfWork.UserTaskAttachment.GetByIdAsync(input.Id);

            if (attach == null)
                throw new AppException(ExceptionEnum.RecordNotExist);

            MapperObject.Mapper.Map(input, attach, typeof(AttachmentDto), typeof(UserTaskAttachment));

            await _unitOfWork.CompleteAsync();

            var response = MapperObject.Mapper.Map<AttachmentDto>(attach);

            var user = await _userService.GetUserNameEmail(attach.CreateUser);
            response.ProfileImage = user.ProfileImage;
            response.CreatedUserName = user.FullName;
            return input;
        }
    }
}
