package cn.freemud.management.adapter;

import cn.freemud.management.entities.dto.request.console.BizDTO;
import cn.freemud.management.entities.dto.request.console.ConsoleResponseDTO;
import cn.freemud.management.entities.dto.request.console.StoreInfoDTO;
import com.freemud.application.sdk.api.deliverycenter.dto.CreateDeliveryOrderRequestDto;
import com.freemud.application.sdk.api.ordercenter.entities.v1.OrderBeanV1;
import com.freemud.application.sdk.api.ordercenter.entities.v1.ProductBeanV1;
import com.freemud.application.sdk.api.ordercenter.enums.OrderType;
import org.apache.commons.collections4.CollectionUtils;
import org.apache.commons.lang.StringUtils;
import org.apache.commons.lang.math.NumberUtils;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.stereotype.Component;

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

@Component
public class DeliverySdkAdapter {

    @Value("${calculate.depatch.weight.partnerId:}")
    private List<String> calculateWeightPartnerId;

    /**
     * 创建配送单请求对象
     *
     * @param order
     * @param bizDTO
     * @param deliveryCallBackUrl
     * @return
     */
    public CreateDeliveryOrderRequestDto buildDeliveryOrderRequestDto(OrderBeanV1 order
            , ConsoleResponseDTO<BizDTO> bizDTO, String deliveryCallBackUrl) {
        CreateDeliveryOrderRequestDto deliveryOrderRequestDto = new CreateDeliveryOrderRequestDto();
        deliveryOrderRequestDto.setDepatchWeight(this.getDepatchWeightByOrder(order.getProductList(), order.getCompanyId()));
        deliveryOrderRequestDto.setSerialNumber(order.getOtherCode());
        deliveryOrderRequestDto.setOrderId(order.getOid());
        deliveryOrderRequestDto.setOrderRemark(order.getRemark());
        deliveryOrderRequestDto.setOrderTotalAmount(order.getAmount().intValue());
        deliveryOrderRequestDto.setOrderActualAmount(order.getAmount().intValue());
        deliveryOrderRequestDto.setPartnerId(order.getCompanyId());
        deliveryOrderRequestDto.setOrderChannel(order.getSource());
        StoreInfoDTO storeInfo = bizDTO.getBizVO().getStoreInfo();
        deliveryOrderRequestDto.setStoreId(storeInfo.getStoreId());
        deliveryOrderRequestDto.setStoreCode(storeInfo.getStoreCode());
        StringBuffer address = new StringBuffer(storeInfo.getCity())
                .append(storeInfo.getProvince())
                .append(storeInfo.getRegion())
                .append(storeInfo.getAddress());
        deliveryOrderRequestDto.setStoreAddress(address.toString());
        deliveryOrderRequestDto.setStoreLng(new BigDecimal(storeInfo.getLongitude()));
        deliveryOrderRequestDto.setStoreLat(new BigDecimal(storeInfo.getLatitude()));
        deliveryOrderRequestDto.setStorePhone(storeInfo.getPhone());
        deliveryOrderRequestDto.setStoreName(order.getShopName());
        deliveryOrderRequestDto.setCityName(storeInfo.getCity());
        deliveryOrderRequestDto.setReceiverName(StringUtils.isNotEmpty(order.getContactsName()) ? order.getContactsName() : order.getUserName());
        deliveryOrderRequestDto.setReceiverPrimaryPhone(order.getPhone());
        deliveryOrderRequestDto.setReceiverAddress(order.getAddress());
        deliveryOrderRequestDto.setReceiverLng(BigDecimal.valueOf(order.getLongitude()));
        deliveryOrderRequestDto.setReceiverLat(BigDecimal.valueOf(order.getLatitude()));
        deliveryOrderRequestDto.setOrderTime(new Date(order.getGmtCreate()));
        deliveryOrderRequestDto.setCallbackUrl(deliveryCallBackUrl);
        deliveryOrderRequestDto.setOrderClient(NumberUtils.toInt(order.getOrderClient()));
        // 预约单预计送到时间
        if (order.getGmtExpect() != null && order.getGmtExpect() != 0) {
            deliveryOrderRequestDto.setExpectTime(new Date(order.getGmtExpect()));
        }
        deliveryOrderRequestDto.setIsPre(order.getNewOrderType() == OrderType.RESERVED_EXPRESS.getIndex() ? 1 : 0);
        Optional.ofNullable(order.getProductList())
                .ifPresent(productList ->
                        deliveryOrderRequestDto.setProductInfos(productList.stream()
                                .filter(productBean -> Objects.nonNull(productBean.getPrice()))
                                .filter(productBean -> productBean.getPrice() > 0)
                                .map(productBean -> {
                                    CreateDeliveryOrderRequestDto.DeliveryProductInfo deliveryProductInfo = new CreateDeliveryOrderRequestDto.DeliveryProductInfo();
                                    deliveryProductInfo.setProductCode(productBean.getProductId());
                                    deliveryProductInfo.setProductName(productBean.getProductName());
                                    deliveryProductInfo.setProductNumber(productBean.getNumber());
                                    deliveryProductInfo.setProductPrice(productBean.getPrice().intValue());
                                    return deliveryProductInfo;
                                }).collect(Collectors.toCollection(LinkedList::new))));
        return deliveryOrderRequestDto;
    }

    private BigDecimal getDepatchWeightByOrder(List<ProductBeanV1> productList, String partnerId) {
        if (CollectionUtils.isEmpty(calculateWeightPartnerId) || !calculateWeightPartnerId.contains(partnerId)) {
            // 原始逻辑,都是默认传递 1kg给到配送
            return new BigDecimal("1");
        }
        if (CollectionUtils.isEmpty(productList)) {
            return new BigDecimal("0.5");
        }
        BigDecimal result = BigDecimal.ZERO;
        for (ProductBeanV1 p : productList) {
//            if (p.getIsSendGoods()) {
//                continue;
//            }
            BigDecimal sum = p.getWeight().multiply(new BigDecimal(p.getNumber()));
            BigDecimal comboSum = this.sumWeightByProduct(p.getComboProduct());
            BigDecimal materSum = this.sumWeightByProduct(p.getMaterialProduct());
//            BigDecimal sendSum = this.sumWeightByProduct(p.getSendProduct());
//            result = result.add(sum).add(comboSum).add(materSum).add(sendSum);
            result = result.add(sum).add(comboSum).add(materSum);
        }
        if (result.compareTo(BigDecimal.ZERO) <= 0) {
            return new BigDecimal("0.5");
        }
        // 这里 计算的结果是 g  需要变成 kg 给接口 保留3位小数 后面多余直接舍弃
        return result.divide(new BigDecimal("1000"), 3, BigDecimal.ROUND_DOWN);
    }


    private BigDecimal sumWeightByProduct(List<ProductBeanV1> productBeanV) {
        BigDecimal result = BigDecimal.ZERO;
        if (CollectionUtils.isEmpty(productBeanV)) {
            return result;
        }
        for (ProductBeanV1 p : productBeanV) {
            BigDecimal weight = p.getWeight();
            int number = p.getNumber();
            BigDecimal multiply = weight.multiply(new BigDecimal(number));
            result = result.add(multiply);
        }
        return result;
    }
}
