using System;
using System.Collections.Generic;
using System.Threading;
using System.Linq;
using System.Data;
using MySystem;
using MySystem.PxcModels;
using Library;
using LitJson;

public class VirtualApplyHelper
{
    public readonly static VirtualApplyHelper Instance = new VirtualApplyHelper();
    private VirtualApplyHelper()
    {
    }

    public void Start()
    {
        Thread th = new Thread(StartDo);
        th.IsBackground = true;
        th.Start();
    }

    private void StartDo()
    {
        while (true)
        {
            try
            {
                string data = RedisDbconn.Instance.RPop<string>("VirtualApplyQueue");
                if(!string.IsNullOrEmpty(data))
                {
                    TransferOneDo(data);
                }
                else
                {
                    Thread.Sleep(5000);
                }
            }
            catch (Exception ex)
            {
                Utils.WriteLog(DateTime.Now.ToString() + "\n" + ex.ToString(), "申请虚拟卡异常");
            }
        }
    }

    public void TransferOneDo(string value)
    {
        WebCMSEntities maindb = new WebCMSEntities();
        JsonData data = JsonMapper.ToObject(value);
        int OrderId = int.Parse(function.CheckInt(data["OrderId"].ToString()));
        int StoreId = int.Parse(function.CheckInt(data["StoreId"].ToString())); //仓库
        int ToUserId = int.Parse(function.CheckInt(data["ToUserId"].ToString())); //收货人
        int SnCount = int.Parse(function.CheckInt(data["SnCount"].ToString()));
        Dictionary<string, object> Obj = new Dictionary<string, object>();
        StoreHouse store = maindb.StoreHouse.FirstOrDefault(m => m.Id == StoreId) ?? new StoreHouse();

        string SnNos = ""; //划拨的机具号（多个）
        Orders order = maindb.Orders.FirstOrDefault(m => m.Id == OrderId);
        if (order != null)
        {
            if (order.Status == 2)
            {
                return;
            }
            int ApplyType = 0; // 申请类型，1-机具SN，2-200兑换码，3-300券
            List<string> SourceSnNos = new List<string>();
            if (order.Sort > 0)
            {
                MachineApply Apply = maindb.MachineApply.FirstOrDefault(m => m.Id == order.Sort);
                if (Apply != null)
                {
                    Apply.Status = 1;
                    Apply.QueryCount = order.Id;
                    ApplyType = Apply.Sort;
                    if (!string.IsNullOrEmpty(Apply.SwapSnExpand))
                    {
                        string[] SwapSnExpands = Apply.SwapSnExpand.Split('\n');
                        foreach (string sub in SwapSnExpands)
                        {
                            if (!string.IsNullOrEmpty(sub))
                            {
                                SourceSnNos.Add(sub.Split(':')[0]);
                            }
                        }
                    }
                }
            }
            Dictionary<int, string> couponIds = new Dictionary<int, string>();
            int SnIndex = 0;
            List<PosMachinesTwo> PosList = maindb.PosMachinesTwo.Where(m => m.BrandId == 14 && m.StoreId == 8664 && m.BuyUserId == 0 && m.BindingState == 0 && m.ActivationState == 0).Take(SnCount).ToList();
            foreach (PosMachinesTwo pos in PosList)
            {
                string ChangeNo = "SC" + DateTime.Now.ToString("yyyyMMddHHmmssfff") + function.get_Random(8);
                int SnIdNum = pos.Id;
                DateTime RecycEndDate = DateTime.Now.AddDays(360);
                int LeaderUserId = 0;
                int BigPosCouponKind = 0;
                if (SourceSnNos.Count > SnIndex)
                {
                    string SourceSnNo = SourceSnNos[SnIndex];
                    if (ApplyType <= 1)
                    {
                        MachineForSnNo forSnNo = maindb.MachineForSnNo.FirstOrDefault(m => m.SnNo == SourceSnNo) ?? new MachineForSnNo();
                        PosMachinesTwo spos = maindb.PosMachinesTwo.FirstOrDefault(m => m.Id == forSnNo.SnId) ?? new PosMachinesTwo();
                        RecycEndDate = spos.RecycEndDate == null ? RecycEndDate = DateTime.Now.AddDays(360) : spos.RecycEndDate.Value;
                        LeaderUserId = spos.LeaderUserId;
                        BigPosCouponKind = spos.OpId;
                        if(BigPosCouponKind == 0)
                        {
                            KqProducts brand = maindb.KqProducts.FirstOrDefault(m => m.Id == spos.BrandId) ?? new KqProducts();
                            BigPosCouponKind = brand.Kind;
                        }
                    }
                    else if (ApplyType > 1)
                    {
                        PosCoupons coupon = maindb.PosCoupons.FirstOrDefault(m => m.ExchangeCode == SourceSnNo) ?? new PosCoupons();
                        LeaderUserId = coupon.LeaderUserId;
                        BigPosCouponKind = coupon.QueryCount;
                        if (coupon.OpId > 0)
                        {
                            if (couponIds.ContainsKey(coupon.OpId))
                            {
                                string[] datas = couponIds[coupon.OpId].Split(',');
                                int Num = int.Parse(datas[2]) + 1;
                                couponIds[coupon.OpId] = datas[0] + "," + datas[1] + "," + Num;
                            }
                            else
                            {
                                couponIds.Add(coupon.OpId, coupon.Id + "," + coupon.QueryCount + ",1");
                            }
                        }
                    }
                }

                if (StoreId == 0)
                {
                    StoreId = pos.StoreId;
                }
                SnNos += pos.PosSn + ",";
                Users toUser = maindb.Users.FirstOrDefault(m => m.Id == ToUserId) ?? new Users();
                StoreStockChange query = maindb.StoreStockChange.Add(new StoreStockChange()
                {
                    CreateDate = DateTime.Now,
                    StoreId = StoreId, //仓库
                    BrandId = pos.BrandId, //产品类型
                    ProductName = RelationClass.GetKqProductBrandInfo(pos.BrandId), //产品名称
                    ChangeNo = ChangeNo, //变更单号
                    TransType = 11, //交易类型
                    SnNo = pos.PosSn, //SN编号
                    SnType = pos.PosSnType, //SN机具类型
                    StockOpDirect = 1, //库存操作方向
                    DeviceType = pos.DeviceType, //设备类型
                    FromUserId = store.UserId, //出货人
                    FromDate = DateTime.Now, //出库时间
                    ToUserId = ToUserId, //收货人
                    ToStoreId = StoreId, //退货收货仓库
                    OpId = pos.OpId
                }).Entity;
                UserStoreChange userstore = maindb.UserStoreChange.Add(new UserStoreChange()
                {
                    CreateDate = DateTime.Now,
                    UserId = store.UserId, //创客
                    BrandId = pos.BrandId, //产品类型
                    ChangeRecordNo = ChangeNo, //变更记录单号
                    TransType = 0, //交易类型
                    SnNo = pos.PosSn, //SN编号
                    SnType = pos.PosSnType, //SN机具类型
                    StockOpDirect = 0, //库存操作方向
                    DeviceVendor = pos.DeviceName, //设备厂商
                    DeviceType = pos.DeviceKind, //设备类型
                    DeviceModel = pos.DeviceType, //设备型号
                    ToUserId = ToUserId, //收货创客
                    ToDate = DateTime.Now, //入库时间
                    SourceStoreId = pos.SourceStoreId, //源仓库
                    SnStatus = 1, //SN状态
                    BindStatus = (int)pos.BindingState, //绑定状态
                    BindMerchantId = pos.BindMerchantId, //绑定商户
                    ActiveStatus = (int)pos.ActivationState, //激活状态
                    ActRewardUserId = pos.BuyUserId, //激活奖励创客
                    BrandType = pos.DeviceType, //品牌类型
                }).Entity;
                StoreChangeHistory history = maindb.StoreChangeHistory.Add(new StoreChangeHistory()
                {
                    CreateDate = DateTime.Now,
                    UserId = store.UserId, //创客
                    BrandId = pos.BrandId, //产品类型
                    ChangeRecordNo = ChangeNo, //变更记录单号
                    TransType = 2, //交易类型
                    SnNo = pos.PosSn, //SN编号
                    SnType = pos.PosSnType, //SN机具类型
                    StockOpDirect = 1, //库存操作方向
                    DeviceVendor = pos.DeviceName, //设备厂商
                    DeviceModel = pos.DeviceKind, //设备型号
                    DeviceType = pos.DeviceType, //设备类型
                    ToUserId = ToUserId, //收货创客
                    FromUserId = store.UserId, //出货创客
                    FromDate = DateTime.Now, //出库时间
                    SourceStoreId = pos.SourceStoreId, //源仓库
                    StoreId = store.Id, //仓库
                    OpId = pos.OpId
                }).Entity;
                maindb.SaveChanges();
                PublicFunction.StatUserMachineData(ToUserId, pos.BrandId, 1);
                store.LaveNum -= 1;
                store.OutNum += 1;

                PosMachinesTwo editPos = maindb.PosMachinesTwo.FirstOrDefault(m => m.Id == pos.Id);
                if(editPos != null)
                {
                    pos.OrderId = OrderId;
                    pos.BuyUserId = ToUserId;
                    pos.UserId = ToUserId;
                    pos.TransferTime = DateTime.Now;
                    pos.RecycEndDate = RecycEndDate; // 循环结束时间
                    pos.PosSnType = order.QueryCount;
                    pos.LeaderUserId = LeaderUserId;
                    pos.OpId = BigPosCouponKind;
                }
                
                maindb.SaveChanges();
                SnIndex += 1;

            }
            order.Status = 2;
            order.SendStatus = 1;
            order.SendDate = DateTime.Now;
            order.SnNos = SnNos.TrimEnd(',');
            maindb.SaveChanges();
        }
        maindb.Dispose();
    }
}