using HHncore.Pass.Vpn.Request.Product;
using Hncore.Infrastructure.Common;
using Hncore.Infrastructure.Extension;
using Hncore.Infrastructure.Service;
using Hncore.Infrastructure.WebApi;
using Hncore.Pass.Vpn.Domain;
using Microsoft.AspNetCore.Http;
using Microsoft.EntityFrameworkCore;
using Microsoft.Extensions.Configuration;
using System;
using System.Collections.Generic;
using System.Linq;
using System.Linq.Expressions;
using System.Threading.Tasks;
using Hncore.Infrastructure.EntitiesExtension;
using Hncore.Infrastructure.EF;
namespace Hncore.Pass.Vpn.Service
{
    public partial class ProductAccountService : ServiceBase<ProductAccountEntity>, IFindService
    {
        CourseContext m_DbContext;
        private IConfiguration m_Configuration;
        public AgentService m_AgentService;
        private UserService m_UserService;
        public ProductAccountService(CourseContext dbContext  
            , AgentService _AgentService
            , UserService _UserService
             , IConfiguration _Configuration
            , IHttpContextAccessor httpContextAccessor) : base(dbContext, httpContextAccessor)
        {
            m_DbContext = dbContext;
            m_AgentService = _AgentService;
            m_Configuration = _Configuration;
            m_UserService = _UserService;
        }

        public async Task<bool> CheckAccountExist(int productId, List<string> accouts)
        {
            var flag = this.Exist(m => accouts.Contains(m.Account) && m.DeleteTag == 0);
            if (flag)
            {
                return true;
            }
            foreach (var item in accouts)
            {
                var ret = await m_AgentService.Exist(productId, item);
                await Task.Delay(50);
                if (ret == true)
                    return true;
            }

            return false;
        }
        //检查参加活动账号是否已经存在
        public async Task<bool> CheckMonthAccountExist(string account)
        {
            var flag = this.Exist(m => m.Account == account && m.PackageId == 86);
            if (flag)
            {
                return true;
            }

            return false;
        }
        public bool CheckUserAccountExist(int product, List<string> accouts, int userId)
        {
            return this.Exist(m => accouts.Contains(m.Account) && m.UserId == userId);
        }

        public async Task<ProductAccountEntity> GetAccountInfo(string accout, int userId)
        {
            return await this.Query(true).FirstOrDefaultAsync(m => m.Account == accout && m.UserId == userId && m.DeleteTag == 0);
        }

        public async Task<List<ProductAccountEntity>> GetAccounts(string accouts,int userId=0)
        {
            var alist = accouts.Split(",");
            return await this.Query(m =>(userId==0||m.UserId== userId)&& alist.Contains(m.Account)&&m.DeleteTag==0).ToListAsync();
        }

        public async Task<ProductAccountEntity> GetAccountInfo(string accout)
        {
            return await this.Query(true).FirstOrDefaultAsync(m => m.Account == accout);
        }
        
        public async Task<ProductAccountEntity> GetAccountNotRefundInfo(string accout)
        {
            return await this.Query(true).FirstOrDefaultAsync(m => m.Account == accout && m.DeleteTag == 0);
        }

        public async Task<ProductAccountEntity> GetAccountInfo(int packageId,string accout)
        {
            return await this.Query(true).FirstOrDefaultAsync(m =>m.PackageId== packageId&& m.Account == accout);
        }

        public async Task<ProductAccountEntity> GetProductAccountInfo(int productId, string accout)
        {
            return await this.Query(true).FirstOrDefaultAsync(m => m.ProductId == productId && m.Account == accout && m.DeleteTag == 0);
        }

        /// <summary>
        /// day 0：已过期，1天 
        /// </summary>
        /// <param name="day"></param>
        /// <returns></returns>
        public async Task<List<ProductAccountEntity>> GetExpireingAccounts_bak(int day)
        {
            Expression<Func<ProductAccountEntity, bool>> expr = m => 1 == 1;          

            if (day == 0)
            {
                expr = expr.And(m => m.EndTime.Value < DateTime.Now);
            }
            else
            {
                var startTime = DateTime.Now.Begin().AddDays(day);               
                var EndTime = DateTime.Now.End().AddDays(day);
                expr = expr.And(m => m.EndTime >= startTime && m.EndTime <= EndTime);
            }
            return await this.Query(expr,true).ToListAsync();
        }

        public async Task<List<ProductAccountEntity>> GetExpireingAccounts(int day)
        {
            var sql = $"select * from product_account where DATEDIFF(EndTime,now())={day}";
            return this.m_DbContext.SqlQuery<ProductAccountEntity>(sql);
        }

        //主要是用来定时执行的
        public async Task<List<ProductAccountEntity>> GetExpireingAccountsTime(int day)
        {
            var sql = $"select * from product_account WHERE DATEDIFF(EndTime,now())={day} AND `PackageName` NOT LIKE '天卡' AND `PackageName` NOT LIKE '测试卡' GROUP BY UserId";
            // var sql = $"select * from product_account where DATEDIFF(EndTime,now())={day} AND PackageName!='测试卡' AND PackageName!='天卡' GROUP BY UserId";
            return this.m_DbContext.SqlQuery<ProductAccountEntity>(sql);
        }

        public async Task<ApiResult> UpdateAccountPwd(UpdateAccountPwdRequest request)
        {
            var entity = await this.GetById(request.Id);
            if (entity == null)
            {
                return new ApiResult(ResultCode.C_INVALID_ERROR, "账号不存在");
            }
            if (request.Pwd.NotHas())
            {
                return new ApiResult(ResultCode.C_INVALID_ERROR, "密码不能为空");
            }
            var agentRet = await m_AgentService.UpdateAccountPwd(entity.ProductId.Value, entity.Account, request.Pwd);
            if (!agentRet)
            {
                return new ApiResult(ResultCode.C_INVALID_ERROR, "远程更新失败");
            }
            entity.Pwd = request.Pwd;
            await this.Update(entity);
            return new ApiResult(1);
        }

        public async Task<ApiResult> ApiUpdateAccountPwd(UpdateAccountPwdRequest request,int userid)
        {
            var entity = await this.Query(m => m.Account == request.Account && m.Pwd == request.Pwd && m.DeleteTag == 0 && m.UserId == userid).FirstOrDefaultAsync();
            if (entity == null)
            {
                return new ApiResult(ResultCode.C_INVALID_ERROR, "账号不存在");
            }
            if (request.Pwd.NotHas()&&request.RePwd.NotHas())
            {
                return new ApiResult(ResultCode.C_INVALID_ERROR, "密码不能为空");
            }
            var agentRet = await m_AgentService.UpdateAccountPwd(entity.ProductId.Value, entity.Account, request.RePwd);
            if (!agentRet)
            {
                return new ApiResult(ResultCode.C_INVALID_ERROR, "远程更新失败");
            }
            entity.Pwd = request.RePwd;
            await this.Update(entity);
            return new ApiResult(1);
        }


        public async Task<List<ProductAccountEntity>> GetUserTestAccount(int userId)
        {
           return await this.Query(m => m.UserId == userId && m.AccountType == (int)AccountType.Test).ToListAsync();
        }

        public async Task<int> GetRestTestCount(int userId)
        {
            var userInfo = await m_UserService.GetById(userId);
            var restTimes = Convert.ToInt32(m_Configuration["TestCountLimit"]);
            if (userInfo.TestCountLimit > 0) restTimes = userInfo.TestCountLimit.Value;
            restTimes = restTimes - userInfo.UseTestCount.Value;
            restTimes = restTimes < 0 ? 0 : restTimes;
            return restTimes;
        }
        //获取是否实名认证
        public async Task<int> GetUserStatus(int userId)
        {
            var userInfo = await m_UserService.GetById(userId);
            var flag = userInfo.is_verify;
            return flag;
        }
    }
}
