using BPA.SAAS.Manage.Application.Device.Dtos.DeviceVesion;
using BPA.SAAS.Manage.Application.Device.Interface;
using BPA.SAAS.Manage.Comm.Const;
using BPA.SAAS.Manage.Comm.Enum;
using BPA.SAAS.Manage.Core.Base;
using BPA.SAAS.Manage.Core.Device;
using BPA.SAAS.Manage.Core.Product;
using Microsoft.AspNetCore.Server.IISIntegration;
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;

namespace BPA.SAAS.Manage.Application.Device.Services
{
    public class DeviceVesionService: IDeviceVesionService, ITransient
    {
        ISqlSugarClient _db;
        public DeviceVesionService(ISqlSugarClient db)
        {
            _db=db;
        }
        /// <summary>
        /// 分页查询
        /// </summary>
        /// <param name="inputDto"></param>
        /// <returns></returns>
        public async Task<PageUtil> GetDeviceVesionPageAsync(DeviceVesionQueryInputDto inputDto)
        {
            var total = new RefAsync<int>();
            var data = await _db.Queryable<BPA_ProductVesion,BPA_Product>((a, b) => new JoinQueryInfos(JoinType.Left, b.Id == a.ProductId))
                .WhereIF(!string.IsNullOrWhiteSpace(inputDto.ProductName), (a, b) => b.Name.Contains(inputDto.ProductName))
                  .WhereIF(!string.IsNullOrWhiteSpace(inputDto.Vesion), (a, b) => a.Vesion.Contains(inputDto.Vesion))
                .OrderBy(a => a.CreateAt, OrderByType.Desc)
                .Select((a,b)=>new DeviceVesionModel()
                {
                    Id=a.Id.SelectAll(),
                    ProductName=b.Name,
                    ProductCode=b.Code,
                    ProductNumber=a.ProductNumber,
                    ProductUrl=a.ProductUrl,
                })
                .ToPageListAsync(inputDto.Current, inputDto.PageSize, total);

            return new PageUtil()
            {
                Data = data,
                Total = total

            };
        }

        /// <summary>
        /// 新增
        /// </summary>
        /// <returns></returns>
        
        public async Task<bool> AddDeviceVesionAsync(DeviceVesionBaseDto inputDto)
        {
            try
            {
                _db.Ado.BeginTran();
                var res = await _db.Insertable(new BPA_ProductVesion
                {
                    Vesion = inputDto.Vesion,
                    ProductId = inputDto.ProductId,
                    TemplatePath = inputDto.TemplatePath,
                    ProductNumber = inputDto.ProductNumber,
                    ProductUrl = inputDto.ProductUrl,
                    Status = CommonStatus.ENABLE
                }).CallEntityMethod(m => m.Create()).ExecuteReturnEntityAsync();
                var Product = _db.Queryable<BPA_Product>().Where(x => x.Id == inputDto.ProductId).First();
                #region 添加默认功能和topics
                List<BPA_ProductTopics> list = new();
                var goodspushtopics = new BPA_ProductTopics()
                {
                    Topics = " /" + Product.Key + "/" + inputDto.Vesion + "/${deviceKey}/defaul/goodspush",
                    TopicsType = TopicsTypeEnum.SUBSCRIBE,
                    Description = "商品数据下发",
                    ProductId = inputDto.ProductId,
                    ProductVesionId = res.Id,
                    Name = "商品数据下发",
                    IsDefault = true
                };
                var goodspushtopics_reply = new BPA_ProductTopics()
                {
                    Topics = " /" + Product.Key + "/" + inputDto.Vesion + "/${deviceKey}/defaul/goodspush_reply",
                    TopicsType = TopicsTypeEnum.PUBLISH,
                    Description = "响应商品数据下发",
                    ProductId = inputDto.ProductId,
                    ProductVesionId = res.Id,
                    Name = "商品数据下发",
                    IsDefault = true
                };
                var batchingpushtopics = new BPA_ProductTopics()
                {
                    Topics = " /" + Product.Key + "/" + inputDto.Vesion + "/${deviceKey}/defaul/batvhingpush",
                    TopicsType = TopicsTypeEnum.PUBLISH,
                    Description = "物料数据下发",
                    ProductId = inputDto.ProductId,
                    ProductVesionId = res.Id,
                    Name = "物料数据下发",
                    IsDefault = true
                };
                var batchingpushtopics_reply = new BPA_ProductTopics()
                {
                    Topics = " /" + Product.Key + "/" + inputDto.Vesion + "/${deviceKey}/defaul/batvhingpush_reply",
                    TopicsType = TopicsTypeEnum.SUBSCRIBE,
                    Description = "响应物料数据下发",
                    ProductId = inputDto.ProductId,
                    ProductVesionId = res.Id,
                    Name = "物料数据下发",
                    IsDefault = true
                };
                var chnologypushtopics = new BPA_ProductTopics()
                {
                    Topics = " /" + Product.Key + "/" + inputDto.Vesion + "/${deviceKey}/defaul/chnologypush",
                    TopicsType = TopicsTypeEnum.PUBLISH,
                    Description = "工艺数据下发",
                    ProductId = inputDto.ProductId,
                    ProductVesionId = res.Id,
                    Name = "工艺数据下发",
                    IsDefault = true
                };
                var chnologypushtopics_reply = new BPA_ProductTopics()
                {
                    Topics = " /" + Product.Key + "/" + inputDto.Vesion + "/${deviceKey}/defaul/chnologypush_reply",
                    TopicsType = TopicsTypeEnum.SUBSCRIBE,
                    Description = "响应工艺数据下发",
                    ProductId = inputDto.ProductId,
                    Name = "工艺数据下发",
                    ProductVesionId = res.Id,
                    IsDefault = true
                };
                list.Add(goodspushtopics);
                list.Add(goodspushtopics_reply);
                list.Add(batchingpushtopics);
                list.Add(batchingpushtopics_reply);
                list.Add(chnologypushtopics);
                list.Add(chnologypushtopics_reply);
                await _db.Insertable(list).CallEntityMethod(m => m.Create()).ExecuteCommandAsync();
                List<BPA_ProductFunction> ProductFunctionlist = new();
                var goodsProductFunction = new BPA_ProductFunction()
                {
                    Id=Guid.NewGuid().ToString(),
                    CreateAt= DateTime.Now,
                    DataType = "",
                    Type = FunctionTypeEnum.SERVER,
                    Name = "商品数据下发",
                    Description = "商品数据下发",
                    ProductId = inputDto.ProductId,
                    DeviceVersionKey = res.Id,
                    IsDefault = true
                };
                var goodsProductFunction_reply = new BPA_ProductFunction()
                {
                    Id = Guid.NewGuid().ToString(),
                    CreateAt = DateTime.Now,
                    DataType = "",
                    Type = FunctionTypeEnum.SERVER,
                    Name = "响应商品数据下发",
                    Description = "响应商品数据下发",
                    ProductId = inputDto.ProductId,
                    DeviceVersionKey = res.Id,
                    IsDefault = true
                };
                var batchingProductFunction = new BPA_ProductFunction()
                {
                    Id = Guid.NewGuid().ToString(),
                    CreateAt = DateTime.Now,
                    DataType = "",
                    Type = FunctionTypeEnum.SERVER,
                    Name = "物料数据下发",
                    Description = "物料数据下发",
                    ProductId = inputDto.ProductId,
                    DeviceVersionKey = res.Id,
                    IsDefault = true
                };
                var batchingProductFunction_reply = new BPA_ProductFunction()
                {
                    Id = Guid.NewGuid().ToString(),
                    CreateAt = DateTime.Now,
                    DataType = "",
                    Type = FunctionTypeEnum.SERVER,
                    Name = "响应物料数据下发",
                    Description = "响应物料数据下发",
                    ProductId = inputDto.ProductId,
                    DeviceVersionKey = res.Id,
                    IsDefault = true
                };
                var chnologyProductFunction = new BPA_ProductFunction()
                {
                    Id = Guid.NewGuid().ToString(),
                    CreateAt = DateTime.Now,
                    DataType = "",
                    Type = FunctionTypeEnum.SERVER,
                    Name = "工艺数据下发",
                    Description = "工艺数据下发",
                    ProductId = inputDto.ProductId,
                    DeviceVersionKey = res.Id,
                    IsDefault = true
                };
                var chnologyProductFunction_reply = new BPA_ProductFunction()
                {
                    Id = Guid.NewGuid().ToString(),
                    CreateAt = DateTime.Now,
                    DataType = "",
                    Type = FunctionTypeEnum.SERVER,
                    Name = "响应工艺数据下发",
                    Description = "响应工艺数据下发",
                    ProductId = inputDto.ProductId,
                    DeviceVersionKey = res.Id,
                    IsDefault = true
                };
                ProductFunctionlist.Add(goodsProductFunction);
                ProductFunctionlist.Add(goodsProductFunction_reply);
                ProductFunctionlist.Add(batchingProductFunction);
                ProductFunctionlist.Add(batchingProductFunction_reply);
                ProductFunctionlist.Add(chnologyProductFunction);
                ProductFunctionlist.Add(chnologyProductFunction_reply);
                await _db.Insertable(ProductFunctionlist).ExecuteCommandAsync();
                List<BPA_ProductFunctionAction> ProductFunctionActionlist = new();
                var goodsProductFunctionActionlist = new BPA_ProductFunctionAction()
                {
                    ActionType = "textareaary",
                    ProductFunctionId = goodsProductFunction.Id,
                    ActionName = "DataSoure",
                    ActionValue = "",
                    IsDefault = true
                };
                var batchingProductFunctionActionlist = new BPA_ProductFunctionAction()
                {
                    ActionType = "textareaary",
                    ProductFunctionId = batchingProductFunction.Id,
                    ActionName = "DataSoure",
                    ActionValue = "",
                    IsDefault = true
                };
                var chnologyProductFunctionActionlist = new BPA_ProductFunctionAction()
                {
                    ActionType = "textareaary",
                    ProductFunctionId = chnologyProductFunction.Id,
                    ActionName = "DataSoure",
                    ActionValue = "",
                    IsDefault = true
                };
                var goodsProductFunctionActionlist_reply = new BPA_ProductFunctionAction()
                {
                    ActionType = "textareaary",
                    ProductFunctionId = goodsProductFunction_reply.Id,
                    ActionName = "DataSoure",
                    ActionValue = "",
                    IsDefault = true
                };
                var batchingProductFunctionActionlist_reply = new BPA_ProductFunctionAction()
                {
                    ActionType = "textareaary",
                    ProductFunctionId = batchingProductFunction_reply.Id,
                    ActionName = "DataSoure",
                    ActionValue = "",
                    IsDefault = true
                };
                var chnologyProductFunctionActionlist_reply = new BPA_ProductFunctionAction()
                {
                    ActionType = "textareaary",
                    ProductFunctionId = chnologyProductFunction_reply.Id,
                    ActionName = "DataSoure",
                    ActionValue = "",
                    IsDefault = true
                };
                ProductFunctionActionlist.Add(goodsProductFunctionActionlist);
                ProductFunctionActionlist.Add(batchingProductFunctionActionlist);
                ProductFunctionActionlist.Add(chnologyProductFunctionActionlist);
                ProductFunctionActionlist.Add(goodsProductFunctionActionlist_reply);
                ProductFunctionActionlist.Add(batchingProductFunctionActionlist_reply);
                ProductFunctionActionlist.Add(chnologyProductFunctionActionlist_reply);
                await _db.Insertable(ProductFunctionActionlist).CallEntityMethod(m => m.Create()).ExecuteCommandAsync();
                #endregion
                _db.Ado.CommitTran();
                return res != null;
            }
            catch (Exception e)
            {
                _db.Ado.RollbackTran();
                throw Oops.Oh("添加失败，失败信息："+e.Message);
            }
        }
        /// <summary>
        /// 删除
        /// </summary>
        /// <param name="inputList"></param>
        /// <returns></returns>
        public async Task<bool> DelDeviceVesionAsync(List<string> inputList)
        {
            try
            {
                _db.Ado.BeginTran();
                var data = await _db.Queryable<BPA_DeviceInfo>().Where(x => inputList.Contains(x.ProductVersionId)).ToListAsync();
                if (data.Count > 0)
                {
                    throw Oops.Oh("当前版本已有设备使用，无法删除");
                }
                var datas = await _db.Queryable<BPA_ProductVesion>()
                    .Where(x => inputList.Contains(x.Id))
                    .ToListAsync();
                var ProductFunctions = await _db.Queryable<BPA_ProductFunction>()
                  .Where(x => inputList.Contains(x.DeviceVersionKey))
                  .ToListAsync();
                var ProductTopics = await _db.Queryable<BPA_ProductTopics>()
                .Where(x => inputList.Contains(x.ProductVesionId))
                .ToListAsync();
                _db.Deleteable(ProductTopics).ExecuteCommand();//删除相关topic
                _db.Deleteable(ProductFunctions).ExecuteCommand();//删除相关服务和功能
                var res=await _db.Deleteable(datas).ExecuteCommandAsync();
                _db.Ado.CommitTran();
                return res>0;
            }
            catch (Exception e)
            {
                _db.Ado.RollbackTran();
                throw Oops.Oh("删除失败，失败信息："+e.Message);
            }
           
        }
        /// <summary>
        /// 修改
        /// </summary>
        /// <returns></returns>
        public async Task<bool> UpdateDeviceVesionAsync(DeviceVesionBaseDto inputDto)
        {
            var data = await _db.Queryable<BPA_ProductVesion>().Where(x => x.Id == inputDto.Id).FirstAsync();

            if (data != null)
            {
                var res = _db.Updateable<BPA_ProductVesion>().SetColumns(t => t.Vesion == inputDto.Vesion)
                     .SetColumns(t => t.TemplatePath == inputDto.TemplatePath)
                     .SetColumns(t => t.ProductNumber == inputDto.ProductNumber)
                     .SetColumns(t => t.ProductUrl == inputDto.ProductUrl)
                     .SetColumns(t => t.ProductId == inputDto.ProductId)
                     .SetColumns(t => t.Status == (CommonStatus)inputDto.Status).Where(t => t.Id == inputDto.Id)
                     .ExecuteCommandHasChange();

                return res;
            }

            return false;
        }
        /// <summary>
        /// 更新状态
        /// </summary>
        /// <param name="inputDto"></param>
        /// <returns></returns>
        public async Task<bool> UpdateDeviceVesionSatatus(DeviceVesionSatatusDto inputDto)
        {
            var data = await _db.Queryable<BPA_ProductVesion>().Where(x => x.Id == inputDto.Id).FirstAsync();

            if (data != null)
            {
                var res = _db.Updateable<BPA_ProductVesion>()
                     .SetColumns(t => t.Status == (CommonStatus)inputDto.Status).Where(t => t.Id == inputDto.Id)
                     .ExecuteCommandHasChange();

                return res;
            }

            return false;
        }
        /// <summary>
        /// 根据产品查询版本
        /// </summary>
        /// <param name="Code"></param>
        /// <returns></returns>
        public async Task<List<BPA_ProductVesion>> GetDeviceVesion(string ProductId)
        {
            var resEntity =await _db.Queryable<BPA_ProductVesion>().Where(a => a.ProductId == ProductId && a.Status==0).Select(a => new BPA_ProductVesion() { Id = a.Id.SelectAll() }).ToListAsync();
            return resEntity;
        }
        /// <summary>
        /// 查询版本列表
        /// </summary>
        /// <returns></returns>
        public async Task<List<BPA_ProductVesion>> GetDeviceVesionList()
        {
            var resEntity =await _db.Queryable<BPA_ProductVesion>()
                .Select(a => new BPA_ProductVesion() { Id = a.Id.SelectAll() })
                .ToListAsync();
            return resEntity;
        }
    }
}
