/***********************************************************************
|
* Project: baifenBinfa
|
* ProjectName: 百分兵法管理系统
|
* Web: http://chuanyin.com
|
* Author:
|
* Email:
|
* CreateTime: 202403/02
|
* Description: 暂无
|
***********************************************************************/
|
|
|
using System;
|
using System.Collections.Generic;
|
using System.Linq;
|
using System.Linq.Expressions;
|
using System.Threading.Tasks;
|
using CoreCms.Net.Configuration;
|
using CoreCms.Net.DTO.ComponentsDTO;
|
using CoreCms.Net.IRepository;
|
using CoreCms.Net.IRepository.UnitOfWork;
|
using CoreCms.Net.IServices;
|
using CoreCms.Net.IServices.baifenbingfa;
|
using CoreCms.Net.Loging;
|
using CoreCms.Net.Model.Entities;
|
using CoreCms.Net.Model.Entities.Expression;
|
using CoreCms.Net.Model.FromBody;
|
using CoreCms.Net.Model.ViewModels.Basics;
|
using CoreCms.Net.Model.ViewModels.DTO;
|
using CoreCms.Net.Model.ViewModels.UI;
|
using CoreCms.Net.Utility.Extensions;
|
using CoreCms.Net.Utility.Helper;
|
using Microsoft.Extensions.DependencyInjection;
|
using Newtonsoft.Json;
|
using Newtonsoft.Json.Linq;
|
using SqlSugar;
|
using static SKIT.FlurlHttpClient.Wechat.Api.Models.CgibinUserInfoBatchGetRequest.Types;
|
|
|
namespace CoreCms.Net.Services
|
{
|
/// <summary>
|
/// 商品表 接口实现
|
/// </summary>
|
public class CoreCmsGoodsServices : BaseServices<CoreCmsGoods>, ICoreCmsGoodsServices
|
{
|
private readonly ICoreCmsGoodsRepository _dal;
|
private readonly IUnitOfWork _unitOfWork;
|
private readonly ICoreCmsProductsServices _productsServices;
|
private readonly ICoreCmsGoodsGradeServices _goodsGradeServices;
|
private readonly ICoreCmsLabelServices _labelServices;
|
private readonly ICoreCmsPromotionServices _promotionServices;
|
private readonly ICoreCmsGoodsCollectionServices _goodsCollectionServices;
|
private readonly ICoreCmsBrandServices _brandServices;
|
private readonly ICoreCmsOrderItemServices _orderItemServices;
|
private readonly ICoreCmsUserServices _userServices;
|
private readonly ICoreCmsUserGradeServices _userGradeServices;
|
private readonly IBfbfComAPIService _bfbfComAPIService;
|
|
private readonly IServiceProvider _serviceProvider;
|
|
|
public CoreCmsGoodsServices(IUnitOfWork unitOfWork, ICoreCmsGoodsRepository dal
|
, ICoreCmsProductsServices productsServices
|
, ICoreCmsGoodsGradeServices goodsGradeServices
|
, ICoreCmsLabelServices labelServices
|
, ICoreCmsPromotionServices promotionServices
|
, ICoreCmsGoodsCollectionServices goodsCollectionServices
|
, ICoreCmsBrandServices brandServices
|
, ICoreCmsOrderItemServices orderItemServices, ICoreCmsUserServices userServices, ICoreCmsUserGradeServices userGradeServices, IServiceProvider serviceProvider, IBfbfComAPIService bfbfComAPIService)
|
{
|
this._dal = dal;
|
base.BaseDal = dal;
|
_unitOfWork = unitOfWork;
|
_productsServices = productsServices;
|
_goodsGradeServices = goodsGradeServices;
|
_labelServices = labelServices;
|
_promotionServices = promotionServices;
|
_goodsCollectionServices = goodsCollectionServices;
|
_brandServices = brandServices;
|
_orderItemServices = orderItemServices;
|
_userServices = userServices;
|
_userGradeServices = userGradeServices;
|
_serviceProvider = serviceProvider;
|
_bfbfComAPIService = bfbfComAPIService;
|
|
}
|
|
|
|
/// <summary>
|
/// 重写异步插入方法
|
/// </summary>
|
/// <param name="entity">实体数据</param>
|
/// <returns></returns>
|
public async Task<AdminUiCallBack> InsertAsync(FMGoodsInsertModel entity)
|
{
|
return await _dal.InsertAsync(entity);
|
}
|
|
/// <summary>
|
/// 重写异步更新方法方法
|
/// </summary>
|
/// <param name="entity"></param>
|
/// <returns></returns>
|
public async Task<AdminUiCallBack> UpdateAsync(FMGoodsInsertModel entity)
|
{
|
return await _dal.UpdateAsync(entity);
|
}
|
|
/// <summary>
|
/// 重写删除指定ID集合的数据(批量删除)
|
/// </summary>
|
/// <param name="ids"></param>
|
/// <returns></returns>
|
public async Task<AdminUiCallBack> DeleteByIdsAsync(int[] ids)
|
{
|
return await _dal.DeleteByIdsAsync(ids);
|
}
|
|
|
#region 批量修改价格==========================================
|
/// <summary>
|
/// 批量修改价格
|
/// </summary>
|
/// <param name="entity"></param>
|
/// <returns></returns>
|
public async Task<AdminUiCallBack> DoBatchModifyPrice(FmBatchModifyPrice entity)
|
{
|
var jm = new AdminUiCallBack();
|
|
var bl = false;
|
//获取商品信息
|
var goods = await base.BaseDal.QueryListByClauseAsync(p => entity.ids.Contains(p.id));
|
if (!goods.Any())
|
{
|
jm.msg = GlobalConstVars.DataisNo;
|
return jm;
|
}
|
var goodIds = goods.Select(p => p.id).ToList();
|
//获取货品信息
|
var products = await _productsServices.QueryListByClauseAsync(p => goodIds.Contains((int)p.goodsId));
|
var productIds = products.Select(p => p.id).ToList();
|
//获取自定义价格信息
|
var goodsGrade = await _goodsGradeServices.QueryListByClauseAsync(p => goodIds.Contains(p.goodsId));
|
var goodsGradeIds = goodsGrade.Select(p => p.id).ToList();
|
|
var priceValue = entity.priceValue;
|
|
switch (entity.modifyType)
|
{
|
case "=":
|
if (entity.priceType == GlobalEnumVars.PriceType.price.ToString())
|
{
|
bl = await _productsServices.UpdateAsync(p => new CoreCmsProducts() { price = priceValue }, p => goodIds.Contains((int)p.goodsId) && p.isDel == false);
|
}
|
else if (entity.priceType == GlobalEnumVars.PriceType.costprice.ToString())
|
{
|
bl = await _productsServices.UpdateAsync(p => new CoreCmsProducts() { costprice = priceValue }, p => goodIds.Contains((int)p.goodsId) && p.isDel == false);
|
}
|
else if (entity.priceType == GlobalEnumVars.PriceType.mktprice.ToString())
|
{
|
bl = await _productsServices.UpdateAsync(p => new CoreCmsProducts() { mktprice = priceValue }, p => goodIds.Contains((int)p.goodsId) && p.isDel == false);
|
}
|
else if (entity.priceType.Contains("grade_price_"))
|
{
|
var gradeArr = entity.priceType.Split("_");
|
var goodsGradeId = Convert.ToInt16(gradeArr[2]);
|
if (goodsGradeId > 0)
|
{
|
bl = await _goodsGradeServices.UpdateAsync(p => new CoreCmsGoodsGrade { gradePrice = priceValue }, p => goodsGradeIds.Contains(p.id) && p.gradeId == goodsGradeId);
|
}
|
}
|
break;
|
case "-":
|
if (entity.priceType == GlobalEnumVars.PriceType.price.ToString())
|
{
|
bl = await _productsServices.UpdateAsync(p => new CoreCmsProducts() { price = p.price - priceValue }, p => goodIds.Contains((int)p.goodsId) && p.isDel == false);
|
}
|
else if (entity.priceType == GlobalEnumVars.PriceType.costprice.ToString())
|
{
|
bl = await _productsServices.UpdateAsync(p => new CoreCmsProducts() { costprice = p.costprice - priceValue }, p => goodIds.Contains((int)p.goodsId) && p.isDel == false);
|
}
|
else if (entity.priceType == GlobalEnumVars.PriceType.mktprice.ToString())
|
{
|
bl = await _productsServices.UpdateAsync(p => new CoreCmsProducts() { mktprice = p.mktprice - priceValue }, p => goodIds.Contains((int)p.goodsId) && p.isDel == false);
|
}
|
else if (entity.priceType.Contains("grade_price_"))
|
{
|
var gradeArr = entity.priceType.Split("_");
|
var goodsGradeId = Convert.ToInt16(gradeArr[2]);
|
if (goodsGradeId > 0)
|
{
|
bl = await _goodsGradeServices.UpdateAsync(p => new CoreCmsGoodsGrade { gradePrice = p.gradePrice - priceValue }, p => goodsGradeIds.Contains(p.id) && p.gradeId == goodsGradeId);
|
}
|
}
|
break;
|
case "+":
|
if (entity.priceType == GlobalEnumVars.PriceType.price.ToString())
|
{
|
bl = await _productsServices.UpdateAsync(p => new CoreCmsProducts() { price = p.price + priceValue }, p => goodIds.Contains((int)p.goodsId) && p.isDel == false);
|
}
|
else if (entity.priceType == GlobalEnumVars.PriceType.costprice.ToString())
|
{
|
bl = await _productsServices.UpdateAsync(p => new CoreCmsProducts() { costprice = p.costprice + priceValue }, p => goodIds.Contains((int)p.goodsId) && p.isDel == false);
|
}
|
else if (entity.priceType == GlobalEnumVars.PriceType.mktprice.ToString())
|
{
|
bl = await _productsServices.UpdateAsync(p => new CoreCmsProducts() { mktprice = p.mktprice + priceValue }, p => goodIds.Contains((int)p.goodsId) && p.isDel == false);
|
}
|
else if (entity.priceType.Contains("grade_price_"))
|
{
|
var gradeArr = entity.priceType.Split("_");
|
var goodsGradeId = Convert.ToInt16(gradeArr[2]);
|
if (goodsGradeId > 0)
|
{
|
bl = await _goodsGradeServices.UpdateAsync(p => new CoreCmsGoodsGrade { gradePrice = p.gradePrice + priceValue }, p => goodsGradeIds.Contains(p.id) && p.gradeId == goodsGradeId);
|
}
|
}
|
break;
|
case "*":
|
if (entity.priceType == GlobalEnumVars.PriceType.price.ToString())
|
{
|
bl = await _productsServices.UpdateAsync(p => new CoreCmsProducts() { price = p.price * priceValue }, p => goodIds.Contains((int)p.goodsId) && p.isDel == false);
|
}
|
else if (entity.priceType == GlobalEnumVars.PriceType.costprice.ToString())
|
{
|
bl = await _productsServices.UpdateAsync(p => new CoreCmsProducts() { costprice = p.costprice * priceValue }, p => goodIds.Contains((int)p.goodsId) && p.isDel == false);
|
}
|
else if (entity.priceType == GlobalEnumVars.PriceType.mktprice.ToString())
|
{
|
bl = await _productsServices.UpdateAsync(p => new CoreCmsProducts() { mktprice = p.mktprice * priceValue }, p => goodIds.Contains((int)p.goodsId) && p.isDel == false);
|
}
|
else if (entity.priceType.Contains("grade_price_"))
|
{
|
var gradeArr = entity.priceType.Split("_");
|
var goodsGradeId = Convert.ToInt16(gradeArr[2]);
|
if (goodsGradeId > 0)
|
{
|
bl = await _goodsGradeServices.UpdateAsync(p => new CoreCmsGoodsGrade { gradePrice = p.gradePrice * priceValue }, p => goodsGradeIds.Contains(p.id) && p.gradeId == goodsGradeId);
|
}
|
}
|
break;
|
}
|
jm.code = bl ? 0 : 1;
|
jm.msg = bl ? "价格修改成功" : "价格修改失败";
|
|
return jm;
|
}
|
|
#endregion
|
|
#region 批量修改库存==========================================
|
/// <summary>
|
/// 批量修改价格
|
/// </summary>
|
/// <param name="entity"></param>
|
/// <returns></returns>
|
public async Task<AdminUiCallBack> DoBatchModifyStock(FmBatchModifyStock entity)
|
{
|
var jm = new AdminUiCallBack();
|
|
var bl = false;
|
//获取商品信息
|
var goods = await base.BaseDal.QueryListByClauseAsync(p => entity.ids.Contains(p.id));
|
if (!goods.Any())
|
{
|
jm.msg = GlobalConstVars.DataisNo;
|
return jm;
|
}
|
var goodIds = goods.Select(p => p.id).ToList();
|
|
var modifyValue = entity.modifyValue;
|
|
switch (entity.modifyType)
|
{
|
case "=":
|
bl = await _productsServices.UpdateAsync(p => new CoreCmsProducts() { stock = modifyValue }, p => goodIds.Contains((int)p.goodsId) && p.isDel == false);
|
break;
|
case "-":
|
bl = await _productsServices.UpdateAsync(p => new CoreCmsProducts() { stock = p.stock - modifyValue }, p => goodIds.Contains((int)p.goodsId) && p.isDel == false);
|
break;
|
case "+":
|
bl = await _productsServices.UpdateAsync(p => new CoreCmsProducts() { stock = p.stock + modifyValue }, p => goodIds.Contains((int)p.goodsId) && p.isDel == false);
|
break;
|
case "*":
|
bl = await _productsServices.UpdateAsync(p => new CoreCmsProducts() { stock = p.stock * modifyValue }, p => goodIds.Contains((int)p.goodsId) && p.isDel == false);
|
break;
|
}
|
jm.code = bl ? 0 : 1;
|
jm.msg = bl ? "库存修改成功" : "库存修改失败";
|
|
return jm;
|
}
|
|
#endregion
|
|
#region 批量上架==========================================
|
|
/// <summary>
|
/// 批量上架
|
/// </summary>
|
/// <param name="ids"></param>
|
/// <returns></returns>
|
public async Task<AdminUiCallBack> DoBatchMarketableUp(int[] ids)
|
{
|
var jm = new AdminUiCallBack();
|
|
var bl = await _dal.UpdateAsync(p => new CoreCmsGoods() { isMarketable = true }, p => ids.Contains(p.id));
|
jm.code = bl ? 0 : 1;
|
jm.msg = bl ? "上架成功" : "上架失败";
|
|
return jm;
|
}
|
#endregion
|
|
#region 批量下架==========================================
|
|
/// <summary>
|
/// 批量下架
|
/// </summary>
|
/// <param name="ids"></param>
|
/// <returns></returns>
|
public async Task<AdminUiCallBack> DoBatchMarketableDown(int[] ids)
|
{
|
var jm = new AdminUiCallBack();
|
|
var bl = await _dal.UpdateAsync(p => new CoreCmsGoods() { isMarketable = false }, p => ids.Contains(p.id));
|
jm.code = bl ? 0 : 1;
|
jm.msg = bl ? "下架成功" : "下架失败";
|
|
return jm;
|
}
|
#endregion
|
|
#region 设置标签==========================================
|
|
/// <summary>
|
/// 设置标签
|
/// </summary>
|
/// <param name="entity"></param>
|
/// <returns></returns>
|
public async Task<AdminUiCallBack> DoSetLabel(FmSetLabel entity)
|
{
|
var jm = new AdminUiCallBack();
|
|
|
var names = entity.labels.Select(p => p.text).ToList();
|
//获取已经存在数据库数据
|
var olds = await _labelServices.QueryListByClauseAsync(p => names.Contains(p.name));
|
if (olds.Any())
|
{
|
var oldNames = olds.Select(p => p.name).ToList();
|
//获取未插入数据库数据
|
var newNames = entity.labels.Where(p => !oldNames.Contains(p.text)).ToList();
|
if (newNames.Any())
|
{
|
var labels = new List<CoreCmsLabel>();
|
newNames.ForEach(p =>
|
{
|
labels.Add(new CoreCmsLabel()
|
{
|
name = p.text,
|
style = p.style
|
});
|
});
|
await _labelServices.InsertAsync(labels);
|
}
|
}
|
else
|
{
|
var labels = new List<CoreCmsLabel>();
|
entity.labels.ForEach(p =>
|
{
|
labels.Add(new CoreCmsLabel()
|
{
|
name = p.text,
|
style = p.style
|
});
|
});
|
await _labelServices.InsertAsync(labels);
|
}
|
|
var items = await _labelServices.QueryListByClauseAsync(p => names.Contains(p.name));
|
var idsInts = items.Select(p => p.id).ToArray();
|
var ids = String.Join(",", idsInts);
|
|
var bl = await base.BaseDal.UpdateAsync(p => new CoreCmsGoods() { labelIds = ids }, p => entity.ids.Contains(p.id));
|
|
jm.code = bl ? 0 : 1;
|
jm.msg = bl ? "设置成功" : "设置失败";
|
|
return jm;
|
}
|
#endregion
|
|
#region 取消标签==========================================
|
|
/// <summary>
|
/// 取消标签
|
/// </summary>
|
/// <param name="entity"></param>
|
/// <returns></returns>
|
public async Task<AdminUiCallBack> DoDeleteLabel(FmSetLabel entity)
|
{
|
var jm = new AdminUiCallBack();
|
|
var names = entity.labels.Select(p => p.text).ToList();
|
//获取已经存在数据库数据
|
var labels = await _labelServices.QueryListByClauseAsync(p => names.Contains(p.name));
|
var labelIds = labels.Select(p => p.id).ToList();
|
|
var goods = await base.QueryListByClauseAsync(p => entity.ids.Contains(p.id));
|
goods.ForEach(p =>
|
{
|
if (!string.IsNullOrEmpty(p.labelIds))
|
{
|
var ids = CommonHelper.StringToIntArray(p.labelIds);
|
var newIds = ids.Except(labelIds).ToList();
|
if (newIds.Any())
|
{
|
p.labelIds = String.Join(",", newIds);
|
}
|
else
|
{
|
p.labelIds = "";
|
}
|
}
|
});
|
|
var bl = await base.UpdateAsync(goods);
|
|
jm.code = bl ? 0 : 1;
|
jm.msg = bl ? "设置成功" : "设置失败";
|
|
|
return jm;
|
}
|
#endregion
|
|
#region 判断商品是否参加团购或者秒杀
|
|
public bool IsInGroup(int goodId, out CoreCmsPromotion promotionsModel, int promotionId = 0)
|
{
|
promotionsModel = new CoreCmsPromotion();
|
if (goodId == 0)
|
{
|
return false;
|
}
|
|
var dt = DateTime.Now;
|
var where = PredicateBuilder.True<CoreCmsPromotion>();
|
where = where.And(p => p.isEnable == true);
|
if (promotionId > 0)
|
{
|
where = where.And(p => p.id == promotionId);
|
}
|
where = where.And(p =>
|
(p.type == (int)GlobalEnumVars.PromotionType.Group ||
|
p.type == (int)GlobalEnumVars.PromotionType.Seckill));
|
where = where.And(p => p.startTime < dt || p.endTime > dt);
|
where = where.And(p => p.isDel == false);
|
|
var promotions = _promotionServices.QueryByClause(where);
|
if (promotions == null) return false;
|
|
try
|
{
|
if (string.IsNullOrEmpty(promotions.parameters)) return false;
|
var obj = JsonConvert.DeserializeAnonymousType(promotions.parameters, new
|
{
|
goodsId = "",
|
num = 0,
|
});
|
if (obj.goodsId.ObjectToInt(0) != goodId) return false;
|
promotionsModel = promotions;
|
return true;
|
}
|
catch
|
{
|
return false;
|
}
|
}
|
#endregion
|
|
#region 获取商品重量
|
|
/// <summary>
|
/// 获取商品重量
|
/// </summary>
|
/// <param name="productsId"></param>
|
/// <returns></returns>
|
public async Task<decimal> GetWeight(int productsId)
|
{
|
return await _dal.GetWeight(productsId);
|
}
|
#endregion
|
|
#region 库存改变机制
|
/// <summary>
|
/// 库存改变机制。
|
/// 库存机制:商品下单 总库存不变,冻结库存加1,
|
/// 商品发货:冻结库存减1,总库存减1,
|
/// 订单完成但未发货:总库存不变,冻结库存减1
|
/// 商品退款&取消订单:总库存不变,冻结库存减1,
|
/// 商品退货:总库存加1,冻结库存不变,
|
/// 可销售库存:总库存-冻结库存
|
/// </summary>
|
/// <returns></returns>
|
public WebApiCallBack ChangeStock(int productsId, string type = "order", int num = 0)
|
{
|
|
return _dal.ChangeStock(productsId, type, num);
|
}
|
#endregion
|
|
|
#region 获取商品详情
|
|
/// <summary>
|
/// 获取商品详情
|
/// </summary>
|
/// <param name="id"></param>
|
/// <param name="userId"></param>
|
/// <param name="isPromotion">是否涉及优惠</param>
|
/// <param name="type"></param>
|
/// <param name="groupId"></param>
|
/// <param name="needSku">是否需要sku</param>
|
/// <returns></returns>
|
public async Task<CoreCmsGoods> GetGoodsDetail(int id, int userId = 0, bool isPromotion = false, string type = "goods", int groupId = 0, bool needSku = false)
|
{
|
var good = await _dal.QueryByClauseAsync(p => p.id == id, true);
|
if (good == null) return null;
|
//取图片集
|
good.album = good.images.Split(",");
|
//获取主图
|
good.image = !string.IsNullOrEmpty(good.image) ? good.image : "/static/images/common/empty-banner.png";
|
//获取用户信息
|
if (userId > 0)
|
{
|
good.isFav = await _goodsCollectionServices.ExistsAsync(p => p.goodsId == good.id && p.userId == userId, true);
|
}
|
|
var product = new CoreCmsProducts();
|
var products = new List<CoreCmsProducts>();
|
if (needSku == true)
|
{
|
//取所有货品
|
products = await _productsServices.QueryListByClauseAsync(p => p.goodsId == good.id && p.isDel == false, p => p.id, OrderByType.Asc, true);
|
if (products == null) return null;
|
//获取默认货品
|
product = products.FirstOrDefault(p => p.isDefalut);
|
if (product == null) return null;
|
|
good.skuList = await GetCoreCmsProductsView(good, products, userId, isPromotion, type, groupId);
|
}
|
else
|
{
|
product = await _productsServices.QueryByClauseAsync(p => p.goodsId == good.id && p.isDel == false && p.isDefalut == true, true);
|
if (product == null) return null;
|
}
|
|
//商品基础赋值===================================================================================================
|
good.product = product;
|
good.sn = product.sn;
|
good.price = product.price;
|
good.costprice = product.costprice;
|
good.mktprice = product.mktprice;
|
good.stock = product.stock;
|
good.freezeStock = product.freezeStock;
|
good.weight = product.weight;
|
good.buyPinTuanCount = product.buyPinTuanCount;
|
good.buyPromotionCount = product.buyPromotionCount;
|
|
if (!string.IsNullOrEmpty(good.labelIds))
|
{
|
var ids = CommonHelper.StringToIntArray(good.labelIds);
|
var lbs = await _labelServices.QueryAsync(true, true, 3600);
|
good.labels = lbs.Where(p => ids.Contains(p.id)).ToList();
|
}
|
|
//获取商品最小价格
|
good.minPrice = products.Any() ? products.OrderBy(p => p.price).First().price : product.price;
|
//获取商品最大价格
|
good.maxPrice = products.Any() ? products.OrderByDescending(p => p.price).First().price : product.price;
|
|
//获取品牌
|
good.brand = await _brandServices.QueryByIdAsync(good.brandId, true, true);
|
|
//取出销量
|
good.buyCount = good.initialSales + await _orderItemServices.GetSumAsync(p => p.goodsId == good.id, o => o.nums, true);
|
return good;
|
}
|
#endregion
|
|
#region 通过商品序列获取sku列表
|
/// <summary>
|
/// 通过商品序列获取sku列表
|
/// </summary>
|
/// <param name="good"></param>
|
/// <param name="products"></param>
|
/// <param name="userId"></param>
|
/// <param name="isPromotion"></param>
|
/// <param name="type"></param>
|
/// <param name="groupId"></param>
|
/// <returns></returns>
|
public async Task<CoreCmsProductsView> GetCoreCmsProductsView(CoreCmsGoods good, List<CoreCmsProducts> products, int userId = 0, bool isPromotion = false, string type = "goods", int groupId = 0)
|
{
|
//获取默认货品
|
var product = products.FirstOrDefault(p => p.isDefalut);
|
if (product == null) return null;
|
|
|
//获取会员级别优惠价
|
//获取会员等级优惠价格体系
|
decimal gradePrice = 0;
|
//百分兵法增加
|
bool IsDictionary = await _bfbfComAPIService.IsDictionary(userId);
|
if (userId > 0 && type == "goods")
|
{
|
//获取用户信息
|
var userInfo = await _userServices.QueryByIdAsync(userId);
|
if (userInfo != null)
|
{
|
var goodsGrades = await _goodsGradeServices.QueryByClauseAsync(p => p.goodsId == good.id && p.gradeId == userInfo.grade);
|
//对接经销商会员
|
|
if (goodsGrades != null)
|
{
|
gradePrice = goodsGrades.gradePrice;
|
}
|
}
|
}
|
//sku优惠计算===================================================================================
|
using var container = _serviceProvider.CreateScope();
|
var orderServices = container.ServiceProvider.GetService<ICoreCmsOrderServices>();
|
var pinTuanRuleServices = container.ServiceProvider.GetService<ICoreCmsPinTuanRuleServices>();
|
var promotionServices = container.ServiceProvider.GetService<ICoreCmsPromotionServices>();
|
var promotionConditionServices = container.ServiceProvider.GetService<ICoreCmsPromotionConditionServices>();
|
var promotionResultServices = container.ServiceProvider.GetService<ICoreCmsPromotionResultServices>();
|
|
if (isPromotion)
|
{
|
var dt = DateTime.Now;
|
if (type == GlobalEnumVars.OrderType.Group.ToString().ToLowerInvariant() || type == GlobalEnumVars.OrderType.Seckill.ToString().ToLowerInvariant())
|
{
|
//团购秒杀默认时间过期后,不可以下单
|
var key = false;
|
var promotionInfo = await promotionServices.QueryByClauseAsync(p => p.startTime < dt && p.endTime > dt && p.id == groupId, true);
|
if (promotionInfo != null)
|
{
|
//去除所有的条件
|
var promotionCondition = await promotionConditionServices.QueryByClauseAsync(p => p.promotionId == promotionInfo.id);
|
if (!string.IsNullOrEmpty(promotionCondition.parameters))
|
{
|
JObject parameters = (JObject)JsonConvert.DeserializeObject(promotionCondition.parameters);
|
if (parameters.ContainsKey("goodsId") && parameters.ContainsKey("nums"))
|
{
|
var objNums = Convert.ToInt32(parameters["nums"]);
|
var goodsIds = CommonHelper.StringToIntArray(parameters["goodsId"].ObjectToString());
|
key = goodsIds.Any() && goodsIds.Contains(good.id);
|
}
|
};
|
}
|
if (key)
|
{
|
//走到这一步就说明所有的促销条件都符合,那么就去计算结果
|
var promotionResult = await promotionResultServices.QueryByClauseAsync(p => p.promotionId == promotionInfo.id);
|
if (!string.IsNullOrEmpty(promotionResult?.parameters))
|
{
|
foreach (var productModel in products)
|
{
|
var item = new CartProducts()
|
{
|
id = 0,
|
isSelect = true,
|
userId = userId,
|
productId = productModel.id,
|
nums = 1,
|
products = productModel
|
};
|
decimal promotionMoney;
|
JObject parameters = (JObject)JsonConvert.DeserializeObject(promotionResult.parameters);
|
switch (promotionResult.code)
|
{
|
//指定商品减固定金额
|
case "GOODS_REDUCE":
|
promotionMoney = promotionResultServices.result_GOODS_REDUCE(parameters, item, promotionInfo);
|
break;
|
//指定商品打X折
|
case "GOODS_DISCOUNT":
|
promotionMoney = promotionResultServices.result_GOODS_DISCOUNT(parameters, item, promotionInfo);
|
break;
|
//指定商品一口价
|
case "GOODS_ONE_PRICE":
|
promotionMoney = promotionResultServices.result_GOODS_ONE_PRICE(parameters, item, promotionInfo);
|
break;
|
//指定商品每第几件减指定金额
|
case "GOODS_HALF_PRICE": //todo 指定商品每第几件减指定金额
|
promotionMoney = promotionResultServices.result_GOODS_HALF_PRICE(parameters, item, promotionInfo);
|
break;
|
default:
|
promotionMoney = 0;
|
break;
|
}
|
//productModel.price = Math.Round(productModel.price - promotionMoney, 2);
|
}
|
}
|
}
|
|
}
|
else
|
{
|
//走全局优惠模式
|
var promotions = await promotionServices.QueryListByClauseAsync(p => p.isEnable == true && p.startTime < dt && p.endTime > dt && p.type == (int)GlobalEnumVars.PromotionType.Promotion && p.isDel == false, p => p.sort, OrderByType.Asc, true);
|
|
}
|
}
|
|
//获取活动数量===================================================================================
|
var stock = 0;
|
var isMaxPinTuanGoodsNums = false;
|
var buyPinTuanCount = 0;
|
var isMaxGroupOrSeckillGoodsNums = false;
|
var buyPromotionCount = 0;
|
if (type == GlobalEnumVars.OrderType.PinTuan.ToString().ToLowerInvariant())
|
{
|
//把拼团的一些属性等加上
|
var pinTuanRule = pinTuanRuleServices.QueryMuchFirst<CoreCmsPinTuanRule, CoreCmsPinTuanGoods, CoreCmsPinTuanRule>(
|
(role, pinTuanGoods) => new object[] { JoinType.Inner, role.id == pinTuanGoods.ruleId }
|
, (role, pinTuanGoods) => role
|
, (role, pinTuanGoods) => pinTuanGoods.goodsId == good.id);
|
//调整前台显示数量
|
var checkOrder = orderServices.FindLimitOrderByGoodId(good.id, userId, pinTuanRule.startTime, pinTuanRule.endTime, (int)GlobalEnumVars.OrderType.PinTuan);
|
if (pinTuanRule.maxGoodsNums != 0 && pinTuanRule.maxNums != 0)
|
{
|
isMaxPinTuanGoodsNums = true;
|
//总剩余可购买总数量
|
var residue = pinTuanRule.maxGoodsNums - checkOrder.TotalOrders;
|
//用户剩余可购买数量
|
var userResidue = pinTuanRule.maxGoodsNums - checkOrder.TotalUserOrders;
|
//求最小匹配
|
stock = userResidue > residue ? residue : userResidue;
|
}
|
else if (pinTuanRule.maxNums != 0 && pinTuanRule.maxNums == 0)
|
{
|
//限制个人最多购买数量
|
stock = pinTuanRule.maxNums - checkOrder.TotalUserOrders == 0 ? 0 : pinTuanRule.maxNums - checkOrder.TotalUserOrders;
|
}
|
else if (pinTuanRule.maxNums == 0 && pinTuanRule.maxNums != 0)
|
{
|
//限制最大购买总数
|
stock = pinTuanRule.maxGoodsNums - checkOrder.TotalOrders == 0 ? 0 : pinTuanRule.maxGoodsNums - checkOrder.TotalOrders;
|
}
|
buyPinTuanCount = checkOrder.TotalOrders;
|
}
|
else if (type == GlobalEnumVars.OrderType.Group.ToString().ToLowerInvariant() || type == GlobalEnumVars.OrderType.Seckill.ToString().ToLowerInvariant())
|
{
|
if (!IsInGroup(good.id, out var groupModel, groupId))
|
{
|
return null;
|
}
|
var orderType = type == GlobalEnumVars.OrderType.Seckill.ToString().ToLowerInvariant()
|
? (int)GlobalEnumVars.OrderType.Group
|
: (int)GlobalEnumVars.OrderType.Seckill;
|
|
//调整前台显示数量
|
var checkOrder = orderServices.FindLimitOrderByGoodId(good.id, userId, groupModel.startTime, groupModel.endTime, orderType);
|
if (groupModel.maxGoodsNums != 0 && groupModel.maxNums != 0)
|
{
|
isMaxGroupOrSeckillGoodsNums = true;
|
//总剩余可购买总数量
|
var residue = groupModel.maxGoodsNums - checkOrder.TotalOrders;
|
//用户剩余可购买数量
|
var userResidue = groupModel.maxGoodsNums - checkOrder.TotalUserOrders;
|
//求最小匹配
|
stock = userResidue > residue ? residue : userResidue;
|
}
|
else if (groupModel.maxNums != 0 && groupModel.maxNums == 0)
|
{
|
isMaxGroupOrSeckillGoodsNums = true;
|
//限制个人最多购买数量
|
stock = groupModel.maxNums - checkOrder.TotalUserOrders;
|
}
|
else if (groupModel.maxNums == 0 && groupModel.maxNums != 0)
|
{
|
isMaxGroupOrSeckillGoodsNums = true;
|
//限制最大购买总数
|
stock = groupModel.maxGoodsNums - checkOrder.TotalOrders;
|
}
|
buyPromotionCount = checkOrder.TotalOrders;
|
}
|
|
|
//sku前端json组合实体===================================================================================
|
CoreCmsProductsView result;
|
//如果是多规格商品,算多规格
|
if (good.openSpec == 1 && !string.IsNullOrEmpty(good.spesDesc))
|
{
|
// 1910&&电线型号:1.5mm²|1911&&电线型号:2.5mm²|1912&&电线型号:4mm²|1913&&电线型号:6mm²|1901&&电线颜色:红色|1902&&电线颜色:蓝色|1903&&电线颜色:黄色|1904&&电线颜色:绿色|1905&&电线颜色:双色
|
// 电线型号:1.5mm²,电线颜色:蓝色
|
var defaultSpec = new Dictionary<string, List<string>>();
|
foreach (var item in good.spesDesc.Split("|"))
|
{
|
//1911&&电线型号:2.5mm²
|
var temp = item.Split("&&")[1].Split(":");
|
var name = temp[0];
|
var value = temp[1];
|
if (!defaultSpec.ContainsKey(name))
|
{
|
defaultSpec.Add(name, new List<string>());
|
}
|
defaultSpec[name].Add(value);
|
}
|
result = new CoreCmsProductsView();
|
result._id = product.id.ToString();
|
result.name = good.name;
|
result.goods_thumb = product.images;
|
result.buyPinTuanCount = buyPinTuanCount;
|
result.buyPromotionCount = buyPromotionCount;
|
|
var skuList = new List<Product_Sku_listItem>();
|
products.ForEach(o =>
|
{
|
var item = new Product_Sku_listItem();
|
item._id = o.id.ToString();
|
item.goods_id = good.id.ToString();
|
item.goods_name = good.name;
|
item.image = o.images;
|
if(!IsDictionary)
|
item.price = o.price - gradePrice; //减去会员等级价格
|
else
|
item.price = o.distributionPrice;
|
item.sku_name_arr = o.spesDesc.Split(",").Select(s => s.Split(":")[1]).ToList();
|
item.stock = o.stock;
|
item.cutMoney = o.cutMoney;
|
item.distributionCutMoney = o.distributionCutMoney;
|
item.mktPrice = o.mktprice;
|
item.selPrice = o.price;
|
if (type == GlobalEnumVars.OrderType.PinTuan.ToString().ToLowerInvariant())
|
{
|
if (isMaxPinTuanGoodsNums)
|
{
|
item.stock = stock;
|
}
|
}
|
else if (type == GlobalEnumVars.OrderType.Group.ToString().ToLowerInvariant() || type == GlobalEnumVars.OrderType.Seckill.ToString().ToLowerInvariant())
|
{
|
if (isMaxGroupOrSeckillGoodsNums)
|
{
|
item.stock = stock;
|
}
|
}
|
skuList.Add(item);
|
});
|
|
result.sku_list = skuList;
|
|
result.spec_list = defaultSpec.Select(d => new Product_Spec_listItem()
|
{
|
name = d.Key,
|
list = d.Value.Select(s => new Product_Sku_list
|
{
|
name = s
|
}).ToList(),
|
}).ToList();
|
}
|
else
|
{
|
result = new CoreCmsProductsView();
|
result._id = product.id.ToString();
|
result.name = good.name;
|
result.goods_thumb = product.images;
|
result.buyPinTuanCount = buyPinTuanCount;
|
result.buyPromotionCount = buyPromotionCount;
|
|
var skuList = new List<Product_Sku_listItem>();
|
products.ForEach(o =>
|
{
|
var item = new Product_Sku_listItem();
|
item._id = o.id.ToString();
|
item.goods_id = good.id.ToString();
|
item.goods_name = good.name;
|
item.image = o.images;
|
if (!IsDictionary)
|
item.price = o.price - gradePrice; //减去会员等级价格
|
else
|
item.price = o.distributionPrice;
|
//item.price = o.price - gradePrice; //减去会员等级价格
|
item.sku_name_arr = new List<string> { "默认" };
|
item.stock = o.stock;
|
item.cutMoney = o.cutMoney;
|
item.distributionCutMoney = o.distributionCutMoney;
|
item.mktPrice = o.mktprice;
|
item.selPrice = o.price;
|
if (type == GlobalEnumVars.OrderType.PinTuan.ToString().ToLowerInvariant())
|
{
|
if (isMaxPinTuanGoodsNums)
|
{
|
item.stock = stock;
|
}
|
}
|
else if (type == GlobalEnumVars.OrderType.Group.ToString().ToLowerInvariant() || type == GlobalEnumVars.OrderType.Seckill.ToString().ToLowerInvariant())
|
{
|
if (isMaxGroupOrSeckillGoodsNums)
|
{
|
item.stock = stock;
|
}
|
}
|
|
skuList.Add(item);
|
});
|
result.sku_list = skuList;
|
result.spec_list = new List<Product_Spec_listItem>() {
|
new Product_Spec_listItem(){
|
list = new List<Product_Sku_list>{
|
new Product_Sku_list{
|
name = "默认"
|
}
|
},
|
name = "默认"
|
}
|
};
|
}
|
return result;
|
}
|
|
#endregion
|
|
#region 获取随机推荐数据
|
|
/// <summary>
|
/// 获取随机推荐数据
|
/// </summary>
|
/// <param name="number"></param>
|
/// <param name="isRecommend"></param>
|
/// <returns></returns>
|
public async Task<List<GoodListDTO>> GetGoodsRecommendList(int number, bool isRecommend = false)
|
{
|
return await _dal.GetGoodsRecommendList(number, isRecommend);
|
}
|
#endregion
|
|
#region 获取数据总数
|
/// <summary>
|
/// 获取数据总数
|
/// </summary>
|
/// <param name="predicate">条件表达式树</param>
|
/// <param name="blUseNoLock">是否使用WITH(NOLOCK)</param>
|
/// <returns></returns>
|
public async Task<int> GetCountAsync(Expression<Func<CoreCmsGoods, bool>> predicate, bool blUseNoLock = false)
|
{
|
return await _dal.GetCountAsync(predicate, blUseNoLock);
|
}
|
|
#endregion
|
|
#region 重写根据条件查询分页数据
|
/// <summary>
|
/// 重写根据条件查询分页数据
|
/// </summary>
|
/// <param name="predicate">判断集合</param>
|
/// <param name="orderByType">排序方式</param>
|
/// <param name="pageIndex">当前页面索引</param>
|
/// <param name="pageSize">分布大小</param>
|
/// <param name="orderByExpression"></param>
|
/// <param name="blUseNoLock">是否使用WITH(NOLOCK)</param>
|
/// <returns></returns>
|
public async Task<IPageList<CoreCmsGoods>> QueryPageAsync(Expression<Func<CoreCmsGoods, bool>> predicate,
|
Expression<Func<CoreCmsGoods, object>> orderByExpression, OrderByType orderByType, int pageIndex = 1,
|
int pageSize = 20, bool blUseNoLock = false)
|
{
|
return await _dal.QueryPageAsync(predicate, orderByExpression, orderByType, pageIndex, pageSize, blUseNoLock);
|
}
|
#endregion
|
|
#region 重写根据条件查询一定数量数据
|
/// <summary>
|
/// 重写根据条件查询一定数量数据
|
/// </summary>
|
/// <param name="predicate">条件表达式树</param>
|
/// <param name="take">获取数量</param>
|
/// <param name="orderByPredicate">排序字段</param>
|
/// <param name="orderByType">排序顺序</param>
|
/// <param name="blUseNoLock">是否使用WITH(NOLOCK)</param>
|
/// <returns></returns>
|
public async Task<List<CoreCmsGoods>> QueryListByClauseAsync(Expression<Func<CoreCmsGoods, bool>> predicate, int take,
|
Expression<Func<CoreCmsGoods, object>> orderByPredicate, OrderByType orderByType, bool blUseNoLock = false)
|
{
|
return await _dal.QueryListByClauseAsync(predicate, take, orderByPredicate, orderByType, blUseNoLock);
|
}
|
#endregion
|
|
#region 重写根据条件查询数据
|
/// <summary>
|
/// 重写根据条件查询数据
|
/// </summary>
|
/// <param name="predicate">条件表达式树</param>
|
/// <param name="orderBy">排序字段,如name asc,age desc</param>
|
/// <param name="blUseNoLock">是否使用WITH(NOLOCK)</param>
|
/// <returns>泛型实体集合</returns>
|
public async Task<List<CoreCmsGoods>> QueryListByClauseAsync(Expression<Func<CoreCmsGoods, bool>> predicate, string orderBy = "",
|
bool blUseNoLock = false)
|
{
|
return await _dal.QueryListByClauseAsync(predicate, orderBy, blUseNoLock);
|
}
|
#endregion
|
|
#region 重写根据条件及自定义排序查询分页数据
|
/// <summary>
|
/// 重写根据条件及自定义排序查询分页数据
|
/// </summary>
|
/// <param name="predicate"></param>
|
/// <param name="orderBy"></param>
|
/// <param name="pageIndex">当前页面索引</param>
|
/// <param name="pageSize">分布大小</param>
|
/// <param name="blUseNoLock">是否使用WITH(NOLOCK)</param>
|
/// <returns></returns>
|
public async Task<IPageList<CoreCmsGoods>> QueryPageAsync(Expression<Func<CoreCmsGoods, bool>> predicate, string orderBy = "",
|
int pageIndex = 1, int pageSize = 20, bool blUseNoLock = false)
|
{
|
return await _dal.QueryPageAsync(predicate, orderBy, pageIndex, pageSize, blUseNoLock);
|
}
|
#endregion
|
|
|
#region 重写根据条件及自定义排序查询分页数据(返回DTO)
|
/// <summary>
|
/// 重写根据条件及自定义排序查询分页数据(返回DTO)
|
/// </summary>
|
/// <param name="predicate"></param>
|
/// <param name="orderBy"></param>
|
/// <param name="pageIndex">当前页面索引</param>
|
/// <param name="pageSize">分布大小</param>
|
/// <param name="blUseNoLock">是否使用WITH(NOLOCK)</param>
|
/// <returns></returns>
|
public async Task<IPageList<GoodListDTO>> QueryPageByDTOAsync(Expression<Func<GoodListDTO, bool>> predicate, int pageIndex = 1, int pageSize = 20, bool blUseNoLock = false)
|
{
|
return await _dal.QueryPageByDTOAsync(predicate, pageIndex, pageSize, blUseNoLock);
|
}
|
#endregion
|
|
/// <summary>
|
/// 根据条件查询代理池商品分页数据
|
/// </summary>
|
/// <param name="predicate"></param>
|
/// <param name="orderBy"></param>
|
/// <param name="pageIndex">当前页面索引</param>
|
/// <param name="pageSize">分布大小</param>
|
/// <param name="blUseNoLock">是否使用WITH(NOLOCK)</param>
|
/// <returns></returns>
|
public async Task<IPageList<CoreCmsGoods>> QueryAgentGoodsPageAsync(Expression<Func<CoreCmsGoods, bool>> predicate,
|
int pageIndex = 1, int pageSize = 20, bool blUseNoLock = false)
|
{
|
return await _dal.QueryAgentGoodsPageAsync(predicate, pageIndex, pageSize, blUseNoLock);
|
}
|
|
|
/// <summary>
|
/// 根据条件查询商品及sku分页数据
|
/// </summary>
|
/// <param name="predicate">判断集合</param>
|
/// <param name="orderByType">排序方式</param>
|
/// <param name="pageIndex">当前页面索引</param>
|
/// <param name="pageSize">分布大小</param>
|
/// <param name="orderByExpression"></param>
|
/// <param name="blUseNoLock">是否使用WITH(NOLOCK)</param>
|
/// <returns></returns>
|
public async Task<IPageList<CoreCmsGoods>> QueryGoodAndSkuPageAsync(Expression<Func<CoreCmsGoods, bool>> predicate,
|
Expression<Func<CoreCmsGoods, object>> orderByExpression, OrderByType orderByType, int pageIndex = 1,
|
int pageSize = 20, bool blUseNoLock = false)
|
{
|
return await _dal.QueryGoodAndSkuPageAsync(predicate, orderByExpression, orderByType, pageIndex, pageSize, blUseNoLock);
|
}
|
|
#region 获取下拉商品数据
|
/// <summary>
|
/// 获取下拉商品数据
|
/// </summary>
|
/// <returns></returns>
|
public async Task<List<EnumEntity>> QueryEnumEntityAsync()
|
{
|
|
return await _dal.QueryEnumEntityAsync();
|
}
|
#endregion
|
|
|
/// <summary>
|
/// 获取商品及默认货品信息
|
/// </summary>
|
/// <param name="predicate"></param>
|
/// <param name="orderByPredicate"></param>
|
/// <param name="orderByType"></param>
|
/// <param name="blUseNoLock">是否使用WITH(NOLOCK)</param>
|
/// <returns></returns>
|
public async Task<List<CoreCmsGoods>> QueryGoodWithDefaultProductAsync(Expression<Func<CoreCmsGoods, bool>> predicate,
|
Expression<Func<CoreCmsGoods, object>> orderByPredicate, OrderByType orderByType, bool blUseNoLock = false)
|
{
|
return await _dal.QueryGoodWithDefaultProductAsync(predicate, orderByPredicate, orderByType, blUseNoLock);
|
}
|
|
/// <summary>
|
/// 根据条件查询一定数量数据(用于组件)
|
/// </summary>
|
/// <param name="predicate">条件表达式树</param>
|
/// <param name="take">获取数量</param>
|
/// <param name="orderByPredicate">排序字段</param>
|
/// <param name="orderByType">排序顺序</param>
|
/// <param name="blUseNoLock">是否使用WITH(NOLOCK)</param>
|
/// <param name="isDataCache">是否缓存</param>
|
/// <param name="cacheTimes">缓存时间(分钟)</param>
|
/// <returns></returns>
|
public async Task<List<GoodListDTO>> QueryListByComponentsAsync(Expression<Func<GoodListDTO, bool>> predicate,
|
int take,
|
Expression<Func<GoodListDTO, object>> orderByPredicate, OrderByType orderByType, bool blUseNoLock = false,
|
bool isDataCache = false, int cacheTimes = int.MaxValue)
|
{
|
return await _dal.QueryListByComponentsAsync(predicate, take, orderByPredicate, orderByType, blUseNoLock,
|
isDataCache, cacheTimes);
|
}
|
|
|
/// <summary>
|
/// 根据条件查询一定数量数据(用于组件)
|
/// </summary>
|
/// <param name="predicate">条件表达式树</param>
|
/// <param name="take">获取数量</param>
|
/// <param name="orderByPredicate">排序字段</param>
|
/// <param name="orderByType">排序顺序</param>
|
/// <param name="blUseNoLock">是否使用WITH(NOLOCK)</param>
|
/// <param name="isDataCache">是否缓存</param>
|
/// <param name="cacheTimes">缓存时间(分钟)</param>
|
/// <returns></returns>
|
public async Task<List<GoodListDTO>> QueryListByComponentsAsync(Expression<Func<GoodListDTO, bool>> predicate,
|
int take, string orderByType = "", bool blUseNoLock = false,
|
bool isDataCache = false, int cacheTimes = int.MaxValue)
|
{
|
return await _dal.QueryListByComponentsAsync(predicate, take, orderByType, blUseNoLock,
|
isDataCache, cacheTimes);
|
}
|
|
|
/// <summary>
|
/// 根据类型获取商品数据(用于PC,H5)
|
/// </summary>
|
/// <param name="predicate">条件表达式树</param>
|
/// <param name="take">获取数量</param>
|
/// <param name="orderByPredicate">排序字段</param>
|
/// <param name="orderByType">排序顺序</param>
|
/// <param name="blUseNoLock">是否使用WITH(NOLOCK)</param>
|
/// <param name="isDataCache">是否缓存</param>
|
/// <param name="cacheTimes">缓存时间(分钟)</param>
|
public async Task<List<GoodListDTO>> QueryListByTypeAsync(Expression<Func<GoodListDTO, bool>> predicate, int take, Expression<Func<GoodListDTO, object>> orderByPredicate, OrderByType orderByType,
|
bool blUseNoLock = false, bool isDataCache = false, int cacheTimes = int.MaxValue)
|
{
|
return await _dal.QueryListByTypeAsync(predicate, take, orderByPredicate, orderByType, blUseNoLock, isDataCache, cacheTimes);
|
}
|
}
|
}
|