using Furion.DependencyInjection;
using Furion.DistributedIDGenerator;
using Nirvana.Common;
using Nirvana.Common.ApiBase;
using SqlSugar;
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
using YBDevice.Application.AdInfo;
using YBDevice.Entity;

namespace YBDevice.Application
{
    /// <summary>
    /// 资讯管理
    /// </summary>
    public class InfoService :IInfoService, ITransient
    {
        private readonly ISqlSugarRepository<YB_nSecInfo> repository;
        private readonly SqlSugarClient dbClient;
        private readonly OperatorModel currentUser;

        public InfoService(ISqlSugarRepository<YB_nSecInfo> sqlSugarRepository)
        {
            repository = sqlSugarRepository;
            dbClient = repository.Context;
            currentUser = BaseInfoService.GetUserInfo();
        }

        /// <summary>
        /// 资讯列表
        /// </summary>
        /// <param name="param"></param>
        /// <returns></returns>
        public async Task<PageParms<SecInfoListModel>> GetListAsync(QueryParams param)
        {
            RefAsync<int> totalnum = 0;
            var temquery = dbClient.Queryable<YB_nSecInfo>();
            if (param.queryParam != null && param.queryParam.Count > 0)
            {
                List<IConditionalModel> conModels = new List<IConditionalModel>();
                param.queryParam.ForEach(x =>
                {
                    if (!string.IsNullOrEmpty(x.Value))
                    {
                        conModels.Add(new ConditionalModel()
                        {
                            FieldName = x.Name,
                            ConditionalType = (ConditionalType)x.Type,
                            FieldValue = x.Value.Trim()
                        });
                    }
                });
                if (conModels.Count > 0)
                {
                    temquery = temquery.Where(conModels);
                }
            }
            if (currentUser.AccountType != AccountType.platform)
            {
                temquery = temquery.Where(x => x.BusienssId == currentUser.BusinessId);
            }
            string sorts = string.Format("{0} {1}", param.sort, param.order);
            var query = await temquery.OrderBy(sorts)
                .Select(x => new SecInfoListModel
                {
                    Id = x.Id,
                    Title = x.Title,
                    HeadImg = x.HeadImg,
                    CreateTime = x.CreateTime,
                    TagId = x.TagId,
                    Status = x.Status,
                    ClickCount = x.ClickCount
                })
                .Mapper((it, cache) =>
                {
                    var alltag = cache.Get(list =>
                    {
                        var ids = list.Select(x => x.TagId).ToList();
                        return dbClient.Queryable<YB_SecInfoType>().Where(x => ids.Contains(x.Id)).ToList();
                    });
                    it.tagname = alltag.FirstOrDefault(x => x.Id == it.TagId)?.Name;
                })
                 .ToPageListAsync(param.offset, param.limit, totalnum);
            return new PageParms<SecInfoListModel>
            {
                page = param.offset,
                Items = query,
                totalnum = totalnum,
                limit = param.limit
            };
        }

        ///// <summary>
        ///// 迁移secinfo到新表中
        ///// </summary>
        ///// <returns></returns>
        //public async Task SecToNew()
        //{
        //    var allsec = await dbClient.Queryable<YB_nSecInfo>().ToListAsync();
        //    var allcontent = await dbClient.Queryable<YB_SecInfoContent>().ToListAsync();
        //    List<YB_nSecInfo> slist = new List<YB_nSecInfo>();
        //    List<YB_nSecInfoAppId> alist = new List<YB_nSecInfoAppId>();
        //    List<YB_nSecInfoContent> clist = new List<YB_nSecInfoContent>();
        //    foreach (var item in allsec)
        //    {
        //        var secinfo = new YB_nSecInfo
        //        {
        //            Id = IDGen.NextID(),
        //            Status = item.Status,
        //            StatusRemark = item.StatusRemark,
        //            BusienssId = item.BusienssId,
        //            ClickCount = item.ClickCount,
        //            HeadImg = item.HeadImg,
        //            CreateTime = item.CreateTime,
        //            TagId = item.TagId,
        //            Title = item.Title,
        //            Type = item.Type
        //        };
        //        slist.Add(secinfo);
        //        alist.Add(new YB_nSecInfoAppId
        //        {
        //            AppId = item.AppId,
        //            InfoId = secinfo.Id
        //        });
        //        var content = allcontent.FirstOrDefault(x => x.InfoId == item.Id);
        //        string cont = content != null ? content.Content : "";
        //        clist.Add(new YB_nSecInfoContent
        //        {
        //            InfoId = secinfo.Id,
        //            Content = cont
        //        });
        //    }
        //    await dbClient.Insertable(slist).ExecuteCommandAsync();
        //    await dbClient.Insertable(alist).ExecuteCommandAsync();
        //    await dbClient.Insertable(clist).ExecuteCommandAsync();
        //}


        /// <summary>
        /// 信息提交
        /// </summary>
        /// <param name="model"></param>
        /// <returns></returns>
        public async Task<ResultInfo> SubmitAsync(SecInfoSubmitModel model)
        {
            model.AppId = model.AppId.ToStr();
            List<string> appids = model.AppId.Split(',').ToList();
            if (model.Id !=Guid.Empty)
            {
                await dbClient.Updateable<YB_nSecInfo>().SetColumns(x => new YB_nSecInfo
                {
                    HeadImg = model.HeadImg,
                    TagId = model.TagId,
                    Title = model.Title,
                    Type = model.Type,
                    ClickCount = model.ClickCount
                }).Where(x => x.Id == model.Id).ExecuteCommandAsync();

                await dbClient.Updateable<YB_nSecInfoContent>().SetColumns(x => new YB_nSecInfoContent
                {
                    Content = model.content
                }).Where(x => x.InfoId == model.Id).ExecuteCommandAsync();
                //修改绑定的小程序
                await dbClient.Deleteable<YB_nSecInfoAppId>().Where(x => x.InfoId == model.Id).ExecuteCommandAsync();
                var list = new List<YB_nSecInfoAppId>();
                appids.ForEach(x => {
                    list.Add(new YB_nSecInfoAppId { 
                        AppId = x,
                        InfoId = model.Id
                    });
                });
                await dbClient.Insertable(list).ExecuteCommandAsync();
                return new ResultInfo(ResultState.SUCCESS, "修改成功");
            }
            else
            {
                var info = new YB_nSecInfo
                {
                    CreateTime = DateTime.Now,
                    Status = (int)AdStatus.Wait,
                    BusienssId = currentUser.BusinessId,
                    ClickCount = model.ClickCount,
                    HeadImg = model.HeadImg,
                    StatusRemark = "",
                    TagId = model.TagId,
                    Title = model.Title,
                    Type = model.Type,
                    Id = IDGen.NextID()
                };
                await dbClient.Insertable(info).ExecuteCommandAsync();
                var data = new YB_nSecInfoContent
                {
                    Content = model.content,
                    InfoId = info.Id
                };
                await dbClient.Insertable(data).ExecuteCommandAsync();
                //修改绑定的小程序
                var list = new List<YB_nSecInfoAppId>();
                appids.ForEach(x => {
                    list.Add(new YB_nSecInfoAppId
                    {
                        AppId = x,
                        InfoId = model.Id
                    });
                });
                await dbClient.Insertable(list).ExecuteCommandAsync();
                return new ResultInfo(ResultState.SUCCESS, "添加成功");
            }
        }
        /// <summary>
        /// 状态修改
        /// </summary>
        /// <param name="id">记录ID</param>
        /// <param name="status">状态</param>
        /// <param name="remark">状态描述</param>
        /// <returns></returns>
        public async Task<ResultInfo> SetStatusAsync(Guid id, AdStatus status, string remark)
        {
            if (!await dbClient.Queryable<YB_nSecInfo>().AnyAsync(x => x.Id == id))
            {
                return new ResultInfo(ResultState.FAIL, "记录未找到");
            }
            //更新状态
            await dbClient.Updateable<YB_nSecInfo>().SetColumns(x => new YB_nSecInfo
            {
                Status = status
            }).Where(x => x.Id == id).ExecuteCommandAsync();
            return new ResultInfo(ResultState.SUCCESS, "状态更新成功");
        }

        /// <summary>
        /// 详情
        /// </summary>
        /// <param name="id"></param>
        /// <returns></returns>
        public async Task<SecInfoSubmitModel> DetailAsync(Guid id)
        {
            var info = await dbClient.Queryable<YB_nSecInfo>().Select(x => new SecInfoSubmitModel
            {
                Title = x.Title,
                HeadImg = x.HeadImg,
                TagId = x.TagId,
                Type = x.Type,
                Id = x.Id
            }).Where(x => x.Id == id).FirstAsync();
            var content = await dbClient.Queryable<YB_nSecInfoContent>().Where(x => x.InfoId == id).FirstAsync();
            info.content = content?.Content;
            var appid = await dbClient.Queryable<YB_nSecInfoAppId>()
                .Where(x => x.InfoId == id)
                .Select(x=>x.AppId)
                .ToListAsync();
            info.AppId = String.Join(",", appid);
            return info;
        }

        /// <summary>
        /// 类型列表
        /// </summary>
        /// <param name="param"></param>
        /// <returns></returns>
        public async Task<PageParms<SecInfoTypeModel>> GetTypeListAsync(QueryParams param)
        {
            RefAsync<int> totalnum = 0;
            var temquery = dbClient.Queryable<YB_SecInfoType>();
            if (param.queryParam != null && param.queryParam.Count > 0)
            {
                List<IConditionalModel> conModels = new List<IConditionalModel>();
                param.queryParam.ForEach(x =>
                {
                    if (!string.IsNullOrEmpty(x.Value))
                    {
                        conModels.Add(new ConditionalModel()
                        {
                            FieldName = x.Name,
                            ConditionalType = (ConditionalType)x.Type,
                            FieldValue = x.Value.Trim()
                        });
                    }
                });
                if (conModels.Count > 0)
                {
                    temquery = temquery.Where(conModels);
                }
            }
            if (currentUser.AccountType != AccountType.platform)
            {
                temquery = temquery.Where(x => x.BusienssId == currentUser.BusinessId);
            }
            string sorts = string.Format("{0} {1}", param.sort, param.order);
            var query = await temquery.OrderBy(sorts)
                    .Select(x => new SecInfoTypeModel
                    {
                        Id = x.Id,
                        Status = x.Status,
                        SortCode = x.SortCode,
                        BusienssId = x.BusienssId,
                        CreateTime = x.CreateTime,
                        Name = x.Name,
                        Remark = x.Remark
                    })
                     .Mapper((it, cache) =>
                     {
                         var allbuss = cache.Get(list =>
                         {
                             var ids = list.Where(x => x.BusienssId > 0).Select(x => x.BusienssId).ToList();
                             return dbClient.Queryable<YB_Business>().Where(x => ids.Contains(x.Id)).ToList();
                         });
                         it.BusinessName = allbuss.FirstOrDefault(x => x.Id == it.BusienssId)?.Name;
                     })
                 .ToPageListAsync(param.offset, param.limit, totalnum);
            return new PageParms<SecInfoTypeModel>
            {
                page = param.offset,
                Items = query,
                totalnum = totalnum,
                limit = param.limit
            };
        }

        /// <summary>
        /// 所有类型列表
        /// </summary>
        /// <returns></returns>
        public async Task<List<YB_SecInfoType>> GetAllTypeAsync()
        {
            var tempquery = dbClient.Queryable<YB_SecInfoType>()
                .Where(x => x.Status == StatusType.Enabled);
            if (currentUser.AccountType != AccountType.platform)
            {
                tempquery = tempquery.Where(x => x.BusienssId == currentUser.BusinessId);
            }
            else
            {
                tempquery = tempquery.Where(x => x.BusienssId == 0);
            }
            return await tempquery
                .OrderBy(x => x.SortCode, OrderByType.Asc)
                .ToListAsync();
        }

        /// <summary>
        /// 类型信息修改
        /// </summary>
        /// <param name="model"></param>
        /// <returns></returns>
        public async Task<ResultInfo> SubmitTypeAsync(SecInfoTypeCS2Dto model)
        {
            model.Remark = model.Remark.ToStr();
            if (model.Id > 0)
            {
                if (!await dbClient.Queryable<YB_SecInfoType>().AnyAsync(x => x.Id == model.Id))
                {
                    return new ResultInfo(ResultState.FAIL, "记录未找到");
                }
                await dbClient.Updateable<YB_SecInfoType>().SetColumns(x => new YB_SecInfoType
                {
                    Name = model.Name,
                    SortCode = model.SortCode,
                    Remark = model.Remark
                }).Where(x => x.Id == model.Id).ExecuteCommandAsync();
                return new ResultInfo(ResultState.SUCCESS, "修改成功");
            }
            else
            {
                await dbClient.Insertable(new YB_SecInfoType
                {
                    Name = model.Name,
                    CreateTime = DateTime.Now,
                    Status = StatusType.Enabled,
                    SortCode = model.SortCode,
                    Remark = model.Remark,
                    BusienssId = currentUser.BusinessId
                }).ExecuteCommandAsync();
                return new ResultInfo(ResultState.SUCCESS, "添加成功");
            }
        }
        /// <summary>
        /// 类型状态修改
        /// </summary>
        /// <param name="id">记录ID</param>
        /// <param name="status">状态</param>
        /// <returns></returns>
        public async Task<ResultInfo> SetTypeStatusAsync(int id, StatusType status)
        {
            if (!await repository.Change<YB_SecInfoType>().Context.Queryable<YB_SecInfoType>().AnyAsync(x => x.Id == id))
            {
                return new ResultInfo(ResultState.FAIL, "记录未找到");
            }
            //更新状态
            await repository.Change<YB_SecInfoType>().Context.Updateable<YB_SecInfoType>().SetColumns(x => new YB_SecInfoType
            {
                Status = status
            }).Where(x => x.Id == id).ExecuteCommandAsync();
            return new ResultInfo(ResultState.SUCCESS, "状态更新成功");
        }
        /// <summary>
        /// 类型详情
        /// </summary>
        /// <param name="id"></param>
        /// <returns></returns>
        public async Task<YB_SecInfoType> DetailTypeAsync(int id)
        {
            return await repository.Change<YB_SecInfoType>().Context.Queryable<YB_SecInfoType>().Where(x => x.Id == id).FirstAsync();
        }
    }
}
