package cn.freemud.service.impl;

import cn.freemud.entities.dto.*;
import cn.freemud.entities.dto.activity.ActivityQueryDto;
import cn.freemud.entities.dto.activity.ActivityQueryResponseDto;
import cn.freemud.entities.dto.calculate.*;
import cn.freemud.entities.dto.shoppingCart.ShoppingCartGoodsDto;
import cn.freemud.entities.vo.*;
import cn.freemud.enums.ActivityPromptEnum;
import cn.freemud.enums.ActivityTypeEnum;
import cn.freemud.enums.GiftTypeEnum;
import cn.freemud.service.ActivityService;
import cn.freemud.service.IPromotionService;
import cn.freemud.utils.WebUtil;
import lombok.experimental.var;
import org.apache.commons.collections4.CollectionUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;

import java.util.*;
import java.util.stream.Collectors;

/**
 * All rights Reserved, Designed By www.freemud.cn
 *
 * @version V1.0
 * @Title: FullPromotionService
 * @Package cn.freemud.service.impl
 * @Description:
 * @author: jiaxin.liu
 * @date: 2019/4/18 10:51
 * @Copyright: 2019 www.freemud.cn Inc. All rights reserved.
 * 注意：本内容仅限于上海非码科技内部传阅，禁止外泄以及用于其他的商业目
 */
@Service
public class FullPromotionService implements IPromotionService {

//    @Autowired
//    private PromotionSdkService promotionSdkService;

    @Autowired
    private ActivityService activityService;

    /**
     * 查询每满减和阶梯满减活动中的第一个，构建提示语，筛选出购物车内的参与满减的商品，计算总的优惠金额
     * @param couponPromotionVO
     * @param activityQueryDto
     * @param calculationDiscountResult
     * @param allCartGoodsList
     * @param shoppingCartGoodsResponseVo
     */
    @Override
    public void updateShoppingCartGoodsDiscount(CouponPromotionVO couponPromotionVO, ActivityQueryDto activityQueryDto, CalculationDiscountResult calculationDiscountResult, List<CartGoods> allCartGoodsList, ShoppingCartGoodsResponseVo shoppingCartGoodsResponseVo, UserLoginInfoDto userLoginInfoDto, ShoppingCartInfoRequestVo shoppingCartInfoRequestVo) {
        shoppingCartGoodsResponseVo.setActivityTip(new ActivityTip());
        List<ActivityTypeEnum> activityTypeEnums = new LinkedList<>();
        activityTypeEnums.add(ActivityTypeEnum.TYPE_11);
        activityTypeEnums.add(ActivityTypeEnum.TYPE_12);
        activityTypeEnums.add(ActivityTypeEnum.TYPE_230);
        //调用促销统一活动查询
        //过滤出参与的满减(目前只有每满减和阶梯满减)
        ActivityQueryResponseDto activityQueryResponseDto = activityService.queryActivityByType(activityQueryDto, activityTypeEnums, null);
        if (activityQueryResponseDto == null) {
            return ;
        }
        List<ActivityResponseDto> activityQueryDtoList = activityQueryResponseDto.getResult();
        if(CollectionUtils.isEmpty(activityQueryDtoList)){
            return;
        }

        PromotionMessageDto promotionMessageDto = new PromotionMessageDto();
        ActivityResponseDto activityResponseDto = activityQueryDtoList.get(0);
        promotionMessageDto.setActivityId(activityResponseDto.getActivityCode());
        promotionMessageDto.setActivityName(activityResponseDto.getActivityName());
        promotionMessageDto.setActivityType(activityResponseDto.getActivityType());
        promotionMessageDto.setPromotionAmount(0L);
        StringBuilder messageBuilder = new StringBuilder();
        ArrayList<ActivityList> activityList = new ArrayList<>();
        //没有加入购物车
        if (calculationDiscountResult == null) {
            // 因为没有促销活动的计算信息，所以没有加入购物车内
            List<BenefitBeanDto> benefitBeanDtos = activityResponseDto.getBenefits();
            //调用没有加入购物车的提示语的方法
            setMessageNotInShoppingCart(messageBuilder, activityResponseDto, benefitBeanDtos, activityList);
        }
        else{
            //促销返回满减提示语
            List<ActivityPrompt> activityPrompts = calculationDiscountResult.getActivityPrompts();
            List<Discount> discountList1 = calculationDiscountResult.getDiscounts();
            //构建提示语
            if (CollectionUtils.isNotEmpty(activityPrompts)){
                // 还差多少提示
                setMessageSatisfyCart(messageBuilder, activityPrompts, activityResponseDto, activityList);
            }else {
                setMessageNoSatisfyCart(messageBuilder, discountList1, activityList);
            }
        }

        promotionMessageDto.setPromotionMessage(messageBuilder.toString());
        ActivityTip activityTip = new ActivityTip();
        activityTip.setActivityCode(promotionMessageDto.getActivityId());
        activityTip.setActivityType(promotionMessageDto.getActivityType());
        activityTip.setActivityName(promotionMessageDto.getPromotionMessage());
        activityTip.setActivityList(activityList);
        shoppingCartGoodsResponseVo.setActivityTip(activityTip);
        if (calculationDiscountResult == null){
            return;
        }

        List<Discount> discountList = calculationDiscountResult.getDiscounts();
        if(CollectionUtils.isEmpty(discountList)){
            return;
        }

        //过滤出参与的满减(目前只有每满减和阶梯满减)
        List<Discount> fullDiscountsList = discountList
                .stream().filter(discount -> ActivityTypeEnum.TYPE_11.getCode().equals(discount.getType()) || ActivityTypeEnum.TYPE_12.getCode().equals(discount.getType()))
                .collect(Collectors.toList());
        if (CollectionUtils.isEmpty(fullDiscountsList)) {
            return;
        }
        //总的满减优惠金额
        long fullDiscount = 0L;
        for (Discount fullDiscounts : fullDiscountsList) {
            fullDiscount = fullDiscount + (fullDiscounts.getDiscount() == null ? 0 : fullDiscounts.getDiscount());
        }
        //设置到响应中
        shoppingCartGoodsResponseVo.setFullDiscount(fullDiscount);
        shoppingCartGoodsResponseVo.setProducts(allCartGoodsList);
        shoppingCartGoodsResponseVo.setProductsCount(allCartGoodsList.size());
    }

    @Override
    public void updateShoppingCartGoodsApportion(ShoppingCartGoodsResponseVo shoppingCartGoodsResponseVo, CalculationDiscountResult calculationDiscountResult, ShoppingCartGoodsDto shoppingCartGoodsDto, CreateOrderVo.PremiumExchangeActivity premiumExchangeActivity, ShoppingCartInfoRequestVo shoppingCartInfoRequestVo) {
        return;
    }

    //设置没有加入购物车的提示语
    private void setMessageNotInShoppingCart(StringBuilder messageBuilder, ActivityResponseDto activityResponseDto,
                                             List<BenefitBeanDto> benefitBeanDtos,
                                             ArrayList<ActivityList> activityList) {
        if(CollectionUtils.isEmpty(benefitBeanDtos)){
            return;
        }
        BenefitBeanDto benefitBeanDto = benefitBeanDtos.get(0);
        if (Objects.equals(ActivityTypeEnum.TYPE_11.getCode(), activityResponseDto.getActivityType())) {

            //此处的getCouponType == getPreferentialType 优惠类型
            if(ActivityPromptEnum.PreferentialTypeEnum.TO_ORDER_ITEM_QUANTITY.getCode().equals(activityResponseDto.getCouponType())) {

                messageBuilder
                        .append("购买 <span style=\"color:#fa5555\">")
                        .append(WebUtil.formatAmount(activityResponseDto.getDelayTimes() * 1.00 / 100) )
                        .append(" 元以上的商品可参与 <span style=\"color:#fa5555\">")
                        .append("每满 <span style=\"color:#fa5555\">")
                        .append(benefitBeanDto.getBenefitNumber())
                        .append("</span>件 减 <span style=\"color:#fa5555\">")
                        .append(WebUtil.formatAmount(benefitBeanDto.getDiscountAmount() * 1.00 / 100))
                        .append("</span> ")
                        .append("元 最高减 <span style=\"color:#fa5555\">")
                        .append(WebUtil.formatAmount(activityResponseDto.getMaxMoney() * 1.00 / 100))
                        .append("</span> 元");

                //满足  x 元 减 Y 元 ，最高 减 Z元
                ActivityList notInShopping = new ActivityList();
                notInShopping.setTipType(ActivityPromptEnum.TipTypeEnum.THIRTEEN.getCode());
                notInShopping.setSatisfy(benefitBeanDto.getBenefitNumber().toString());
                notInShopping.setDeduct(WebUtil.formatAmount(benefitBeanDto.getDiscountAmount() * 1.00 / 100).toString());
                notInShopping.setMaxDeduct(WebUtil.formatAmount(activityResponseDto.getMaxMoney() * 1.00 / 100).toString());
                notInShopping.setInvokeAmount(WebUtil.formatAmount(activityResponseDto.getDelayTimes() * 1.00 / 100).toString());                activityList.add(notInShopping);
            }else{
                messageBuilder.append("每满 <span style=\"color:#fa5555\">")
                        .append(WebUtil.formatAmount(benefitBeanDto.getThresholdAmount() * 1.00 / 100))
                        .append("</span> 减 <span style=\"color:#fa5555\">")
                        .append(WebUtil.formatAmount(benefitBeanDto.getDiscountAmount() * 1.00 / 100))
                        .append("</span> ")
                        .append("最高减 <span style=\"color:#fa5555\">")
                        .append(WebUtil.formatAmount(activityResponseDto.getMaxMoney() * 1.00 / 100))
                        .append("</span> 元");

                //满足  x 元 减 Y 元 ，最高 减 Z元
                ActivityList notInShopping = new ActivityList();
                notInShopping.setTipType(1);
                notInShopping.setSatisfy(WebUtil.formatAmount(benefitBeanDto.getThresholdAmount() * 1.00 / 100).toString());
                notInShopping.setDeduct(WebUtil.formatAmount(benefitBeanDto.getDiscountAmount() * 1.00 / 100).toString());
                notInShopping.setMaxDeduct(WebUtil.formatAmount(activityResponseDto.getMaxMoney() * 1.00 / 100).toString());
                activityList.add(notInShopping);
            }
        }
        if (Objects.equals(ActivityTypeEnum.TYPE_12.getCode(), activityResponseDto.getActivityType())) {
            int len = benefitBeanDtos.size();
            // // 购物车中无商品或者存在与满减互斥的活动
            if(ActivityPromptEnum.PreferentialTypeEnum.TO_ORDER_ITEM_QUANTITY.getCode().equals(activityResponseDto.getCouponType())) {
                for (int i = len - 1; i >= 0; i--) {
                    benefitBeanDto = benefitBeanDtos.get(i);
                    messageBuilder
                            .append("购买 <span style=\"color:#fa5555\">")
                            .append(WebUtil.formatAmount(activityResponseDto.getDelayTimes() * 1.00 / 100) )
                            .append(" 元以上的商品可参与 <span style=\"color:#fa5555\">")
                            .append("购买 <span style=\"color:#fa5555\">")
                            .append(WebUtil.formatAmount(activityResponseDto.getDelayTimes() * 1.00 / 100) )
                            .append(" 元以上的商品可参与 <span style=\"color:#fa5555\">")
                            .append("满 <span style=\"color:#fa5555\">")
                            .append(benefitBeanDto.getBenefitNumber())
                            .append("</span> 件减 <span style=\"color:#fa5555\">")
                            .append(WebUtil.formatAmount(benefitBeanDto.getDiscountAmount() * 1.00 / 100))
                            .append("</span> 元");
                    if (i > 0) {messageBuilder.append("，");}
                }
                //  阶梯满减：满足 X 元 减 Y 元,
                for (int j = len - 1; j >= 0; j--) {
                    benefitBeanDto = benefitBeanDtos.get(j);
                    cn.freemud.entities.vo.ActivityList notInShopping = new ActivityList();
                    notInShopping.setTipType(ActivityPromptEnum.TipTypeEnum.FOURTEEN.getCode());
                    notInShopping.setSatisfy(benefitBeanDto.getBenefitNumber().toString());
                    notInShopping.setDeduct(WebUtil.formatAmount(benefitBeanDto.getDiscountAmount() * 1.00 / 100).toString());
                    notInShopping.setInvokeAmount(WebUtil.formatAmount(activityResponseDto.getDelayTimes() * 1.00 / 100).toString());
                    activityList.add(notInShopping);
                }
            }else{
                for (int i = len - 1; i >= 0; i--) {
                benefitBeanDto = benefitBeanDtos.get(i);
                messageBuilder.append("满 <span style=\"color:#fa5555\">")
                        .append(WebUtil.formatAmount(benefitBeanDto.getThresholdAmount() * 1.00 / 100))
                        .append("</span> 减 <span style=\"color:#fa5555\">")
                        .append(WebUtil.formatAmount(benefitBeanDto.getDiscountAmount() * 1.00 / 100))
                        .append("</span> 元");
                if (i > 0) {
                    messageBuilder.append("，");
                }
            }
            //  阶梯满减：满足 X 元 减 Y 元,
            for (int j = len - 1; j >= 0; j--) {
                benefitBeanDto = benefitBeanDtos.get(j);
                cn.freemud.entities.vo.ActivityList notInShopping = new ActivityList();
                notInShopping.setTipType(2);
                notInShopping.setSatisfy(WebUtil.formatAmount(benefitBeanDto.getThresholdAmount() * 1.00 / 100).toString());
                notInShopping.setDeduct(WebUtil.formatAmount(benefitBeanDto.getDiscountAmount() * 1.00 / 100).toString());
                activityList.add(notInShopping);
            }
            }
        }
        if (Objects.equals(ActivityTypeEnum.TYPE_230.getCode(), activityResponseDto.getActivityType())) {
            ActivityList notInShopping = new ActivityList();
            // 规则:满5赠奶茶2件，炸鸡1件，满10赠布丁3件，牛奶1份，鸡翅2份，
            // 提示语：满5元可获赠奶茶*2，炸鸡*1
            //阶梯满赠
            notInShopping.setSatisfy(WebUtil.formatAmount(benefitBeanDto.getThresholdAmount() * 1.00 / 100).toString());
            if (GiftTypeEnum.TYPE_1.getType().equals(activityResponseDto.getActivitySubType())) {
                notInShopping.setTipType(6);
            }
            //每满赠
            else if (GiftTypeEnum.TYPE_2.getType().equals(activityResponseDto.getActivitySubType())) {
                notInShopping.setTipType(7);
            }
            Collections.sort(benefitBeanDtos);
            BenefitBeanDto dto = benefitBeanDtos.get(0);
            int len = dto.getSendGoodsList().size();
            notInShopping.setSatisfy(WebUtil.formatAmount(dto.getThresholdAmount() * 1.00 / 100).toString());
            List<ActivityList.SendGoods> sends = new ArrayList();
            for (int i = 0; i < len; i++) {
                ActivityList.SendGoods goods = new ActivityList.SendGoods();
                goods.setQty(dto.getSendGoodsList().get(i).getSendNumber());
                goods.setGoodsName(dto.getSendGoodsList().get(i).getGoodsName());
                sends.add(goods);
            }
            notInShopping.setSends(sends);
            activityList.add(notInShopping);
        }
    }

    /**
     * 设置加入商品满足购物车时的提示语
     *
     * @param messageBuilder
     * @param activityPrompts
     * @param activityResponseDto
     */
    private void setMessageSatisfyCart(StringBuilder messageBuilder, List<ActivityPrompt> activityPrompts
            , ActivityResponseDto activityResponseDto, ArrayList<ActivityList> activityList) {

        ActivityList satisfyList = new ActivityList();
        ActivityPrompt activityPrompt = activityPrompts.get(0);
        if (Objects.equals(ActivityTypeEnum.TYPE_11.getCode(), activityResponseDto.getActivityType()) || Objects.equals(ActivityTypeEnum.TYPE_12.getCode(), activityResponseDto.getActivityType())) {
            if (activityPrompt.getAlreadyDiscountAmount() == null || activityPrompt.getAlreadyDiscountAmount() == 0) {

                if(ActivityPromptEnum.PreferentialTypeEnum.TO_ORDER_ITEM_QUANTITY.getCode().equals(activityResponseDto.getCouponType())){
                    // 满足 X 元/件 减 Y 元 还差 Z元
                    satisfyList.setTipType(ActivityPromptEnum.TipTypeEnum.ELEVEN.getCode());
                    satisfyList.setSatisfy(activityPrompt.getThresholdQuantity().toString());
                    satisfyList.setDeduct(WebUtil.formatAmount(activityPrompt.getDiscountAmout() * 1.00 / 100).toString());
                    satisfyList.setMissing(String.valueOf(activityPrompt.getThresholdQuantity() - activityPrompt.getTotalQuantity()));
                    satisfyList.setInvokeAmount(WebUtil.formatAmount(activityResponseDto.getDelayTimes() * 1.00 / 100).toString());
                }else{
                    // 满足 X 元 减 Y 元 还差 Z元
                    satisfyList.setTipType(ActivityPromptEnum.TipTypeEnum.THREE.getCode());
                    satisfyList.setSatisfy(WebUtil.formatAmount(activityPrompt.getThresholdAmount() * 1.00 / 100).toString());
                    satisfyList.setDeduct(WebUtil.formatAmount(activityPrompt.getDiscountAmout() * 1.00 / 100).toString());
                    satisfyList.setMissing(WebUtil.formatAmount((activityPrompt.getThresholdAmount() - activityPrompt.getTotalAmount()) * 1.00 / 100).toString());
                }

                } else {
                Long toDiscountAmout;
                //每满减
                if (Objects.equals(ActivityTypeEnum.TYPE_11.getCode(), activityResponseDto.getActivityType())) {
                    toDiscountAmout = activityPrompt.getDiscountAmout() + activityPrompt.getAlreadyDiscountAmount();
                } else {
                    toDiscountAmout = activityPrompt.getDiscountAmout();
                }
                if(ActivityPromptEnum.PreferentialTypeEnum.TO_ORDER_ITEM_QUANTITY.getCode().equals(activityResponseDto.getCouponType())){
                    //已减 X 元 再买 Y 元 减 Z 元
                    satisfyList.setTipType(ActivityPromptEnum.TipTypeEnum.TWELVE.getCode());
                    satisfyList.setDeduct(WebUtil.formatAmount(activityPrompt.getAlreadyDiscountAmount() * 1.00 / 100).toString());
                    satisfyList.setAgainBuy(String.valueOf(activityPrompt.getThresholdQuantity() - activityPrompt.getTotalQuantity()));
                    satisfyList.setAgianDeduct(WebUtil.formatAmount(toDiscountAmout * 1.00 / 100).toString());
                    satisfyList.setInvokeAmount(WebUtil.formatAmount(activityResponseDto.getDelayTimes() * 1.00 / 100).toString());
                }else{
                    //已减 X 元 再买 Y 元 减 Z 元
                    satisfyList.setTipType(ActivityPromptEnum.TipTypeEnum.FOUR.getCode());
                    satisfyList.setDeduct(WebUtil.formatAmount(activityPrompt.getAlreadyDiscountAmount() * 1.00 / 100).toString());
                    satisfyList.setAgainBuy(WebUtil.formatAmount((activityPrompt.getThresholdAmount() - activityPrompt.getTotalAmount()) * 1.00 / 100).toString());
                    satisfyList.setAgianDeduct(WebUtil.formatAmount(toDiscountAmout * 1.00 / 100).toString());
                }
            }
        }
        if (Objects.equals(ActivityTypeEnum.TYPE_230.getCode(), activityResponseDto.getActivityType()) && CollectionUtils.isNotEmpty(activityPrompt.getSendGoods())) {

            satisfyList.setTipType(ActivityPromptEnum.TipTypeEnum.TEN.getCode());
            List<ActivityList.SendGoods> sends = new ArrayList();
            for (SendGoods sendGood : activityPrompt.getSendGoods()) {
                ActivityList.SendGoods send = new ActivityList.SendGoods();
                send.setGoodsName(sendGood.getGoodsName());
                send.setQty(sendGood.getSendNumber());
                sends.add(send);
            }
            satisfyList.setSends(sends);
            satisfyList.setSatisfy(WebUtil.formatAmount(activityPrompt.getThresholdAmount() * 1.00 / 100).toString());
            satisfyList.setMissing(WebUtil.formatAmount((activityPrompt.getThresholdAmount() - activityPrompt.getTotalAmount()) * 1.00 / 100).toString());
            if (GiftTypeEnum.TYPE_1.getType().equals(activityResponseDto.getActivitySubType())) {
                satisfyList.setTipType(ActivityPromptEnum.TipTypeEnum.EIGHT.getCode());
            }
            else {
                satisfyList.setTipType(ActivityPromptEnum.TipTypeEnum.SEVEN.getCode());
            }
            if (activityPrompt.getTotalAmount()>=activityPrompt.getThresholdAmount()) {
                if (GiftTypeEnum.TYPE_1.getType().equals(activityResponseDto.getActivitySubType())) {
                    satisfyList.setTipType(ActivityPromptEnum.TipTypeEnum.TEN.getCode());
                }
                else {
                    satisfyList.setTipType(ActivityPromptEnum.TipTypeEnum.SEVEN.getCode());
                }
            }
        }
        activityList.add(satisfyList);
    }

    /**
     * 设置加入商品不满足购物车时的提示语
     *
     * @param messageBuilder
     * @param discountList
     */
    private void setMessageNoSatisfyCart(StringBuilder messageBuilder, List<Discount> discountList, ArrayList<ActivityList> activityList) {
        discountList = discountList.parallelStream().filter(k -> (Objects.equals(ActivityTypeEnum.TYPE_11.getCode(), k.getType())
                || Objects.equals(ActivityTypeEnum.TYPE_12.getCode(), k.getType()))).collect(Collectors.toList());
        if (CollectionUtils.isEmpty(discountList)) {
            return;
        }
        //已减 X 元
        messageBuilder.append("已减 <span style=\"color:#fa5555\">")
                .append(WebUtil.formatAmount(discountList.get(0).getDiscount() * 1.00 / 100))
                .append("</span> 元");
        ActivityList noSatisfy = new ActivityList();
        noSatisfy.setTipType(5);
        noSatisfy.setDeduct(WebUtil.formatAmount(discountList.get(0).getDiscount() * 1.00 / 100).toString());
        activityList.add(noSatisfy);
    }
}
