using Common.Models.Auth;
using Common.Models.Auth.CompanySide;
using Common.Models.Auth.UserSide;
using Common.Validation;
using Hushian.Application.Constants;
using Hushian.Application.Contracts.Persistence;
using Hushian.Application.Models;
using Hushian.Domain.Entites;
using Microsoft.EntityFrameworkCore;
using Microsoft.Extensions.Options;
using Microsoft.IdentityModel.Tokens;
using System;
using System.Collections.Generic;
using System.IdentityModel.Tokens.Jwt;
using System.Linq;
using System.Security.Claims;
using System.Text;
using System.Threading.Tasks;

namespace Hushian.Application.Services
{
    public class AuthService
    {
        private readonly JwtSettings _jwtSettings;
        private readonly IGenericRepository<Company> _CompanyRepository;
        private readonly IGenericRepository<User> _UserRepository;
        private readonly IGenericRepository<Exper> _ExperRepository;
        private readonly VerificationService _verificationService;
        public AuthService(IOptions<JwtSettings> jwtSettings
            , IGenericRepository<Company> companyRepository
            , IGenericRepository<User> userRepository
            , IGenericRepository<Exper> experRepository
            , VerificationService verificationService)
        {
            _jwtSettings = jwtSettings.Value;
            _CompanyRepository = companyRepository;
            _UserRepository = userRepository;
            _ExperRepository = experRepository;
            _verificationService = verificationService;
        }
        public async Task<ResponseBase<AuthResponse>> AuthenticationFromCompanySide
            (AuthRequestFromCompanySide auth)
        {
            ResponseBase<AuthResponse> Response = new();
            if (!FixedValidation.CheckUsername(auth.Username))
            {
                Response.Errors.Add("نام کاربری اشتباه است");
            }
            else
            {
                if (auth.Username.StartsWith("09"))
                {
                    // in Company Search
                    var Company = await _CompanyRepository.Get()
                        .FirstOrDefaultAsync(f => f.Mobile == auth.Username && f.Password == auth.Password.GetHash() && f.Verified);
                    if (Company == null)
                    {
                        Response.Errors.Add("کاربری یافت نشد");
                    }
                    else
                    {
                        Response.Success = true;
                        Response.Value = new AuthResponse()
                        {
                            Fullname = Company.FullName,
                            Id = Company.ID,
                            Role="Company",
                            img=Company.logo,
                            MobileOrUserName = Company.Mobile,
                            CompanyId= Company.ID,
                            Token = new JwtSecurityTokenHandler().WriteToken(_jwtSettings.GenerateToken(Company.Mobile, Company.ID, "Company"))
                        };
                    }
                }
                else
                {
                    var exper = await _ExperRepository.Get().Include(inc=>inc.Company).FirstOrDefaultAsync(f => f.UserName == auth.Username
                    && f.Password == auth.Password.GetHash() && f.Available);
                    if (exper == null)
                    {
                        Response.Errors.Add("کاربری یافت نشد");
                    }
                    else
                    {
                        Response.Success = true;
                        Response.Value = new AuthResponse()
                        {
                            Fullname = exper.FullName+" ("+ exper.Company.FullName+")",
                            Id = exper.ID,
                            CompanyId = exper.CompanyID,
                            MobileOrUserName = exper.UserName,
                            Role="Exper",
                            Token = new JwtSecurityTokenHandler().WriteToken(_jwtSettings.GenerateToken(exper.UserName, exper.ID, "Exper"))
                        };
                    }
                }
            }

            return Response;
        }
        public async Task<ResponseBase<int>> AuthenticationFromUserSide
            (AuthRequestFromUserSide auth)
        {
            ResponseBase<int> Response = new();
            if (!FixedValidation.CheckUsername(auth.Mobile))
            {
                Response.Errors.Add("نام کاربری اشتباه است");
            }
            else
            {
                if (!await _UserRepository.Get().AnyAsync(a => a.Mobile == auth.Mobile))
                {
                    if (!await _UserRepository.ADDBool(new User() { Mobile = auth.Mobile, FullName = auth.FullName }))
                    {
                        Response.Errors.Add("خطا در کاربری");
                    }
                }

                if (Response.Errors.Count == 0)
                {

                    Response.Value = await _verificationService.GenerateCodeForLoginUser(auth.Mobile);
                    Response.Success = true;
                }
            }

            return Response;
        }

    
    }
}
