/// <summary> /// 从淘宝中间表生成系统订单 /// </summary> /// <param name="organ"></param> /// <param name="channel"></param> /// <see cref=""/> /// <returns>0转换成功,数值表示失败计数</returns> public int GenerateOrderFromTaobao(MemberOrganization organ, MemberChannel channel) { string strUserPrefix = Utility.ConfigHelper.GlobalConst.GetSetting("TaobaoUserPrefix"); int nFailCount = 0; // 转换失败计数器 string strFailTids = ""; var oTbOrders = (from o in dbEntity.ExTaobaoOrders.Include("TaobaoOrderItems") where o.Transfered == false && o.status == "WAIT_SELLER_SEND_GOODS" && o.OrgID == organ.Gid && o.ChlID == channel.Gid select o).ToList(); foreach (var oTrade in oTbOrders) { try { // 创建数据库事务 using (var scope = new TransactionScope()) { string strTid = oTrade.tid.ToString(); var oOrder = (from o in dbEntity.OrderInformations where o.OrgID == organ.Gid && o.ChlID == channel.Gid && o.LinkCode == strTid select o).FirstOrDefault(); bool bSuccess = false; if (oOrder == null) { // 查询和新建用户 string strLoginName = strUserPrefix + oTrade.buyer_nick; var oUser = (from u in dbEntity.MemberUsers where u.LoginName == strLoginName select u).FirstOrDefault(); if (oUser == null) { oUser = new MemberUser { Organization = organ, Role = dbEntity.MemberRoles.Where(r => r.OrgID == organ.Gid && r.Code == "Public").FirstOrDefault(), Channel = channel, LoginName = strLoginName, Ustatus = (byte)ModelEnum.UserStatus.VALID, NickName = oTrade.buyer_nick, DisplayName = oTrade.buyer_nick, Passcode = String.IsNullOrEmpty(oTrade.receiver_mobile) ? oTrade.receiver_phone : oTrade.receiver_mobile, Culture = dbEntity.GeneralCultureUnits.Where(c => c.Culture == 2052).FirstOrDefault(), Email = oTrade.buyer_email }; } // 匹配地区 var oLocation = (from r in dbEntity.GeneralRegions where r.Code == "CHN" // 中国 select r).FirstOrDefault(); var oProvince = (from r in dbEntity.GeneralRegions where r.Parent.Code == "CHN" && (r.ShortName == oTrade.receiver_state || r.Map01 == oTrade.receiver_state) select r).FirstOrDefault(); if (oProvince != null) { oLocation = oProvince; // 匹配到省 var oCity = (from r in dbEntity.GeneralRegions where r.aParent == oProvince.Gid && (r.ShortName == oTrade.receiver_city || r.Map01 == oTrade.receiver_city) select r).FirstOrDefault(); if (oCity != null) { oLocation = oCity; // 匹配到市 var oDistrict = (from r in dbEntity.GeneralRegions where r.aParent == oCity.Gid && (r.ShortName == oTrade.receiver_district || r.Map01 == oTrade.receiver_district) select r).FirstOrDefault(); if (oDistrict != null) oLocation = oDistrict; // 匹配到区 } } // 支付方式 -- 支付宝 var oPayType = (from p in dbEntity.FinancePayTypes where p.Deleted == false && p.OrgID == organ.Gid && p.Code == "alipay" select p).FirstOrDefault(); // 货币 -- 人民币 var oCurrency = (from u in dbEntity.GeneralMeasureUnits where u.Deleted == false && u.Code == "¥" && u.Utype == (byte)ModelEnum.MeasureUnit.CURRENCY select u).FirstOrDefault(); // 创建订单主表 oOrder = new OrderInformation { Organization = organ, Channel = channel, User = oUser, LinkCode = strTid, Ostatus = (byte)ModelEnum.OrderStatus.NONE, TransType = (oTrade.type == "cod") ? (byte)ModelEnum.TransType.COD : (byte)ModelEnum.TransType.SECURED, PayType = oPayType, PayNote = oTrade.alipay_no, // Pieces = oTrade.num, Currency = oCurrency, SaleAmount = Decimal.Parse(oTrade.total_fee), // ExecuteAmount = Decimal.Parse(oTrade.payment) - Decimal.Parse(oTrade.post_fee), ShippingFee = Decimal.Parse(oTrade.post_fee), MoneyPaid = Decimal.Parse(oTrade.payment), // Differ = 0, PaidTime = new DateTimeOffset(oTrade.pay_time.Value, TimeZone.CurrentTimeZone.GetUtcOffset(DateTime.Now)), Consignee = oTrade.receiver_name, Location = oLocation, FullAddress = oTrade.receiver_state + oTrade.receiver_city + oTrade.receiver_district + oTrade.receiver_address, PostCode = oTrade.receiver_zip, Telephone = oTrade.receiver_phone, Mobile = oTrade.receiver_mobile, Email = oTrade.buyer_email, PostComment = oTrade.buyer_memo, LeaveWord = oTrade.seller_memo }; // 子订单实付金额。精确到2位小数,单位:元。如:200.07,表示:200元7分。计算公式如下:payment = price * num + adjust_fee - discount_fee + post_fee // (邮费,单笔子订单时子订单实付金额包含邮费,多笔子订单时不包含邮费); // 对于退款成功的子订单,由于主订单的优惠分摊金额,会造成该字段可能不为0.00元。建议使用退款前的实付金额减去退款单中的实际退款金额计算。 bool bSingleProduct = (oTrade.TaobaoOrderItems.Count() == 1); decimal nTotalQty = 0m; // 商品总数量,标准计量单位 decimal nItemAmount = 0m; // 商品总金额 // 创建订单从表 foreach (var item in oTrade.TaobaoOrderItems) { // 先找OnSale.Code确定是否为pu-parts模式,SKU号对应不上时,必须判断转换失败 var oParts = (from s in dbEntity.ProductOnSales.Include("Product") where s.Deleted == false && s.OrgID == organ.Gid && s.ChlID == channel.Gid && s.Code == item.outer_sku_id && s.Mode == (byte)ModelEnum.ProductMode.PU_PARTS orderby s.Ostatus descending select s).FirstOrDefault(); if (oParts == null) { // PU-SKU 模式,只导入一个OnItem加入订单 var oOnSku = (from s in dbEntity.ProductOnItems.Include("SkuItem").Include("OnSale") where s.OnSale.Deleted == false && s.Deleted == false && s.OnSale.Mode == (byte)ModelEnum.ProductMode.PU_SKU && s.OnSale.OrgID == organ.Gid && s.OnSale.ChlID == channel.Gid && s.SkuItem.Code == item.outer_sku_id orderby s.OnSale.Ostatus descending, s.OnSale.CreateTime descending select s).FirstOrDefault(); var oOnPrice = (from p in dbEntity.ProductOnUnitPrices.Include("MarketPrice").Include("SalePrice") where p.Deleted == false && p.OnSkuID == oOnSku.Gid // oOnSku空,则直接到catch记录错误 orderby p.IsDefault descending, p.CreateTime descending select p).FirstOrDefault(); // 计量单位转换,进位法 decimal nQuantity = Decimal.Parse(item.num.ToString()); decimal nPercent = Decimal.Parse("1" + new string('0', oOnPrice.Percision)); nQuantity = Math.Ceiling(nQuantity * oOnPrice.UnitRatio * nPercent) / nPercent; decimal nPayment = Decimal.Parse(item.payment); // 单笔子订单时子订单实付金额包含邮费,多笔子订单时不包含邮费 if (bSingleProduct) nPayment -= oOrder.ShippingFee; OrderItem oOrderItem = new OrderItem { OnSkuItem = oOnSku, SkuItem = oOnSku.SkuItem, Name = item.title, Quantity = nQuantity, MarketPrice = oOnPrice.MarketPrice.GetResource(oOrder.Currency.Gid), SalePrice = oOnPrice.SalePrice.GetResource(oOrder.Currency.Gid), ExecutePrice = Math.Round(nPayment / nQuantity, 2), Remark = String.Format("淘宝:{0} | {1} | {2} | {3}", item.num, item.payment, item.discount_fee, item.adjust_fee) }; // 统计与误差计算 nTotalQty += nQuantity; nItemAmount += oOrderItem.ExecutePrice * nQuantity; oOrder.OrderItems.Add(oOrderItem); } else { // PU-Parts模式,需要将所有OnItem加入订单,只第一个商品有价格,其他商品价格为零 var oPartItems = (from i in dbEntity.ProductOnItems.Include("SkuItem").Include("OnSale") where i.Deleted == false && i.OnSaleID == oParts.Gid select i).ToList(); bool bIsFirst = true; decimal nQuantity = Decimal.Parse(item.num.ToString()); decimal nPayment = Decimal.Parse(item.payment); // 单笔子订单时子订单实付金额包含邮费,多笔子订单时不包含邮费 if (bSingleProduct) nPayment -= oOrder.ShippingFee; foreach (var oOnSku in oPartItems) { var oOnPrice = (from p in dbEntity.ProductOnUnitPrices.Include("MarketPrice").Include("SalePrice") where p.Deleted == false && p.OnSkuID == oOnSku.Gid // oOnSku空,则直接到catch记录错误 orderby p.IsDefault descending select p).FirstOrDefault(); // decimal nItemQty = oOnSku.SetQuantity * nQuantity; // 不使用套装数量,使用转换算法 // 计量单位转换,进位法 decimal nPercent = Decimal.Parse("1" + new string('0', oOnPrice.Percision)); decimal nItemQty = Math.Ceiling(nQuantity * oOnPrice.UnitRatio * nPercent) / nPercent; OrderItem oOrderItem = new OrderItem { OnSkuItem = oOnSku, SkuItem = oOnSku.SkuItem, Name = oOnSku.FullName.GetResource(2052), Quantity = nItemQty, MarketPrice = oOnPrice.MarketPrice.GetResource(oOrder.Currency.Gid), SalePrice = oOnPrice.SalePrice.GetResource(oOrder.Currency.Gid), ExecutePrice = (bIsFirst) ? Math.Round(nPayment / nItemQty, 2) : 0m, // 第一个商品有价格,其他商品没有价格 Remark = String.Format("淘宝:{0} | {1} | {2} | {3} | {4}", item.title, item.num, item.payment, item.discount_fee, item.adjust_fee) }; // 统计与误差计算 nTotalQty += nItemQty; nItemAmount += oOrderItem.ExecutePrice * nItemQty; oOrder.OrderItems.Add(oOrderItem); bIsFirst = false; } } } oOrder.Pieces = nTotalQty; oOrder.ExecuteAmount = nItemAmount; oOrder.Differ = oOrder.MoneyPaid - oOrder.ShippingFee - nItemAmount; // 误差 dbEntity.OrderInformations.Add(oOrder); dbEntity.SaveChanges(); // 更新淘宝订单转换成功状态 oTrade.OrderID = oOrder.Gid; oTrade.Transfered = true; dbEntity.SaveChanges(); // 创建已收款记录 FinancePayment oFinance = new FinancePayment { Organization = organ, PayTo = (byte)ModelEnum.PayDirection.TO_CORPBANK, Pstatus = (byte)ModelEnum.PayStatus.PAID, RefType = (byte)ModelEnum.NoteType.ORDER, RefID = oOrder.Gid, Reason = String.Format("支付宝:{0}", oTrade.alipay_no), PayDate = new DateTimeOffset(oTrade.pay_time.Value, TimeZone.CurrentTimeZone.GetUtcOffset(DateTime.Now)), Currency = oOrder.Currency, Amount = oOrder.MoneyPaid, Remark = String.Format("淘宝订单:{0}", oTrade.tid) }; dbEntity.FinancePayments.Add(oFinance); // 索取发票 if (!String.IsNullOrEmpty(oTrade.invoice_name)) { FinanceInvoice oInvoice = new FinanceInvoice { OrderInfo = oOrder, Code = oOrder.Gid.ToString("N"), Title = oTrade.invoice_name, Amount = oOrder.MoneyPaid }; dbEntity.FinanceInvoices.Add(oInvoice); } dbEntity.SaveChanges(); bSuccess = true; } else { // TODO Warning nFailCount++; strFailTids += String.Format("{0},", oTrade.tid); } scope.Complete(); if (bSuccess) { oEventBLL.WriteEvent(String.Format("淘宝订单转换成功: {0}, {1}", oOrder.Code, oTrade.tid), ModelEnum.ActionLevel.GENERIC, ModelEnum.ActionSource.ORDER, this.ToString()); } } } catch { nFailCount++; strFailTids += String.Format("{0},", oTrade.tid); } } if (nFailCount > 0) { oEventBLL.WriteEvent(String.Format("淘宝订单转换失败: {0}", strFailTids), ModelEnum.ActionLevel.ERROR, ModelEnum.ActionSource.ORDER, this.ToString()); } return nFailCount; }
/// <summary> /// 保存添加的发票 /// </summary> /// <param name="NewInvoice"></param> public void SaveNewInvoice(FinanceInvoice NewInvoice) { try { var orderId = NewInvoice.OrderInfo.Code; OrderInformation oOrder = dbEntity.OrderInformations.Where(o => o.Code == orderId).Single(); NewInvoice.OrderInfo = oOrder; dbEntity.FinanceInvoices.Add(NewInvoice); dbEntity.SaveChanges(); } catch (Exception ex) { RedirectToAction("ErrorPage", "Home", new { message = ex.Message }); } }
/// <summary> /// 用户确认订单 /// </summary> /// <param name="formCollection"></param> /// <returns></returns> public string SaveNewOrder(FormCollection formCollection) { string strReturnInfo = "success"; //检查收货人信息是否存在 if (oNewOrder.aLocation == null || oNewOrder.aLocation.Equals(Guid.Empty)) { strReturnInfo = "请选择收货人信息!"; return strReturnInfo; } //检查承运商信息是否存在 if (globalShipperGid == null || globalShipperGid.Equals(Guid.Empty)) { strReturnInfo = "请选择承运商!"; return strReturnInfo; } #region 提交订单的信息 OrderInformation oConfirmOrder = new OrderInformation(); //订单基本信息 oConfirmOrder.OrgID = oNewOrder.OrgID; oConfirmOrder.ChlID = oNewOrder.ChlID; //计算出最佳仓库 var bestWhID = dbEntity.Database.SqlQuery<Guid>("SELECT dbo.fn_FindBestWarehouse({0}, {1}, {2})", oNewOrder.OrgID, oNewOrder.ChlID, oNewOrder.aLocation).FirstOrDefault(); oConfirmOrder.WhID = bestWhID; oConfirmOrder.UserID = oNewOrder.UserID; oConfirmOrder.DocVersion = 0; oConfirmOrder.aCurrency = globalCurrencyGid; //交易类型 oConfirmOrder.TransType = byte.Parse(formCollection["TransType"]); //当前订单是货到付款,则不需要检查支付方式;否则检查用户是否选择支付方式 if (oConfirmOrder.TransType != (byte)ModelEnum.TransType.COD) { if (oNewOrder.PayID == null) { strReturnInfo = "请选择支付方式!"; return strReturnInfo; } else { oConfirmOrder.PayID = oNewOrder.PayID; } } oConfirmOrder.Pieces = globalOrderItemPieces; //计算商品销售总价 decimal salePriceSum = 0m; for (int i = 0; i < globalOrderItemList.Count; i++) { salePriceSum = salePriceSum + globalOrderItemList.ElementAt(i).Value.SalePrice * globalOrderItemList.ElementAt(i).Value.Quantity; } #region 订单价格信息 oConfirmOrder.SaleAmount = salePriceSum; //设定订单执行价的总和 oConfirmOrder.ExecuteAmount = globalProductExacuteAmount; oConfirmOrder.ShippingFee = oNewOrder.ShippingFee; oConfirmOrder.TaxFee = oNewOrder.TaxFee; oConfirmOrder.Insurance = oNewOrder.Insurance; oConfirmOrder.PaymentFee = oNewOrder.PaymentFee; oConfirmOrder.PackingFee = oNewOrder.PackingFee; oConfirmOrder.ResidenceFee = oNewOrder.ResidenceFee; oConfirmOrder.LiftGateFee = oNewOrder.LiftGateFee; oConfirmOrder.InstallFee = oNewOrder.InstallFee; oConfirmOrder.OtherFee = oNewOrder.OtherFee; oConfirmOrder.TotalFee = oNewOrder.TotalFee; oConfirmOrder.UsePoint = oNewOrder.UsePoint; oConfirmOrder.PointPay = oNewOrder.PointPay; oConfirmOrder.CouponPay = oNewOrder.CouponPay; oConfirmOrder.BounsPay = oNewOrder.BounsPay; oConfirmOrder.MoneyPaid = oNewOrder.MoneyPaid; oConfirmOrder.Discount = oNewOrder.Discount; oConfirmOrder.TotalPaid = oNewOrder.TotalPaid; oConfirmOrder.OrderAmount = oNewOrder.OrderAmount; oConfirmOrder.Differ = oNewOrder.Differ; #endregion #region 收货人基本信息 oConfirmOrder.Consignee = oNewOrder.Consignee; oConfirmOrder.aLocation = oNewOrder.aLocation; oConfirmOrder.FullAddress = oNewOrder.FullAddress; oConfirmOrder.PostCode = oNewOrder.PostCode; oConfirmOrder.Telephone = oNewOrder.Telephone; oConfirmOrder.Mobile = oNewOrder.Mobile; oConfirmOrder.Email = oNewOrder.Email; oConfirmOrder.BestDelivery = formCollection["OrderBestDelivery"]; oConfirmOrder.PostComment = formCollection["OrderPosComment"]; dbEntity.OrderInformations.Add(oConfirmOrder); dbEntity.SaveChanges(); #endregion #endregion #region 保存订单商品信息 //将全局订单商品的列表保存入数据库 for (int i = 0; i < globalOrderItemList.Count; i++) { OrderItem oNewOrderItem = new OrderItem(); oNewOrderItem.OrderID = oConfirmOrder.Gid; oNewOrderItem.OnSkuID = globalOrderItemList.ElementAt(i).Value.OnSkuID; oNewOrderItem.SkuID = globalOrderItemList.ElementAt(i).Value.SkuID; oNewOrderItem.Name = globalOrderItemList.ElementAt(i).Value.Name; oNewOrderItem.Quantity = globalOrderItemList.ElementAt(i).Value.Quantity; oNewOrderItem.MarketPrice = globalOrderItemList.ElementAt(i).Value.MarketPrice; oNewOrderItem.SalePrice = globalOrderItemList.ElementAt(i).Value.SalePrice; oNewOrderItem.ExecutePrice = globalOrderItemList.ElementAt(i).Value.ExecutePrice; dbEntity.OrderItems.Add(oNewOrderItem); //删除购物车 Guid mallCartGid = globalOrderItemList.ElementAt(i).Key; MallCart oCurrrentMallCart = dbEntity.MallCarts.Where(p => p.Gid == mallCartGid && p.Deleted == false).FirstOrDefault(); if (oCurrrentMallCart != null) { oCurrrentMallCart.Deleted = true; } dbEntity.SaveChanges(); } #endregion #region 保存订单承运商信息 //如果使用承运商,则保存最佳承运商信息 if (bUseShipper == true) { OrderShipping oNewOrderShipping = new OrderShipping(); oNewOrderShipping.OrderID = oConfirmOrder.Gid; oNewOrderShipping.ShipID = globalShipperGid; dbEntity.OrderShippings.Add(oNewOrderShipping); dbEntity.SaveChanges(); } #endregion #region 订单的属性 #endregion #region 发票信息 //有订单发票信息 if (bInvoiceOrNot == true) { FinanceInvoice oNewFinanceInvoice = new FinanceInvoice(); Guid optionItemGid = Guid.Parse(formCollection["InvoiceItem"]); GeneralOptItem oInvoiceItem = dbEntity.GeneralOptItems.Include("Name").Where(p => p.Gid == optionItemGid && p.Deleted == false).FirstOrDefault(); if (oInvoiceItem != null) { oNewFinanceInvoice.Matter = oInvoiceItem.Name.GetResource(LiveSession.Culture); } oNewFinanceInvoice.Title = formCollection["orderInvoice"]; oNewFinanceInvoice.Amount = oConfirmOrder.OrderAmount; dbEntity.FinanceInvoices.Add(oNewFinanceInvoice); dbEntity.SaveChanges(); } #endregion #region 将使用的券信息写入用户记录 for (int i = 0; i < globalCouponList.Count; i++) { Guid pointGid = globalCouponList.ElementAt(i).Key; MemberPoint oMemberPoint = dbEntity.MemberPoints.Include("User").Include("Promotion").Include("Coupon").Where(p=>p.Gid == pointGid && p.Deleted==false).FirstOrDefault(); if (oMemberPoint != null) { decimal couponBalance = globalCouponList.ElementAt(i).Value; MemberUsePoint oNewMemberUsePoint = new MemberUsePoint(); oNewMemberUsePoint.PointID = pointGid; oNewMemberUsePoint.Pstatus = (byte)ModelEnum.PointUsed.USED; oNewMemberUsePoint.RefType = (byte)ModelEnum.NoteType.ORDER; oNewMemberUsePoint.RefID = oConfirmOrder.Gid; //将原有的金额减去余额即为消费金额 oNewMemberUsePoint.Amount = oMemberPoint.Balance - couponBalance; dbEntity.MemberUsePoints.Add(oNewMemberUsePoint); //将积分表的余额变为当前余额 oMemberPoint.Balance = couponBalance; //将状态变为已使用 oMemberPoint.Pstatus = (byte)ModelEnum.PointStatus.USED; //当余额为0时,是否改变状态 //To do 不改变券的状态 dbEntity.SaveChanges(); } } #endregion return strReturnInfo; }
/// <summary> /// 保存编辑的发票 /// </summary> /// <param name="NewInvoice"></param> public void SaveEditInvoice(FinanceInvoice NewInvoice) { try { FinanceInvoice oldInvoice = dbEntity.FinanceInvoices.Include("OrderInfo").Where(i => i.Gid == NewInvoice.Gid).Single(); oldInvoice.OrderInfo.Code = NewInvoice.OrderInfo.Code; oldInvoice.Code = NewInvoice.Code; oldInvoice.Istatus = NewInvoice.Istatus; oldInvoice.Amount = NewInvoice.Amount; oldInvoice.SendNote = NewInvoice.SendNote; oldInvoice.Remark = NewInvoice.Remark; if (ModelState.IsValid) { dbEntity.Entry(oldInvoice).State = EntityState.Modified; dbEntity.SaveChanges(); } } catch (Exception ex) { RedirectToAction("ErrorPage", "Home", new { message = ex.Message }); } }