库存扣减,库存回滚问题处理。
之前存在商品取消后,自动回滚库存,可是忽略了商品取消可能是因为库存不足导致的问题。
This commit is contained in:
parent
7ce5b517fc
commit
e4b968e0af
@ -12,6 +12,7 @@ import cn.lili.modules.order.order.service.OrderService;
|
|||||||
import cn.lili.modules.promotion.entity.dos.PromotionGoods;
|
import cn.lili.modules.promotion.entity.dos.PromotionGoods;
|
||||||
import cn.lili.modules.promotion.entity.enums.PromotionTypeEnum;
|
import cn.lili.modules.promotion.entity.enums.PromotionTypeEnum;
|
||||||
import cn.lili.modules.promotion.service.PromotionGoodsService;
|
import cn.lili.modules.promotion.service.PromotionGoodsService;
|
||||||
|
import lombok.extern.slf4j.Slf4j;
|
||||||
import org.springframework.beans.factory.annotation.Autowired;
|
import org.springframework.beans.factory.annotation.Autowired;
|
||||||
import org.springframework.data.redis.core.StringRedisTemplate;
|
import org.springframework.data.redis.core.StringRedisTemplate;
|
||||||
import org.springframework.data.redis.core.script.DefaultRedisScript;
|
import org.springframework.data.redis.core.script.DefaultRedisScript;
|
||||||
@ -26,9 +27,12 @@ import java.util.List;
|
|||||||
* @author Chopper
|
* @author Chopper
|
||||||
* @date 2020-07-03 11:20
|
* @date 2020-07-03 11:20
|
||||||
*/
|
*/
|
||||||
|
@Slf4j
|
||||||
@Service
|
@Service
|
||||||
public class StockUpdateExecute implements OrderStatusChangeEvent {
|
public class StockUpdateExecute implements OrderStatusChangeEvent {
|
||||||
|
|
||||||
|
//出库失败消息
|
||||||
|
static String outOfStockMessage = "库存不足,出库失败";
|
||||||
//Redis
|
//Redis
|
||||||
@Autowired
|
@Autowired
|
||||||
private StringRedisTemplate stringRedisTemplate;
|
private StringRedisTemplate stringRedisTemplate;
|
||||||
@ -52,7 +56,7 @@ public class StockUpdateExecute implements OrderStatusChangeEvent {
|
|||||||
|
|
||||||
switch (orderMessage.getNewStatus()) {
|
switch (orderMessage.getNewStatus()) {
|
||||||
case PAID: {
|
case PAID: {
|
||||||
|
//获取订单详情
|
||||||
OrderDetailVO order = orderService.queryDetail(orderMessage.getOrderSn());
|
OrderDetailVO order = orderService.queryDetail(orderMessage.getOrderSn());
|
||||||
//库存key 和 扣减数量
|
//库存key 和 扣减数量
|
||||||
List<String> keys = new ArrayList<>();
|
List<String> keys = new ArrayList<>();
|
||||||
@ -67,33 +71,41 @@ public class StockUpdateExecute implements OrderStatusChangeEvent {
|
|||||||
Boolean skuResult = stringRedisTemplate.execute(quantityScript, keys, values.toArray());
|
Boolean skuResult = stringRedisTemplate.execute(quantityScript, keys, values.toArray());
|
||||||
//如果库存扣减都成功,则记录成交订单
|
//如果库存扣减都成功,则记录成交订单
|
||||||
if (Boolean.TRUE.equals(skuResult)) {
|
if (Boolean.TRUE.equals(skuResult)) {
|
||||||
|
log.info("库存扣减成功,参数为{};{}", keys, values);
|
||||||
//库存确认之后对结构处理
|
//库存确认之后对结构处理
|
||||||
orderService.afterOrderConfirm(orderMessage.getOrderSn());
|
orderService.afterOrderConfirm(orderMessage.getOrderSn());
|
||||||
//成功之后,同步库存
|
//成功之后,同步库存
|
||||||
synchroDB(order);
|
synchroDB(order);
|
||||||
} else {
|
} else {
|
||||||
|
log.info("库存扣件失败,变更缓存key{} 变更缓存value{}", keys, values);
|
||||||
//失败之后取消订单
|
//失败之后取消订单
|
||||||
this.errorOrder(orderMessage.getOrderSn());
|
this.errorOrder(orderMessage.getOrderSn());
|
||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
case CANCELLED: {
|
case CANCELLED: {
|
||||||
|
//获取订单详情
|
||||||
OrderDetailVO order = orderService.queryDetail(orderMessage.getOrderSn());
|
OrderDetailVO order = orderService.queryDetail(orderMessage.getOrderSn());
|
||||||
if (order.getOrder().getPayStatus().equals(PayStatusEnum.PAID.name())) {
|
//判定是否已支付 并且 非库存不足导致库存回滚 则需要考虑订单库存返还业务
|
||||||
|
if (order.getOrder().getPayStatus().equals(PayStatusEnum.PAID.name()) && order.getOrder().getCancelReason().equals(outOfStockMessage)) {
|
||||||
|
//库存key 和 还原数量
|
||||||
|
List<String> keys = new ArrayList<>();
|
||||||
|
List<String> values = new ArrayList<>();
|
||||||
|
|
||||||
|
//返还商品库存,促销库存不与返还,不然前台展示层有展示逻辑错误
|
||||||
for (OrderItem orderItem : order.getOrderItems()) {
|
for (OrderItem orderItem : order.getOrderItems()) {
|
||||||
if (PromotionTypeEnum.haveStock(orderItem.getPromotionType())) {
|
keys.add(GoodsSkuService.getStockCacheKey(orderItem.getSkuId()));
|
||||||
PromotionTypeEnum promotionTypeEnum = PromotionTypeEnum.valueOf(orderItem.getPromotionType());
|
int i = orderItem.getNum();
|
||||||
Integer goodsPromotionOriginStock = promotionGoodsService.getPromotionGoodsStock(promotionTypeEnum, orderItem.getPromotionId(), orderItem.getSkuId());
|
values.add(Integer.toString(i));
|
||||||
int goodsPromotionStock = goodsPromotionOriginStock + orderItem.getNum();
|
|
||||||
String promotionGoodsStockCacheKey = PromotionGoodsService.getPromotionGoodsStockCacheKey(promotionTypeEnum, orderItem.getPromotionId(), orderItem.getSkuId());
|
|
||||||
stringRedisTemplate.opsForValue().set(promotionGoodsStockCacheKey, Integer.toString(goodsPromotionStock));
|
|
||||||
}
|
}
|
||||||
String stockCacheKey = GoodsSkuService.getStockCacheKey(orderItem.getSkuId());
|
//批量脚本执行库存回退
|
||||||
Integer goodsOriginStock = goodsSkuService.getStock(orderItem.getSkuId());
|
Boolean skuResult = stringRedisTemplate.execute(quantityScript, keys, values.toArray());
|
||||||
int goodsStock = goodsOriginStock + orderItem.getNum();
|
|
||||||
stringRedisTemplate.opsForValue().set(stockCacheKey, Integer.toString(goodsStock));
|
//返还失败,则记录日志
|
||||||
|
if (Boolean.FALSE.equals(skuResult)) {
|
||||||
|
log.error("库存回退异常,keys:{},回复库存值为: {}", keys, values);
|
||||||
}
|
}
|
||||||
|
rollbackOrderStock(order);
|
||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
@ -108,7 +120,7 @@ public class StockUpdateExecute implements OrderStatusChangeEvent {
|
|||||||
* @param orderSn 失败入库订单信息
|
* @param orderSn 失败入库订单信息
|
||||||
*/
|
*/
|
||||||
private void errorOrder(String orderSn) {
|
private void errorOrder(String orderSn) {
|
||||||
orderService.systemCancel(orderSn, "库存不足,出库失败");
|
orderService.systemCancel(orderSn, outOfStockMessage);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
@ -132,8 +144,9 @@ public class StockUpdateExecute implements OrderStatusChangeEvent {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* 写入需要更改促销库存的商品
|
* 同步库存和促销库存
|
||||||
*
|
*
|
||||||
* @param order 订单
|
* @param order 订单
|
||||||
*/
|
*/
|
||||||
@ -159,6 +172,7 @@ public class StockUpdateExecute implements OrderStatusChangeEvent {
|
|||||||
if (PromotionTypeEnum.haveStock(orderItem.getPromotionType())) {
|
if (PromotionTypeEnum.haveStock(orderItem.getPromotionType())) {
|
||||||
PromotionTypeEnum promotionTypeEnum = PromotionTypeEnum.valueOf(orderItem.getPromotionType());
|
PromotionTypeEnum promotionTypeEnum = PromotionTypeEnum.valueOf(orderItem.getPromotionType());
|
||||||
PromotionGoods pGoods = promotionGoodsService.getPromotionGoods(promotionTypeEnum, orderItem.getPromotionId(), orderItem.getSkuId());
|
PromotionGoods pGoods = promotionGoodsService.getPromotionGoods(promotionTypeEnum, orderItem.getPromotionId(), orderItem.getSkuId());
|
||||||
|
//记录需要更新的促销库存信息
|
||||||
promotionKey.add(
|
promotionKey.add(
|
||||||
PromotionGoodsService.getPromotionGoodsStockCacheKey(
|
PromotionGoodsService.getPromotionGoodsStockCacheKey(
|
||||||
promotionTypeEnum,
|
promotionTypeEnum,
|
||||||
@ -170,6 +184,7 @@ public class StockUpdateExecute implements OrderStatusChangeEvent {
|
|||||||
goodsSkus.add(goodsSku);
|
goodsSkus.add(goodsSku);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
//批量获取商品库存
|
||||||
List skuStocks = cache.multiGet(skuKeys);
|
List skuStocks = cache.multiGet(skuKeys);
|
||||||
//循环写入商品库存
|
//循环写入商品库存
|
||||||
for (int i = 0; i < skuStocks.size(); i++) {
|
for (int i = 0; i < skuStocks.size(); i++) {
|
||||||
@ -188,8 +203,41 @@ public class StockUpdateExecute implements OrderStatusChangeEvent {
|
|||||||
}
|
}
|
||||||
promotionGoodsService.updateBatchById(promotionGoods);
|
promotionGoodsService.updateBatchById(promotionGoods);
|
||||||
}
|
}
|
||||||
|
//商品库存,包含sku库存集合,批量更新商品库存相关
|
||||||
|
goodsSkuService.updateGoodsStuck(goodsSkus);
|
||||||
|
|
||||||
|
log.info("订单确认,库存同步:商品信息--{};促销信息---{}", goodsSkus, promotionGoods);
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 恢复商品库存
|
||||||
|
*
|
||||||
|
* @param order 订单
|
||||||
|
*/
|
||||||
|
private void rollbackOrderStock(OrderDetailVO order) {
|
||||||
|
|
||||||
|
//sku商品
|
||||||
|
List<GoodsSku> goodsSkus = new ArrayList<>();
|
||||||
|
//sku库存key 集合
|
||||||
|
List<String> skuKeys = new ArrayList<>();
|
||||||
|
// 循环订单
|
||||||
|
for (OrderItem orderItem : order.getOrderItems()) {
|
||||||
|
skuKeys.add(GoodsSkuService.getStockCacheKey(orderItem.getSkuId()));
|
||||||
|
GoodsSku goodsSku = new GoodsSku();
|
||||||
|
goodsSku.setId(orderItem.getSkuId());
|
||||||
|
goodsSkus.add(goodsSku);
|
||||||
|
}
|
||||||
|
//批量获取商品库存
|
||||||
|
List skuStocks = cache.multiGet(skuKeys);
|
||||||
|
//循环写入商品SKU库存
|
||||||
|
for (int i = 0; i < skuStocks.size(); i++) {
|
||||||
|
goodsSkus.get(i).setQuantity(Integer.parseInt(skuStocks.get(i).toString()));
|
||||||
|
}
|
||||||
|
log.info("订单取消,库存还原:{}", goodsSkus);
|
||||||
|
//批量修改商品库存
|
||||||
|
goodsSkuService.updateBatchById(goodsSkus);
|
||||||
goodsSkuService.updateGoodsStuck(goodsSkus);
|
goodsSkuService.updateGoodsStuck(goodsSkus);
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
}
|
}
|
||||||
|
Loading…
x
Reference in New Issue
Block a user