package co.yixiang.yshop.module.order.service.storeorder;

import co.yixiang.yshop.framework.common.util.collection.CollectionUtils;
import co.yixiang.yshop.module.distributor.api.DistributorOrderApi;
import co.yixiang.yshop.module.distributor.api.dto.DistributorOrderDTO;
import co.yixiang.yshop.module.distributor.api.dto.DistributorProductDTO;
import co.yixiang.yshop.module.distributor.enums.DistributorProductTypeEnum;
import co.yixiang.yshop.module.order.controller.admin.storeorder.vo.StoreOrderRespVO;
import co.yixiang.yshop.module.order.controller.admin.storeorderdetail.vo.StoreOrderDetailExportReqVO;
import co.yixiang.yshop.module.order.dal.dataobject.storeorderdetail.StoreOrderDetailDO;
import co.yixiang.yshop.module.order.service.storeorderdetail.StoreOrderDetailService;
import co.yixiang.yshop.module.product.dal.dataobject.storeproduct.StoreProductDO;
import co.yixiang.yshop.module.product.dal.dataobject.storeproductattrvalue.StoreProductAttrValueDO;
import co.yixiang.yshop.module.product.service.storeproduct.StoreProductService;
import co.yixiang.yshop.module.product.service.storeproductattrvalue.StoreProductAttrValueService;
import lombok.extern.slf4j.Slf4j;
import org.springframework.stereotype.Service;
import org.springframework.validation.annotation.Validated;

import javax.annotation.Resource;
import java.util.ArrayList;
import java.util.List;
import java.util.Map;
import java.util.stream.Collectors;

@Slf4j
@Service
@Validated
public class AppDistributorOrderFacadeImpl implements AppDistributorOrderFacade {

    @Resource
    private StoreOrderService storeOrderService;

    @Resource
    private StoreOrderDetailService storeOrderDetailService;

    @Resource
    private StoreProductService storeProductService;

    @Resource
    private StoreProductAttrValueService storeProductAttrValueService;

    @Resource
    private DistributorOrderApi distributorOrderApi;

    @Override
    public void createDistributorOrder(DistributorOrderDTO distributorOrderDTO) {
        // 处理订单
        distributorOrderApi.createDistributorOrder(this.makeDistributorOrderDTO(distributorOrderDTO));
    }

    @Override
    public void cancelDistributorOrder(DistributorOrderDTO distributorOrderDTO) {
        // 获取全部详情
        List<StoreOrderDetailDO> storeOrderDetailList = storeOrderDetailService.getStoreOrderDetailList(new StoreOrderDetailExportReqVO().setOid(distributorOrderDTO.getOid()));
        // 所有详情id
        List<Long> ids = CollectionUtils.convertList(storeOrderDetailList, StoreOrderDetailDO::getId);
        distributorOrderApi.cancelDistributorOrder(ids);
    }

    @Override
    public void updateDistributorOrder(DistributorOrderDTO distributorOrderDTO) {
        distributorOrderApi.updateDistributorOrder(this.makeDistributorOrderDTO(distributorOrderDTO));
    }

    private DistributorOrderDTO makeDistributorOrderDTO(DistributorOrderDTO distributorOrderDTO) {
        List<DistributorProductDTO> productDTOList = new ArrayList<>();

        // 获取订单
        StoreOrderRespVO storeOrder = storeOrderService.getStoreOrder(distributorOrderDTO.getOid());
        // 获取全部详情
        List<StoreOrderDetailDO> storeOrderDetailList = storeOrderDetailService.getStoreOrderDetailList(new StoreOrderDetailExportReqVO().setOid(distributorOrderDTO.getOid()));

        // 所有商品id
        List<Long> productIds = CollectionUtils.convertList(storeOrderDetailList, StoreOrderDetailDO::getProductId);
        List<StoreProductDO> storeProductList = storeProductService.getStoreProductList(productIds);
        Map<Long, StoreProductDO> storeProductMap = storeProductList.stream().collect(Collectors.toMap(StoreProductDO::getId, p -> p, (existingValue, newValue) -> existingValue));

        // 所有商品唯一值
        List<String> uniques = CollectionUtils.convertList(storeOrderDetailList, StoreOrderDetailDO::getProductAttrUnique);
        List<StoreProductAttrValueDO> storeProductAttrValueList = storeProductAttrValueService.getStoreProductAttrValueListByUniques(uniques);
        Map<String, StoreProductAttrValueDO> storeProductAttrValueMap = storeProductAttrValueList.stream().collect(Collectors.toMap(StoreProductAttrValueDO::getUnique, p -> p, (existingValue, newValue) -> existingValue));

        // 赋值
        distributorOrderDTO.setOrderId(storeOrder.getOrderId());
        distributorOrderDTO.setUserId(storeOrder.getUid());
        distributorOrderDTO.setUserName(storeOrder.getRealName());
        distributorOrderDTO.setDistributorId(storeOrder.getDistributorId());

        storeOrderDetailList.forEach(storeOrderDetailDO -> {
            Long productId = storeOrderDetailDO.getProductId();
            DistributorProductDTO distributorProductDTO = new DistributorProductDTO();

            StoreProductDO storeProductDO = storeProductMap.get(productId);
            if (storeProductDO.getIsDistribution().equals(DistributorProductTypeEnum.YES.getType())) {
                distributorProductDTO.setProductId(productId);
                distributorProductDTO.setProductName(storeProductDO.getStoreName());
                distributorProductDTO.setProductOriginalPrice(storeOrderDetailDO.getOriginalPrice());
                distributorProductDTO.setProductPrice(storeOrderDetailDO.getPrice());
                distributorProductDTO.setDetailId(storeOrderDetailDO.getId());
                distributorProductDTO.setDistributionRule(storeProductDO.getDistributionRule());
                distributorProductDTO.setDistributionPurchase(storeProductDO.getDistributionPurchase());
                distributorProductDTO.setDistributionProductSettlement(storeProductDO.getDistributionProductSettlement());
                distributorProductDTO.setDistributionWagesSettlement(storeProductDO.getDistributionWagesSettlement());
                distributorProductDTO.setDistributionLevel(storeProductDO.getDistributionLevel());

                StoreProductAttrValueDO storeProductAttrValueDO = storeProductAttrValueMap.get(storeOrderDetailDO.getProductAttrUnique());
                distributorProductDTO.setProductAttrValueId(storeProductAttrValueDO.getId());
                distributorProductDTO.setFirstWages(storeProductAttrValueDO.getFirstWages());
                distributorProductDTO.setSecondWages(storeProductAttrValueDO.getSecondWages());
                productDTOList.add(distributorProductDTO);
            }
        });

        distributorOrderDTO.setProductDTOList(productDTOList);
        return distributorOrderDTO;
    }

}
