/// 
///LOGIC CLASS FOR TABLE t_Lot
///By wm with codesmith. 
///on 08/03/2018
/// 
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using DeiNiu.wms.Data.Model;
using System.Data;
using System.Transactions;
using DeiNiu.Utils;
namespace DeiNiu.wms.Logical
{
    [Serializable]
    public class lLot   :lbase
    {
        Lot _obj;
        public lLot()
        {
             initialize();
        }
       
        public  Lot  LotObj
        {
            get
            {
             if (_obj == null)
                {
                    _obj = new Lot();
                   
                } 
                _obj.operater = operId;
                return _obj;
            }
        }
        LotAtt _lotAtt;
        public LotAtt lotAtt
        {
            get
            {
                if (_lotAtt == null)
                {
                    _lotAtt = new LotAtt();
                }
                _lotAtt.operater = operId;
                return _lotAtt;
            }
        }
        Sku _sku; 
        public Sku skuObj
        {
            get
            {
                if (_sku == null)
                {
                    _sku = new Sku();
                }
                _sku.operater = operId;
                return _sku;
            }
        }
        
       public lLot(int operId)
            : base(operId)
        {
            initialize();
        }
        
  
		/// 
		/// get all data
		/// 
        public DataSet getAllData()
        {
           return _obj.Query();
        }
        /// 
        /// get all data
        /// 
        public DataSet getAllActiveData()
        {
            return _obj.QueryActived();
        }
		/// 
		/// get a record by id
		/// 
        public void initialize(int id)
		{
            _obj = id != 0 ? new Lot(id) : new Lot();
		}
        /// 
		/// get a record by id 0
		/// 
        public void initialize()
        {
            initialize(0);
        }
         /// 
        /// get a record by id
        /// 
        public void initialize(DataRow dr)
        {
            _obj =   new Lot(dr);
        }
        internal DataTable getLotGoodsType(int lotId)
        {
            return _obj.getLotGoodsType(lotId);
        }
        internal DataTable getFreeGoodsType()
        {
          return _obj.getFreeGoodsType();
        }
        internal bool newGoodTypeLot(int[] goodsType, int lotId)
        {
           GoodTypeLot gl = new GoodTypeLot();
            foreach(int i in goodsType)
            {
                gl.goodsType=i;
                gl.lotId = lotId;
                gl.Add();
            }
            return true;
        }
        internal bool deleteGoodsTypeLot(int id)
        {
            GoodTypeLot gl = new GoodTypeLot(id);
            return gl.Delete() > 0;
        }
        protected override DeiNiu.Data.BaseObject.BaseModel getModel()
        {
            return _obj;
        }
 
        //begin cust db operation, query, excute sql etc.
        
     
        /// 
        /// update in a transaction scrop
        /// 
        public void update()
        {
            if (valid())
            {
                using (TransactionScope scope = new TransactionScope())
                {
 
                    _obj.Update();
                    scope.Complete();
                }
            }
        }
        
         private bool valid()
        {
            return true;
        }
         
         internal int newLot(Data.Model.Lot lot)
         {
             int id = lot.Add();
             if (id <= 0)
             {
                 return -1;
             }
             LotAtt la = new LotAtt();
             la.lotId = id;
             la.operater = operId;
             la.attName = WmsConstants.SKU_RESEVRED_BATCH_ATTNAME;  
             la.attType = 0;           
             la.Add();
             la.attName = WmsConstants.SKU_RESEVRED_PRDDATE_ATTNAME;
             la.attType = 2; 
             la.Add();
             la.attName = WmsConstants.SKU_RESEVRED_EXPIREDATE_ATTNAME;  
             la.attType = 2;
             la.Add();
             return id;
         }
         internal  DataTable getLotAtts(string goodsId)
         {
             return lotAtt.getAttByGoodId(goodsId);
           //  WmsGoods goods = new WmsGoods(goodsId);
           // return lotAtt.queryByLotId(goods.lotId); 
             
         }
       //  internal Dictionary  getSKU(Dictionary skuValues, string goodsId)
        internal Dictionary getSKU(string prdDate, string goodsId, string batch  )
        {
            Dictionary skuValues = getSku(prdDate, goodsId, batch); 
            WmsGoods wg = new WmsGoods(goodsId);
            log.Debug( string.Format(" to get goodsId sku of {0}, expireDays {1}" , goodsId,wg.expiryDays));
           
            string skuCode = "";
             int lotId = 0;
             DataTable lotAtts = getLotAtts(goodsId);
             LotAtt la;
            if (wg.expiryDays > 0)
            {
                foreach (DataRow dr in lotAtts.Rows)
                {
                    la = new LotAtt(dr);
                    if (skuValues.Keys.Contains(la.attName))
                    {
                        skuCode += string.Format("{0}:{1};", la.attName, skuValues[la.attName]);
                    }
                }
            }
             
             Dictionary dic = new Dictionary();
           
            skuCode = string.Format("{0}:{1};", "goodsId", goodsId) + skuCode;
           
           
             int pjCount = lotAtts.Rows.Count;
               
            log.Debug(string.Format("sku lot att count {0},getSKU sku code {1}",pjCount, skuCode ));
             if (pjCount == 0) //没有批次定义
             {
                 return dic;
             }
             else
             {
                 lotId =  Convert.ToInt32(lotAtts.Rows[0]["lotId"].ToString());
             }
            log.Debug(string.Format("lot id {0} ", lotId));
        
             int skuId= getSKU(skuCode, skuValues, lotId, goodsId, wg.ownerCode);
             dic[skuId] = skuCode;
             return dic;
         }
         internal int getSKU(string skuCode, Dictionary skuValues, int lotId, string goodsId, string ownerCode)
         {
           
            _sku = new Sku(skuCode);
             int skuId = 0;
            
            log.Debug(string.Format("to get sku by skucode {0} ...and skuId is {1}",  skuCode, skuObj.ID));
            if (skuObj.ID > 0)
            {
                skuId = skuObj.ID;
            }
            else
            {
                skuObj.skuCode = skuCode;
                skuObj.goodsId = goodsId;
                skuObj.lotId = lotId;
                skuObj.ownerCode = ownerCode;
                DataTable dtAtts = lotAtt.queryByLotId(lotId);
                using (TransactionScope scope = new TransactionScope())
                {
                    try
                    {
                        skuId = skuObj.Add();
                    }catch(Exception e)
                    {
                        log.Error(e);
                        log.Error(skuObj);
                    }
                    log.Debug(string.Format(" new skuId is {0}", skuId));
                    SkuValue sv = new SkuValue();
                    sv.skuId = skuId;
                    sv.operater = operId;
                    if (skuValues != null && skuValues.Count > 0)
                        foreach (string key in skuValues.Keys)
                        {
                            DataRow[] drs = dtAtts.Select("attName ='" + key + "'");
                            log.Debug(string.Format(" to get LotAtt {0},result count {1},value is {2}", "attName ='" + key + "'", drs.Length, skuValues[key]));
                            if (drs.Length > 0)
                            {
                                LotAtt la = new LotAtt(drs[0]);
                                sv.attID = la.ID;
                                log.Debug(string.Format("  sv.attID {0}", sv.attID));
                            }
                            sv.value = skuValues[key];
                            if(string.IsNullOrEmpty(sv.value))
                            {
                                throw new Exception(String.Format("入库批次信息错误,缺少 {0}", key));
                            }
                            log.Debug(string.Format(" sv.value {0}", sv.value));
                            sv.Add();
                        }
                    scope.Complete();
                }
            }
             return skuId;
         }
        Dictionary getSku(string prdDate,string goodsId,string batch)
        {
           //   DateTime pDate = Util.pareseDateString(prdDate);
            string validDate = getDateStr(getValidDate(prdDate, goodsId));
            batch = string.IsNullOrEmpty(batch) ? prdDate : batch;
            Dictionary sku = new Dictionary();
            sku[WmsConstants.SKU_RESEVRED_PRDDATE_ATTNAME] = prdDate;
            sku[WmsConstants.SKU_RESEVRED_EXPIREDATE_ATTNAME] = validDate;
            sku[WmsConstants.SKU_RESEVRED_BATCH_ATTNAME] = batch;
            return sku;
        }
    }
    
    
}