
package com.tmerclub.cloud.product.feign;

import cn.hutool.core.collection.CollUtil;
import cn.hutool.core.collection.CollectionUtil;
import com.tmerclub.cloud.api.product.feign.ShopCartFeignClient;
import com.tmerclub.cloud.common.order.vo.WarehouseVO;
import com.tmerclub.cloud.common.constant.Constant;
import com.tmerclub.cloud.common.constant.SysTypeEnum;
import com.tmerclub.cloud.common.order.constant.DeliveryType;
import com.tmerclub.cloud.common.order.dto.DvyTypeDTO;
import com.tmerclub.cloud.common.order.vo.ShopCartItemVO;
import com.tmerclub.cloud.common.product.constant.SpuMold;
import com.tmerclub.cloud.common.product.constant.SpuType;
import com.tmerclub.cloud.common.product.constant.SupplierDeliveryType;
import com.tmerclub.cloud.common.response.ServerResponseEntity;
import com.tmerclub.cloud.common.security.AuthUserContext;
import com.tmerclub.cloud.product.service.ShopCartItemService;
import com.tmerclub.cloud.product.service.ShopCartService;
import com.tmerclub.cloud.product.service.SkuComboService;
import com.tmerclub.cloud.product.service.WarehouseService;
import org.apache.dubbo.config.annotation.DubboService;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.beans.factory.annotation.Autowired;

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

/**
 * @author tmerclub
 * @date 2020/12/8
 */
@DubboService
public class ShopCartFeignController implements ShopCartFeignClient {

    private static final Logger log = LoggerFactory.getLogger(ShopCartFeignController.class);

    @Autowired
    private ShopCartService shopCartService;
    @Autowired
    private ShopCartItemService shopCartItemService;
    @Autowired
    private SkuComboService skuComboService;
    @Autowired
    private WarehouseService warehouseService;



    @Override
    public List<ShopCartItemVO> handleShopCartItem(List<ShopCartItemVO> shopCartItems, List<DvyTypeDTO> dvyTypes, Boolean isShopCartOrder) {

        // 组装购物车项数据
        shopCartItemService.assembleShopCartItem(shopCartItems, null, isShopCartOrder);
        shopCartItems.forEach(shopCartItemVO -> shopCartItemVO.setIsChecked(1));
        // 处理组合商品信息
        handleComboShopCart(shopCartItems);

        // 组装赠品信息 - 判断库存及插入赠品数据
        shopCartItemService.buildItemGiveawayInfo(shopCartItems);

        // 插入店铺仓库列表
        this.setWarehouseList(shopCartItems, dvyTypes);

        return shopCartItems;
    }


    @Override
    public List<ShopCartItemVO> getCheckedShopCartItems(Long addrId, List<DvyTypeDTO> dvyTypes) {
        List<ShopCartItemVO> shopCartItems = shopCartService.getUserShopCartItems();
        handleShopCartItem(shopCartItems, dvyTypes, Boolean.TRUE);
        return shopCartItems;
    }

    private void handleComboShopCart(List<ShopCartItemVO> shopCartItems) {
        List<ShopCartItemVO> comboShopCartItemList = shopCartItems.stream().filter(shopCartItemVO -> Objects.equals(shopCartItemVO.getMold(), SpuMold.COMBO.value())).toList();
        if(CollectionUtil.isEmpty(comboShopCartItemList)){
            return;
        }
        List<Long> skuIds = new ArrayList<>();
        for (ShopCartItemVO shopCartItemVO : comboShopCartItemList) {
            if (Objects.nonNull(shopCartItemVO.getSupplierDeliveryType()) && Objects.equals(shopCartItemVO.getSupplierDeliveryType(), SupplierDeliveryType.SUPPLIER_DELIVERY.value())) {
                skuIds.add(shopCartItemVO.getSupplierSkuId());
            } else {
                skuIds.add(shopCartItemVO.getSkuId());
            }
        }
        List<ShopCartItemVO> comboShopItems = skuComboService.getCombShopItemsAndBySkuIds(skuIds);
        // 放入组合的所有商品信息
        Map<Long, List<ShopCartItemVO>> skuComboMap = comboShopItems.stream().collect(Collectors.groupingBy(ShopCartItemVO::getMainComboSkuId));
        for (ShopCartItemVO mainShopCartItem : shopCartItems) {
            long skuId = mainShopCartItem.getSkuId();
            // 供应商商品,商家代销的组合商品,找到对应的供应商的skuId进行处理
            if (Objects.nonNull(mainShopCartItem.getSupplierDeliveryType()) && Objects.equals(mainShopCartItem.getSupplierDeliveryType(), SupplierDeliveryType.SUPPLIER_DELIVERY.value())) {
                skuId = mainShopCartItem.getSupplierSkuId();
            }
            if(!skuComboMap.containsKey(skuId)) {
                continue;
            }
            List<ShopCartItemVO> shopCartItemList = skuComboMap.get(skuId);

            for (ShopCartItemVO shopCartItemVO : shopCartItemList) {
                shopCartItemVO.setMainComboSpuId(mainShopCartItem.getSpuId());
                shopCartItemVO.setCartItemId(mainShopCartItem.getCartItemId());
                shopCartItemVO.setComboCount(mainShopCartItem.getCount());
                shopCartItemVO.setShopId(mainShopCartItem.getShopId());
                shopCartItemVO.setIsChecked(1);
            }
            shopCartItemService.assembleShopCartItem(shopCartItemList,mainShopCartItem, null);
            mainShopCartItem.setComboShopCartItems(shopCartItemList);
        }
    }


    @Override
    public void deleteItem(List<Long> shopCartItemIds) {
        Long userId = AuthUserContext.get().getUserId();
        shopCartService.deleteShopCartItemsByShopCartItemIds(userId, shopCartItemIds);
    }

    @Override
    public ServerResponseEntity<Void> updateIsClosedByShopIds(List<Long> shopIds, Integer isClose) {
        shopCartService.updateIsClosedByShopIds(shopIds, isClose);
        return ServerResponseEntity.success();
    }

    @Override
    public void deleteCartByComboUpdate(List<Long> comboIdList, Long spuId, Long skuId) {
        shopCartService.deleteCartByComboUpdate(comboIdList, spuId, skuId);
    }

    @Override
    public ServerResponseEntity<Void> deleteCartByComboIdAndSpuIdS(Long comboId, List<Long> spuIdList) {
        shopCartService.deleteCartByComboIdAndSpuIdS(comboId, spuIdList);
        return ServerResponseEntity.success();
    }

    @Override
    public void deleteCartByComboIdAndSkuIdS(Long comboId, List<Long> spuIdList) {
        shopCartService.deleteCartByComboIdAndSkuIdS(comboId, spuIdList);
    }

    @Override
    public ServerResponseEntity<Void> updateCartSpuPriceByComboIdAndSkuId(Long comboId, Long skuId, Long price) {
        shopCartService.updateCartSpuPriceByComboIdAndSkuId(comboId, skuId, price);
        return ServerResponseEntity.success();
    }

    @Override
    public ServerResponseEntity<List<Long>> skuIdListByComboMainSkuId(List<Long> skuId) {
        List<Long> skuIdList = shopCartService.skuIdListByComboMainSkuId(skuId);
        return ServerResponseEntity.success(skuIdList);
    }

    @Override
    public void updateCartComboCount(Long comboId, Long spuId, Integer count) {
        shopCartService.updateCartComboCount(comboId, spuId, count);
    }

    @Override
    public void deleteShopCartItemsByShopCartItemIds(Long userId, List<Long> shopCartItemIds) {
        log.info("提交订单，删除购物车商品.....用户id:{}, 购物车项id:{}", userId, shopCartItemIds);
        shopCartService.deleteShopCartItemsByShopCartItemIds(userId, shopCartItemIds);
    }




    private void setWarehouseList(List<ShopCartItemVO> shopCartItems, List<DvyTypeDTO> dvyTypes) {
        if (CollUtil.isEmpty(dvyTypes)) {
            return;
        }
        // 获取快递配送的店铺Id列表
        List<Long> dvyShopIds = dvyTypes.stream()
                .filter(dvyTypeDTO -> Objects.equals(dvyTypeDTO.getDvyType(), DeliveryType.DELIVERY.value())).map(DvyTypeDTO::getShopId).toList();
        // Map<id, 类型：供应商、商家>
        Map<String, List<WarehouseVO>> warehouseMap = new HashMap<>(dvyShopIds.size() * 2);
        for (ShopCartItemVO shopCartItem : shopCartItems) {
            // 实物商品，且只有一个默认仓库，也不需要获取店铺仓库列表
            if (notWarehouse(shopCartItem, dvyShopIds)) {
                continue;
            }
            shopCartItem.setWarehouseList(this.listWarehouse(warehouseMap, shopCartItem));
            // 赠品列表
            if (CollUtil.isNotEmpty(shopCartItem.getGiveawayShopCartItemList())) {
                for (ShopCartItemVO giveawayShopCartItem : shopCartItem.getGiveawayShopCartItemList()) {
                    if (realOnlyOnePoint(giveawayShopCartItem)) {
                        continue;
                    }
                    giveawayShopCartItem.setWarehouseList(this.listWarehouse(warehouseMap, giveawayShopCartItem));
                }
            }
            // 组合sku列表
            if (CollUtil.isNotEmpty(shopCartItem.getComboShopCartItems())) {
                for (ShopCartItemVO comboShopCartItem : shopCartItem.getComboShopCartItems()) {
                    if (realOnlyOnePoint(comboShopCartItem)) {
                        continue;
                    }
                    comboShopCartItem.setWarehouseList(this.listWarehouse(warehouseMap, comboShopCartItem));
                }
            }
        }
    }

    private List<WarehouseVO> listWarehouse(Map<String, List<WarehouseVO>> shopMap, ShopCartItemVO shopCartItem) {
        Long id;
        SysTypeEnum sysTypeEnum;
        // 供应商配送，就填供应商id
        if (Objects.equals(shopCartItem.getSupplierDeliveryType(), SupplierDeliveryType.SUPPLIER_DELIVERY.value())) {
            id = shopCartItem.getSupplierId();
            sysTypeEnum = SysTypeEnum.SUPPLIER;
        } else {
            id = shopCartItem.getShopId();
            sysTypeEnum = SysTypeEnum.MULTISHOP;
        }
        String key = id + Constant.UNDERLINE + sysTypeEnum.value();
        if (shopMap.containsKey(key)) {
            return shopMap.get(key);
        }
        List<WarehouseVO> warehouseList = warehouseService.listWarehouseByShopId(id, sysTypeEnum.value());
        shopMap.put(id + Constant.UNDERLINE + sysTypeEnum.value(), warehouseList);
        return warehouseList;
    }

    private static boolean notWarehouse(ShopCartItemVO shopCartItem, List<Long> dvyShopIds) {
        // 虚拟商品、积分商品、用户自提、同城配送都不需要获取店铺仓库列表
        boolean notWarehouse =  Objects.equals(shopCartItem.getMold(), SpuMold.VIRTUAL.value()) ||
                Objects.equals(shopCartItem.getSpuType(), SpuType.SCORE.value()) ||
                !dvyShopIds.contains(shopCartItem.getShopId());
        if (notWarehouse) {
            return true;
        }

        if (realOnlyOnePoint(shopCartItem)) {
            return true;
        }
        return false;
    }

    private static boolean realOnlyOnePoint(ShopCartItemVO shopCartItem) {
        // 实物商品，没有赠品，且只有一个默认仓库，也不需要获取店铺仓库列表
        boolean realOnlyOnePoint = Objects.equals(shopCartItem.getMold(), SpuMold.REAL.value()) &&
                shopCartItem.getStockPointList().size() <= 1 &&
                CollUtil.isEmpty(shopCartItem.getGiveawayShopCartItemList());
        if (realOnlyOnePoint) {
            return true;
        }
        return false;
    }

}
