...
|
...
|
@@ -27,6 +27,7 @@ import java.math.BigDecimal; |
|
|
import java.util.List;
|
|
|
import java.util.Objects;
|
|
|
import java.util.Optional;
|
|
|
import java.util.function.Supplier;
|
|
|
|
|
|
import static com.yohoufo.order.charge.model.ChargeParam.*;
|
|
|
import static com.yohoufo.order.constants.ApiVersionConfig.ApiVersion;
|
...
|
...
|
@@ -85,62 +86,72 @@ public class ChargeService { |
|
|
private void chooseOptimal(ChargeContext context){
|
|
|
ChargeParam chargeParam = context.getChargeParam();
|
|
|
ChargeGoods chargeGoods = context.getChargeGoods();
|
|
|
|
|
|
int uid = chargeParam.getUid();
|
|
|
int skup = chargeGoods.getSkup();
|
|
|
|
|
|
List<ShoppingPromotion> useablePromotionList = chargeGoods.getUseablePromotionList();
|
|
|
|
|
|
ChargeResult chargeResult = context.getChargeResult();
|
|
|
Double finalAmountOfCutPromotion0 = chargeResult.getFinalAmountOfCutPromotion();
|
|
|
|
|
|
|
|
|
double oldFinalAmount = chargeResult.getFinalAmount();
|
|
|
//calculate promotion
|
|
|
List<ShoppingPromotion> useablePromotionList = chargeGoods.getUseablePromotionList();
|
|
|
Double cutAmountOfPromotion = chargeResult.getFinalAmountCutPromotion() == null ? 0D : chargeResult.getFinalAmountCutPromotion();
|
|
|
Supplier<Double> finalAmountAfterCutPromotionSupplier = () -> {
|
|
|
double finalAmountAfterCutPromotion = YHMath.sub(oldFinalAmount, cutAmountOfPromotion);
|
|
|
logger.info("chooseOptimal of coupons and promotions uid {} skup {} cutAmountOfPromotion {} finalAmountAfterCutPromotion {} useablePromotionList {}",
|
|
|
uid, skup, cutAmountOfPromotion, finalAmountAfterCutPromotion, useablePromotionList);
|
|
|
return finalAmountAfterCutPromotion;
|
|
|
};
|
|
|
//calulate coupons
|
|
|
//用券优惠的总金额
|
|
|
Double finalAmountOfCutCoupons = chargeResult.getFinalAmountOfCutCoupons();
|
|
|
boolean useActivityCoupon = Objects.nonNull(finalAmountOfCutCoupons);
|
|
|
Supplier<Double> finalAmountAfterCutCuponsSupplier = ()-> {
|
|
|
double finalAmountAfterCutCupons = useActivityCoupon ? YHMath.sub(oldFinalAmount, finalAmountOfCutCoupons) : chargeResult.getFinalAmount() ;
|
|
|
logger.info("chooseOptimal of coupons and promotions uid {} skup {} finalAmountAfterCutCupons {} finalAmountOfCutCupons {}",
|
|
|
uid, skup, finalAmountAfterCutCupons, finalAmountOfCutCoupons);
|
|
|
return finalAmountAfterCutCupons;
|
|
|
};
|
|
|
|
|
|
//做优惠力度比较
|
|
|
boolean existUseablePromotion = CollectionUtils.isNotEmpty(useablePromotionList);
|
|
|
|
|
|
Double finalAmountOfCutCoupons0 = chargeResult.getFinalAmountOfCutCoupons();
|
|
|
boolean useActivityCoupon = Objects.nonNull(finalAmountOfCutCoupons0);
|
|
|
double finalAmountOfCutCupons = useActivityCoupon ? finalAmountOfCutCoupons0.doubleValue() : chargeResult.getFinalAmount() ;
|
|
|
logger.info("chooseOptimal of coupons and promotions uid {} skup {} finalAmountOfCutPromotion {} finalAmountOfCutCupons {} useablePromotionList {}",
|
|
|
uid, skup, finalAmountOfCutPromotion0, finalAmountOfCutCoupons0, useablePromotionList);
|
|
|
double finalAmount;
|
|
|
PromotionMutexLock promotionMutexLock = new PromotionMutexLock();
|
|
|
//有促销时 尝试比较促销和优惠券计算的结果
|
|
|
if (existUseablePromotion){
|
|
|
int compareResult = finalAmountCompare(finalAmountOfCutPromotion0, finalAmountOfCutCoupons0);
|
|
|
if (compareResult < 0){
|
|
|
finalAmount = finalAmountOfCutPromotion0.doubleValue();
|
|
|
int compareResult = finalAmountCompare(cutAmountOfPromotion, finalAmountOfCutCoupons);
|
|
|
if (compareResult > 0){
|
|
|
finalAmount = finalAmountAfterCutPromotionSupplier.get();
|
|
|
promotionMutexLock.setUsePromotion(true);
|
|
|
}else if(compareResult == 0){
|
|
|
//相等有两种情况 1.两个都为空 2 都不为空
|
|
|
if (useActivityCoupon){
|
|
|
//not null -> equals
|
|
|
//优先推荐促销
|
|
|
finalAmount = finalAmountOfCutCupons;
|
|
|
promotionMutexLock.setUsePromotion(true);
|
|
|
finalAmount = finalAmountAfterCutCuponsSupplier.get();
|
|
|
promotionMutexLock.setUseActivityCoupons(true);
|
|
|
}else{
|
|
|
//equals by null
|
|
|
finalAmount = chargeResult.getFinalAmount();
|
|
|
finalAmount = oldFinalAmount;
|
|
|
}
|
|
|
}else {
|
|
|
finalAmount = finalAmountOfCutCupons;
|
|
|
finalAmount = finalAmountAfterCutCuponsSupplier.get();
|
|
|
promotionMutexLock.setUseActivityCoupons(true);
|
|
|
}
|
|
|
|
|
|
}else{
|
|
|
//没有促销时 直接使用券后价格
|
|
|
finalAmount = finalAmountOfCutCupons;
|
|
|
finalAmount = finalAmountAfterCutCuponsSupplier.get();
|
|
|
promotionMutexLock.setUseActivityCoupons(true);
|
|
|
}
|
|
|
|
|
|
|
|
|
logger.info("chooseOptimal of coupons and promotions uid {} skup {} finalAmountOfCutPromotion {} finalAmountOfCutCupons {} useablePromotionList {} finalAmount {}",
|
|
|
uid, skup, finalAmountOfCutPromotion0, finalAmountOfCutCupons, useablePromotionList, finalAmount);
|
|
|
logger.info("chooseOptimal of coupons and promotions uid {} skup {} finalAmountOfCutPromotion {} finalAmountOfCutCupons {} useablePromotionList {} oldfinal {} finalAmount {}",
|
|
|
uid, skup, cutAmountOfPromotion, finalAmountOfCutCoupons, useablePromotionList, oldFinalAmount, finalAmount);
|
|
|
final double minLimit = 0.01D;
|
|
|
if (finalAmount < minLimit){
|
|
|
logger.warn("chooseOptimal use protected action uid {} skup {} oldFinalAmount {} finalAmount {} cutAmountOfPromotion {} finalAmountOfCutCoupons {}",
|
|
|
uid, skup, oldFinalAmount, finalAmount, cutAmountOfPromotion, finalAmountOfCutCoupons);
|
|
|
finalAmount = minLimit;
|
|
|
}
|
|
|
chargeResult.setFinalAmount(finalAmount);
|
|
|
chargeResult.setPromotionMutexLock(promotionMutexLock);
|
|
|
|
|
|
|
|
|
//
|
|
|
|
|
|
}
|
|
|
|
|
|
|
...
|
...
|
@@ -572,7 +583,14 @@ public class ChargeService { |
|
|
double couponPayAmount = Math.min(chargeContext.getChargeGoods().getRealPrice().doubleValue(), activityCouponsBo.getCouponAmount().doubleValue());
|
|
|
double oldFinalAmount = chargeResult.getFinalAmount();
|
|
|
double newFinalAmount = YHMath.sub(oldFinalAmount, couponPayAmount);
|
|
|
chargeResult.setFinalAmountOfCutCoupons(newFinalAmount);
|
|
|
Double oldFinalAmountOfCutCoupons = chargeResult.getFinalAmountOfCutCoupons();
|
|
|
double newFinalAmountOfCutCoupons;
|
|
|
if (Objects.isNull(oldFinalAmountOfCutCoupons)){
|
|
|
newFinalAmountOfCutCoupons = couponPayAmount;
|
|
|
}else {
|
|
|
newFinalAmountOfCutCoupons = YHMath.add(oldFinalAmountOfCutCoupons, couponPayAmount);
|
|
|
}
|
|
|
chargeResult.setFinalAmountOfCutCoupons(newFinalAmountOfCutCoupons);
|
|
|
CouponPayResult couponPayResult = CouponPayResult.builder().couponCode(activityCouponsBo.getCouponCode())
|
|
|
.couponAmount(couponPayAmount).couponType(activityCouponsBo.getCouponType()).build();
|
|
|
logger.info("[{}] step activity coupon charge,oldFinalAmount:{},newFinalAmount of cut coupons:{}",
|
...
|
...
|
|