package com.fs.live.service.impl;

import java.math.BigDecimal;
import java.sql.Timestamp;
import java.text.ParseException;
import java.text.SimpleDateFormat;
import java.time.LocalDateTime;
import java.time.ZoneId;
import java.time.format.DateTimeFormatter;
import java.time.temporal.ChronoUnit;
import java.util.*;
import java.util.concurrent.TimeUnit;
import java.util.stream.Collectors;

import cn.hutool.core.collection.CollectionUtil;
import cn.hutool.core.date.DateTime;
import cn.hutool.core.date.DateUtil;
import cn.hutool.core.util.IdUtil;
import cn.hutool.core.util.NumberUtil;
import cn.hutool.core.util.ObjectUtil;
import cn.hutool.core.util.StrUtil;
import cn.hutool.json.JSONArray;
import cn.hutool.json.JSONUtil;
import com.alibaba.fastjson.JSON;

import com.alibaba.fastjson.JSONObject;
import com.fs.common.config.FSSysConfig;
import com.fs.common.config.LoginContextManager;
import com.fs.common.core.domain.R;
import com.fs.common.core.redis.RedisCache;
import com.fs.common.event.TemplateBean;
import com.fs.common.event.TemplateEvent;
import com.fs.common.event.TemplateListenEnum;
import com.fs.common.exception.CustomException;
import com.fs.common.utils.*;
import com.fs.company.domain.Company;
import com.fs.company.domain.CompanyDept;
import com.fs.company.domain.CompanyMoneyLogs;
import com.fs.company.domain.CompanyUser;
import com.fs.company.mapper.CompanyMoneyLogsMapper;
import com.fs.company.service.ICompanyDeptService;
import com.fs.company.service.ICompanyService;
import com.fs.company.service.ICompanyUserService;
import com.fs.erp.constant.ErpTypeConstant;
import com.fs.erp.domain.*;
import com.fs.erp.dto.*;
import com.fs.erp.service.IErpOrderService;
import com.fs.erp.utils.ErpContextHolder;
import com.fs.express.FsStoreDeliversService;
import com.fs.live.domain.*;
import com.fs.live.dto.LiveOrderItemDTO;
import com.fs.live.mapper.*;
import com.fs.live.param.FsUserLiveOrderPayUParam;
import com.fs.live.param.LiveOrderConfirmParam;
import com.fs.live.param.LiveOrderFinishParam;
import com.fs.live.service.*;
import com.fs.live.vo.*;
import com.fs.store.cache.IFsExpressCacheService;
import com.fs.store.cache.IFsStoreProductAttrValueCacheService;
import com.fs.store.cache.impl.IFsStoreProductCacheServiceImpl;
import com.fs.store.domain.*;
import com.fs.store.dto.*;
import com.fs.store.enums.*;
import com.fs.store.mapper.*;
import com.fs.store.param.FsStoreOrderAddTuiMoneyParam;
import com.fs.store.param.LiveOrderComputedParam;
import com.fs.store.service.*;
import com.fs.store.service.channel.PaymentHandler;
import com.fs.store.service.channel.PaymentHandlerHolder;
import com.fs.store.service.channel.param.PayProcessContext;
import com.fs.system.config.SnowflakeUtils;
import com.fs.system.service.ISysConfigService;
import com.fs.wx.domain.FsWxExpressTask;
import com.fs.wx.mapper.FsWxExpressTaskMapper;
import lombok.extern.slf4j.Slf4j;
import org.apache.commons.collections4.CollectionUtils;
import org.apache.commons.lang.ObjectUtils;
import org.apache.http.util.Asserts;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.context.ApplicationEventPublisher;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Propagation;
import org.springframework.transaction.annotation.Transactional;
import org.springframework.transaction.interceptor.TransactionAspectSupport;

import static com.fs.store.constants.StoreConstants.DELIVERY;


/**
 * 订单Service业务层处理
 *
 * @author fs
 * @date 2025-07-08
 */
@Service
@Slf4j
public class LiveOrderServiceImpl implements ILiveOrderService {

    private final RedisCache redisCache;
    @Autowired
    private LiveOrderMapper baseMapper;



    @Autowired
    private LiveMapper liveMapper;


    @Autowired
    private LiveGoodsMapper liveGoodsMapper;

    @Autowired
    private IFsExpressService expressService;

    @Autowired
    private LiveOrderItemMapper liveOrderItemMapper;

    @Autowired
    private IFsStoreProductService fsStoreProductService;

    @Autowired
    FsUserMapper userMapper;

    @Autowired
    private IErpOrderService erpOrderService;



    @Autowired
    private ICompanyService companyService;

    @Autowired
    private FsStoreProductAttrValueMapper fsStoreProductAttrValueMapper;

    @Autowired
    private LiveUserLotteryRecordMapper liveUserLotteryRecordMapper;

    @Autowired
    ICompanyUserService companyUserService;

    @Autowired
    private ICompanyDeptService companyDeptService;



    @Autowired
    private ISysConfigService configService;

    @Autowired
    private LiveOrderPaymentMapper liveOrderPaymentMapper;

    @Autowired
    private IFsShippingTemplatesService shippingTemplatesService;

    @Autowired
    private IFsShippingTemplatesRegionService shippingTemplatesRegionService;

    @Autowired
    private IFsUserService userService;

    @Autowired
    private FsWxExpressTaskMapper fsWxExpressTaskMapper;

    @Autowired
    private IFsExpressCacheService fsExpressCacheService;

    @Autowired
    private ApplicationEventPublisher publisher;

    @Value("${fsConfig.omsCode}")
    private String deliverOmsCode;

    @Value("${jst.shop_code}")
    private String jstShopCode;
    @Autowired
    private FsStoreDeliversMapper fsStoreDeliversMapper;
    @Autowired
    private FsStoreDeliversService fsStoreDeliversService;

    @Autowired
    private LiveOrderPaymentErrorMapper liveOrderPaymentErrorMapper;
    @Autowired
    private IFsStoreProductGroupService storeProductGroupService;

    @Autowired
    private IFsStoreProductAttrValueCacheService fsStoreProductAttrValueCacheService;


    @Autowired
    private IFsStoreProductCacheServiceImpl fsStoreProductCacheService;


    @Autowired
    private ILiveOrderLogsService liveOrderLogsService;

    @Autowired
    private LiveCartMapper liveCartMapper;
    @Autowired
    private FSSysConfig sysConfig;
    @Autowired
    private FsWarehousesMapper fsWarehousesMapper;
    @Autowired
    private LiveOrderMapper liveOrderMapper;

    @Autowired
    private ILiveUserFirstEntryService liveUserFirstEntryService;

    @Autowired
    private CompanyMoneyLogsMapper moneyLogsMapper;
    @Autowired
    private ILiveCouponUserService liveCouponUserService;

    @Autowired
    private LiveAfterSalesMapper liveAfterSalesMapper;

    @Autowired
    private ILiveOrderService liveOrderService;


    public LiveOrderServiceImpl(RedisCache redisCache) {
        this.redisCache = redisCache;
    }


    @Override
    public void pushLiveOrder(LiveOrder order) throws ParseException {
        throw new UnsupportedOperationException("该方法已废弃");
        //判断是否开启erp
//        Integer erpOpen = sysConfig.getErpOpen();
//        if (erpOpen==null || erpOpen==0){
//            return;
//        }
//        IErpOrderService erpOrderService = gyOrderService;
//        if(order.getStatus()!=2) return;
//        ErpOrder erpOrder=new ErpOrder();
//        if (order.getCompanyId()!=null){
//            erpOrder.setVip_code(order.getUserId() +order.getCompanyId().toString());
//        }else {
//            erpOrder.setVip_code(order.getUserId());
//        }
//        erpOrder.setPlatform_code(order.getOrderCode());
//        erpOrder.setShop_code(sysConfig.getErpShopCode());
//        erpOrder.setSeller_memo(order.getRemark());
//
//        List<ErpOrderPayment> payments=new ArrayList<>();
//        ErpOrderPayment payment=new ErpOrderPayment();
//        payment.setPay_type_code("weixin");
//        payment.setPayment(order.getPayMoney().doubleValue());
//        if(order.getPayTime()!=null){
//            SimpleDateFormat sdf = new SimpleDateFormat("yyyy-MM-dd HH:mm:ss");
//            String timeString = sdf.format(order.getPayTime());
//            Date date = sdf.parse(timeString); // 时间格式转为时间戳
//            long timeLong = date.getTime();
//            payment.setPaytime(new Timestamp(timeLong));
//        }
//        payments.add(payment);
//
//        if (!("金牛明医".equals(cloudHostProper.getCompanyName()))){
//            if (order.getPayRemain().compareTo(new BigDecimal(0)) == 0) {
//                //没有物流代收
//                //大于100发发顺丰云配
//                if(order.getPayMoney().compareTo(new BigDecimal(100))>0){
//                    //发互联网医院SF.0235488558_241101
//                    FsExpress express=expressService.selectFsExpressByOmsCode("SF.0235488558_241101");
//                    erpOrder.setExpress_code(express.getOmsCode());
//                    order.setDeliveryName(express.getName());
//                    order.setDeliveryCode(express.getCode());
//                }else {
//                    //发ztpdd
//                    FsExpress express=expressService.selectFsExpressByOmsCode("CDYJFYD.400011111705_241230");
//                    erpOrder.setExpress_code(express.getOmsCode());
//                    order.setDeliveryName(express.getName());
//                    order.setDeliveryCode(express.getCode());
//                }
//            } else {
//                FsExpress express = new FsExpress();
//                if (order.getCompanyId()!=null){
//                    Company company = companyService.selectCompanyById(order.getCompanyId());
//                    if (company != null && StringUtils.isNotEmpty(company.getOmsCode())){
//                        express = expressService.selectFsExpressByOmsCode(company.getOmsCode());
//                    }else {
//                        express=expressService.selectFsExpressByOmsCode("SF.0235469535");
//                    }
//                }else {
//                    express=expressService.selectFsExpressByOmsCode("SF.0235469535");
//                }
//                //物流代发互联网医院顺
//                erpOrder.setExpress_code(express.getOmsCode());
//                order.setDeliveryName(express.getName());
//                order.setDeliveryCode(express.getCode());
//                //物流代收金额
//                ErpOrderPayment codPayment = new ErpOrderPayment();
//                codPayment.setPay_type_code("cod");
//                BigDecimal toal = order.getPayRemain();
//                codPayment.setPayment(toal.doubleValue());
//                payments.add(codPayment);
//                erpOrder.setCod(true);
//            }
//        }
//
//        erpOrder.setPayments(payments);
//        if(order.getCompanyId()!=null){
//            Company company=companyService.selectCompanyById(order.getCompanyId());
//            if(company!=null){
//                erpOrder.setSeller_memo(company.getCompanyName());
//            }
//        }
//        if(order.getCompanyUserId()!=null){
//            CompanyUser companyUser=companyUserService.selectCompanyUserById(order.getCompanyUserId());
//            if(companyUser!=null){
//                CompanyDept dept=companyDeptService.selectCompanyDeptById(companyUser.getDeptId());
//                if(dept!=null){
//                    List<String> names=companyDeptService.selectCompanyDeptNamesByIds(dept.getAncestors());
//                    if(names!=null&&names.size()>0){
//                        //写备注
//                        erpOrder.setSeller_memo(erpOrder.getSeller_memo()+"-"+StringUtils.join(names, ",")+","+dept.getDeptName() );
//                    }
//                }
//                erpOrder.setSeller_memo(erpOrder.getSeller_memo()+"-"+companyUser.getNickName());
//            }
//        }
//
//        ErpRemarkDTO remarkDTO=new ErpRemarkDTO();
//        remarkDTO.setTotalPrice(order.getTotalPrice());
//        remarkDTO.setPayPrice(order.getPayPrice());
//        remarkDTO.setDeliveryMoney(order.getPayDelivery());
//        remarkDTO.setPayMoney(order.getPayMoney());
//        remarkDTO.setCouponMoney(order.getDiscountMoney());
//        remarkDTO.setOrderId(order.getOrderCode());
//        remarkDTO.setYdMoney(order.getPayPrice().subtract(order.getPayMoney().subtract(order.getPayDelivery())));
//
//        if(order.getPayTime()!=null){
//            SimpleDateFormat sdf = new SimpleDateFormat("yyyy-MM-dd HH:mm:ss");
//            String format = sdf.format(order.getPayTime());
//            remarkDTO.setPayTime(format);
//        }
//
//        erpOrder.setSeller_memo(erpOrder.getSeller_memo()+JSONUtil.toJsonStr(remarkDTO));
//        erpOrder.setOrder_type_code("order");
//        SimpleDateFormat sdf = new SimpleDateFormat("yyyy-MM-dd HH:mm:ss");
//        erpOrder.setDeal_datetime(sdf.format(new Date()));
//        FsStoreOrderItem itemMap=new FsStoreOrderItem();
//        itemMap.setOrderId(order.getOrderId());
//        List<LiveOrderItem> liveOrderItems = liveOrderItemMapper.selectLiveOrderItemByOrderId(order.getOrderId());
//        List<ErpOrderItem> details=new ArrayList<>();
//        for (LiveOrderItem liveOrderItem : liveOrderItems) {
//            FsStoreCartDTO cartDTO= JSONUtil.toBean(liveOrderItem.getJsonInfo(),FsStoreCartDTO.class);
//            ErpOrderItem item=new ErpOrderItem();
//            item.setItem_code(cartDTO.getBarCode().trim());
//            item.setPrice(cartDTO.getPrice().toString());
//            item.setQty(cartDTO.getNum());
//            item.setRefund(0);
//            details.add(item);
//        }
//
//        erpOrder.setDetails(details);
//        erpOrder.setReceiver_name(order.getUserName().replaceAll("[^\\u4e00-\\u9fa5a-zA-Z0-9]", ""));
//        //2025.6.27 金牛要求erp推送电话可以设置默认 不影响其他推送
//        String phone = null;
//        if (order.getUserPhone().length()>11){
//            phone = decryptPhone(order.getUserPhone());
//        }else {
//            phone = order.getUserPhone();
//        }
//        if(phone.length()>11){
//            erpOrder.setReceiver_phone(phone);
//        } else{
//            erpOrder.setReceiver_mobile(phone);
//        }
//        String[] address=order.getUserAddress().split(" ");
//        if (address.length<3){
//            String kdnAddress = fsUserAddressService.getKdnAddress(order.getUserAddress());
//            Map<String,Object> addDAta = (Map<String,Object>)JSON.parse(kdnAddress);
//            Map<String, String> add = (Map<String, String>)addDAta.get("Data");
//            erpOrder.setReceiver_province(add.get("ProvinceName"));
//            erpOrder.setReceiver_city(add.get("CityName"));
//            erpOrder.setReceiver_district(add.get("ExpAreaName"));
//            erpOrder.setReceiver_address(add.get("StreetName")+add.get("Address"));
//        }else {
//            erpOrder.setReceiver_province(address[0]);
//            erpOrder.setReceiver_city(address[1]);
//            erpOrder.setReceiver_district(address[2]);
//            //处理地址多空隔问题
//            if(address.length>3){
//                StringBuffer addrs=new StringBuffer();
//                for(int i=3;i<address.length;i++){
//                    addrs.append(address[i]);
//                }
//                erpOrder.setReceiver_address(addrs.toString());
//            }
//            else if(address.length==3){
//                erpOrder.setReceiver_address(address[2]);
//            }
//        }
//
//        erpOrder.setReceiver_address(erpOrder.getReceiver_address().replace("+","加"));
//        erpOrder.setReceiver_address(erpOrder.getReceiver_address().replace("\n",""));
//        ErpOrderResponse response= erpOrderService.addOrder(erpOrder);
//        log.info("ErpCreate:"+order.getOrderCode()+":"+JSONUtil.toJsonStr(response));
//        if(response.getSuccess()){
//
//            //支付成功后 将订单号写入待发货的REDIS中
//            redisCache.setCacheObject("delivery"+":"+response.getCode(),order.getOrderCode());
//            //写入外部订单号
//            order.setExtendOrderId(response.getCode());
//            baseMapper.updateLiveOrder(order);
//        }

    }

//    @Override
//    public R aliPayment(FsUserLiveOrderPayUParam param) {
//        LiveOrder order = baseMapper.selectLiveOrderByOrderId(String.valueOf(param.getOrderId()));
//        if (order == null) {
//            return R.error("订单不存在");
//        }
//        if (order.getStatus() != 1) {
//            return R.error("非法操作");
//        }
//        FsUser user = userMapper.selectFsUserByUserId(param.getUserId());
//        if(user!=null){
//            if(order.getPayMoney().compareTo(new BigDecimal(0))==1){
//
//                String payCode =  SnowflakeUtils.nextId();
////                String payCode = String.valueOf(UUID.randomUUID());
//                if(StringUtils.isEmpty(payCode)){
//                    return R.error("订单生成失败，请重试");
//                }
//                String json = configService.selectConfigByKey("his.pay");
//                PayConfigDTO payConfigDTO = JSONUtil.toBean(json, PayConfigDTO.class);
//                LiveOrderPayment storePayment=new LiveOrderPayment();
//                storePayment.setStatus(0);
//                storePayment.setPayMode(payConfigDTO.getType());
//                storePayment.setBusinessCode(order.getOrderCode());
//                storePayment.setPayCode(payCode);
//
////                storePayment.setPayMoney(order.getPayMoney());
//                storePayment.setPayMoney(new BigDecimal("0.01"));
//                storePayment.setCreateTime(new Date());
//                storePayment.setPayTypeCode("alipay");
//                storePayment.setBusinessType(5);
//                storePayment.setRemark("直播订单支付");
////                storePayment.setOpenId(user.getMpOpenId());
//                storePayment.setUserId(user.getUserId());
//                storePayment.setBusinessId(order.getOrderId().toString());
//                if(liveOrderPaymentMapper.insertLiveOrderPayment(storePayment)>0){
//
//                    if (payConfigDTO.getType().equals("yb")) {
//                        return R.error("支付暂不可用!");
//                    } else if (payConfigDTO.getType().equals("tz")) {
//                        PayCreateOrder o = new PayCreateOrder();
//                        o.setOrderNo("appLive" + storePayment.getPayCode()); // 业务系统订单号
//                        o.setTrxAmt(storePayment.getPayMoney().doubleValue()); // 交易金额
//                        o.setBusinessCstNo(order.getUserId().toString()); // 业务平台客户号
//                        String phone="";
//                        if (user.getPhone()!=null&&user.getPhone().length()>4){
//                            phone=user.getPhone().substring(user.getPhone().length()-4);
//                        }
//                        o.setPayerName("微信用户"+phone);
//                        o.setGoodsInfo("直播订单支付"); // 订单信息
////                        o.setOpenId(user.getMpOpenId());
//                        o.setOrderType(5);
//                        o.setOrderId(order.getOrderId().toString());
//                        o.setPayType(Arrays.asList(PayType.支付宝条码支付.getCode()));
//                        TzBankResult<PayCreateOrderResult> result = tzBankService.createOrder(o);
//                        LiveOrderPayment mt=new LiveOrderPayment();
//                        mt.setPaymentId(storePayment.getPaymentId());
//                        mt.setTradeNo(result.getBody().getOrderFlowNo());
//                        liveOrderPaymentMapper.updateLiveOrderPayment(mt);
//                        return R.ok().put("isPay", 0).put("data", result).put("type", "tz");
//                    }else if (payConfigDTO.getType().equals("hf")) {
//                        HuiFuCreateOrder o = new HuiFuCreateOrder();
//                        o.setTradeType("A_NATIVE");
////                        o.setOpenid(user.getMaOpenId());
//                        o.setReqSeqId("appLive-"+storePayment.getPayCode());
//                        o.setTransAmt(storePayment.getPayMoney().toString());
//                        o.setGoodsDesc("直播订单支付");
//                        HuifuCreateOrderResult result = huiFuService.createOrder(o);
//                        LiveOrderPayment mt=new LiveOrderPayment();
//                        mt.setPaymentId(storePayment.getPaymentId());
//                        mt.setTradeNo(result.getHf_seq_id());
//                        liveOrderPaymentMapper.updateLiveOrderPayment(mt);
//                        return R.ok().put("isPay", 0).put("data", result).put("type", "hf");
//                    }
//                }
//            }
//            else{
//                this.payConfirm(order.getOrderCode(),"","","",2);
//                return R.ok().put("isPay",1);
//            }
//        }
//        else{
//            return R.error("用户不存在");
//        }
//        return R.error();
//
//    }

    @Override
    @Transactional(rollbackFor = Throwable.class,propagation = Propagation.REQUIRED)
    public String payConfirm(Integer type,Long orderId,String payCode,String tradeNo,String bankTransactionId,String bankSerialNo) {
        Object savePoint = TransactionAspectSupport.currentTransactionStatus().createSavepoint();
        try {
            LiveOrder order=null;
            if(type.equals(1)){
                LiveOrderPayment storePayment = liveOrderPaymentMapper.selectLiveOrderPaymentByPaymentCode(payCode);
                if (storePayment!=null){
                    if(storePayment.getStatus().equals(0)){
                        LiveOrderPayment paymentMap=new LiveOrderPayment();
                        paymentMap.setPaymentId(storePayment.getPaymentId());
                        paymentMap.setStatus(1);
                        paymentMap.setPayTime(new Date());
                        paymentMap.setTradeNo(tradeNo);
                        paymentMap.setBankSerialNo(bankSerialNo);
                        paymentMap.setBankTransactionId(bankTransactionId);
                        paymentMap.setPayTypeCode("微信小程序支付");
                        liveOrderPaymentMapper.updateLiveOrderPayment(paymentMap);
                        order = baseMapper.selectFsUserVipOrderByOrderCode(storePayment.getBusinessCode());
                        if(order==null || !order.getStatus().equals(1)){
                            throw new CustomException("当前订单未找到或者订单状态不为待支付! paycode:"+payCode);
                        }
                    }
                }
                else{
                    log.info("支付单号不存在:"+payCode);
                    throw new CustomException("当前支付记录未找到!");
                }
            }
            else if(type.equals(2)){
                order=baseMapper.selectLiveOrderByOrderId(String.valueOf(orderId));
                if(!order.getStatus().equals(OrderInfoEnum.STATUS_0.getValue())){
                    TransactionAspectSupport.currentTransactionStatus().setRollbackOnly();
                    return "";
                }
            }
            if(order.getStatus()!=1){
                TransactionAspectSupport.currentTransactionStatus().setRollbackOnly();
                return "";
            }

            // 佣金处理
            if (order.getCompanyUserId() == -1L) {
                companyService.addCompanyTuiLiveMoney(order);
            } else {
                // 目前是一级佣金
                FsStoreProduct product = JSONUtil.toBean(order.getItemJson(), FsStoreProduct.class);
                List<FsStoreProductAttrValue> productAttrValues = fsStoreProductAttrValueMapper.selectFsStoreProductAttrValueByProductId(product.getProductId());
                if (productAttrValues != null && !productAttrValues.isEmpty()) {
                    userService.addTuiLiveMoney(order, productAttrValues);
                }
            }


            //增加用户购买次数
            userService.incPayCount(Long.valueOf(order.getUserId()));

            order.setStatus(2);
            order.setIsPay("1");
            order.setPayTime(new Date());
            baseMapper.updateLiveOrder(order);
            return "SUCCESS";
        }catch (Exception e){
            log.info("支付错误:"+e.getMessage());
            TransactionAspectSupport.currentTransactionStatus().rollbackToSavepoint(savePoint);
            LiveOrderPaymentError err = new LiveOrderPaymentError();
            err.setOrderNo(payCode);
            err.setOrderFlowNo(tradeNo);
            err.setStatus(0);
            err.setMsg("支付错误:"+e.getMessage());
            err.setCreateTime(DateUtils.getNowDate());
            liveOrderPaymentErrorMapper.insertLiveOrderPaymentError(err);
        }
        return "SUCCESS";
    }

    @Override
    @Transactional(rollbackFor = Throwable.class,propagation = Propagation.REQUIRED)
    public R wxPayment(FsUserLiveOrderPayUParam param) {
        LiveOrder order = baseMapper.selectLiveOrderByOrderId(String.valueOf(param.getOrderId()));
        if (order == null) {
            return R.error("订单不存在");
        }
        if (order.getStatus()!=1){
            return R.error("非法操作");
        }
        String orderId=redisCache.getCacheObject("isPaying:"+order.getOrderId());
        if(StringUtils.isNotEmpty(orderId)&&orderId.equals(order.getOrderId().toString())){
            return R.error("正在支付中...");
        }
        FsUser user = userMapper.selectFsUserByUserId(param.getUserId());
        if(user!=null&& StringUtils.isNotEmpty(user.getMaOpenId())) {
            if (order.getPayMoney().compareTo(new BigDecimal(0)) == 0) {
                return R.ok().put("isPay", 1);
            } else {
                String json = configService.selectConfigByKey("store.pay");
                FsPayConfig fsPayConfig = JSON.parseObject(json, FsPayConfig.class);
                String payCode =  SnowflakeUtils.nextId();
                if(StringUtils.isEmpty(payCode)){
                    return R.error("订单生成失败，请重试");
                }
                LiveOrderPayment storePayment = new LiveOrderPayment();
                storePayment.setStatus(0);
                storePayment.setPayMode(fsPayConfig.getType());
                storePayment.setBusinessCode(order.getOrderCode());
                storePayment.setPayCode(payCode);
                storePayment.setPayMoney(order.getPayMoney());
//                storePayment.setPayMoney(new BigDecimal("0.01"));
                storePayment.setCreateTime(new Date());
                storePayment.setPayTypeCode("weixin");
                storePayment.setBusinessType(5);
                storePayment.setRemark("直播商品订单支付");
                storePayment.setOpenId(user.getMaOpenId());
                storePayment.setUserId(user.getUserId());
                storePayment.setBusinessId(order.getOrderId().toString());
                if (liveOrderPaymentMapper.insertLiveOrderPayment(storePayment) > 0) {
                    if (order.getPayType().equals("1")) {
                        //创建微信订单
                        PayProcessContext processContext = new PayProcessContext();
                        processContext.setOrderId(order.getOrderId());
                        processContext.setPayType(1);
                        processContext.setPaymentId(storePayment.getPaymentId());
                        processContext.setPayCode(storePayment.getPayCode());
                        processContext.setFsPayConfig(fsPayConfig);
                        processContext.setUserId(Long.valueOf(order.getUserId()));
                        processContext.setGoodsInfo("直播商品订单支付");
                        processContext.setOrderPrefix("live-");
                        PaymentHandler payment = PaymentHandlerHolder.findBest(fsPayConfig.getType());
                        if(ObjectUtil.isNull(payment)){
                            throw new CustomException("支付方式不存在");
                        }
                        R process = payment.createLiveOrder(processContext);
                        if("200".equals(String.valueOf(process.get("code")))){
                            redisCache.setCacheObject("isPaying:"+order.getOrderId(),order.getOrderId().toString(),1, TimeUnit.MINUTES);
                            return process;
                        }
                    }
                } else {
                    return R.error("用户OPENID不存在");
                }
            }
        }
        return R.ok();
    }

    @Override
    public int tuiOrder(Long orderId) {
        LiveOrder liveOrder = new LiveOrder();
        liveOrder.setOrderId(orderId);
        try {
            pushLiveOrder(liveOrder);
        } catch (Exception e) {
            e.printStackTrace();
        }
        return 1;
    }

    /**
     * 查询订单
     *
     * @param orderId 订单主键
     * @return 订单
     */
    @Override
    public LiveOrder selectLiveOrderByOrderId(String orderId)
    {
        LiveOrder liveOrder = baseMapper.selectLiveOrderByOrderId(orderId);
        if(ObjectUtil.isNull(liveOrder)) {
            throw new RuntimeException("该订单没有找到！");
        }
        List<FsStoreDelivers> byOrderIdWithType = fsStoreDeliversMapper.findByOrderIdWithType(Long.valueOf(orderId), 1);
        if(CollectionUtils.isNotEmpty(byOrderIdWithType)) {
            FsStoreDelivers delivers = byOrderIdWithType.get(0);

            liveOrder.setDeliveryCode(delivers.getDeliverSn());
            liveOrder.setDeliveryName(delivers.getDeliverName());
            liveOrder.setDeliverySn(delivers.getDeliverId());

            liveOrder.setDeliveryStatus(delivers.getStatus());
            liveOrder.setDeliveryType(String.valueOf(delivers.getStateEx()));
        } else {
            liveOrder.setDeliveryCode(null);
            liveOrder.setDeliveryName(null);
            liveOrder.setDeliverySn(null);

            liveOrder.setDeliveryStatus(null);
            liveOrder.setDeliveryType(null);
        }

        // 判断当前用户是否有指定数据权限
        if(!LoginContextManager.hasPermission("live:liveOrder:queryAddress")){
            liveOrder.setUserAddress(ParseUtils.parseAddress(liveOrder.getUserAddress()));
        }
        if(!LoginContextManager.hasPermission("live:liveOrder:queryPhone")){
            liveOrder.setUserPhone(ParseUtils.parsePhone(liveOrder.getUserPhone()));
        }

        return liveOrder;
    }


    @Override
    @Transactional(rollbackFor = Exception.class,propagation = Propagation.REQUIRED)
    public void editLiveOrderDeliveryId(FsStoreDelivers deliveryDTO) {
        LiveOrder liveOrder = liveOrderService.selectLiveOrderByOrderId(String.valueOf(deliveryDTO.getOrderId()));

        Asserts.notNull(deliveryDTO.getDeliverId(),"快递号不能为空！");
        Asserts.notNull(deliveryDTO.getDeliverSn(),"快递类型不能为空！");

        liveOrder.setDeliverySn(deliveryDTO.getDeliverId());
        liveOrder.setDeliveryCode(deliveryDTO.getDeliverSn());
        liveOrder.setStatus(3);
        liveOrderService.updateLiveOrder(liveOrder);


        fsStoreDeliversService.editDeliveryId(deliveryDTO);
        fsStoreDeliversService.syncDeliverInfo(deliveryDTO.getOrderId(),deliveryDTO.getType());
        fsStoreDeliversService.finishOrder(deliveryDTO.getOrderId(),deliveryDTO.getType());
    }

    /**
     * 查询订单列表
     *
     * @param liveOrder 订单
     * @return 订单
     */
    @Override
    public List<LiveOrder> selectLiveOrderList(LiveOrderQueryVO liveOrder)
    {
        List<LiveOrder> liveOrders = baseMapper.selectLiveOrderList(liveOrder);
        if(CollectionUtils.isEmpty(liveOrders)){
            return liveOrders;
        }
        List<Long> collect = liveOrders.stream().map(LiveOrder::getOrderId)
                .filter(Objects::nonNull).collect(Collectors.toList());

        if(CollectionUtils.isEmpty(collect)) {
            return Collections.emptyList();
        }
        Map<Long, FsStoreDelivers> byOrderIdWithTypeBatch = fsStoreDeliversMapper
                .findByOrderIdWithTypeBatch(collect, 1);

        for (LiveOrder order : liveOrders) {
            FsStoreDelivers delivers = byOrderIdWithTypeBatch.get(order.getOrderId());
            if(ObjectUtil.isNotNull(delivers)) {
                order.setDeliveryCode(delivers.getDeliverSn());
                order.setDeliveryName(delivers.getDeliverName());
                order.setDeliverySn(delivers.getDeliverId());
                order.setDeliveryStatus(delivers.getStatus());
                order.setDeliveryType(String.valueOf(delivers.getStateEx()));
            } else {
                order.setDeliveryCode(null);
                order.setDeliveryName(null);
                order.setDeliverySn(null);
                order.setDeliveryStatus(null);
                order.setDeliveryType(null);
            }
        }
        return liveOrders;
    }


    @Override
    public List<LiveOrder> selectLiveOrderListExport(LiveOrderQueryVO liveOrder) {
        List<LiveOrder> liveOrders = baseMapper.selectLiveOrderList(liveOrder);
        if(CollectionUtils.isEmpty(liveOrders)){
            return liveOrders;
        }
        List<Long> collect = liveOrders.stream().map(LiveOrder::getOrderId)
                .filter(Objects::nonNull).collect(Collectors.toList());

        if(CollectionUtils.isEmpty(collect)) {
            return Collections.emptyList();
        }
        Map<Long, FsStoreDelivers> byOrderIdWithTypeBatch = fsStoreDeliversMapper
                .findByOrderIdWithTypeBatch(collect, 1);
        Map<String, LiveOrderPayment> paymentMap = liveOrderPaymentMapper.selectAllPayments();

        for (LiveOrder order : liveOrders) {
            FsStoreDelivers delivers = byOrderIdWithTypeBatch.get(order.getOrderId());
            if(ObjectUtil.isNotNull(delivers)) {
                order.setDeliveryCode(delivers.getDeliverSn());
                order.setDeliveryName(delivers.getDeliverName());
                order.setDeliverySn(delivers.getDeliverId());
                order.setDeliveryStatus(delivers.getStatus());
                order.setDeliveryType(String.valueOf(delivers.getStateEx()));
            } else {
                order.setDeliveryCode(null);
                order.setDeliveryName(null);
                order.setDeliverySn(null);
                order.setDeliveryStatus(null);
                order.setDeliveryType(null);
            }
            order.setPayPrice(order.getTotalPrice());

            LiveOrderPayment liveOrderPayment = paymentMap.get(String.valueOf(order.getOrderId()));
            if(ObjectUtil.isNotNull(liveOrderPayment)){
                order.setBankTrxId(liveOrderPayment.getBankTransactionId());
            }
        }
        return liveOrders;
    }

    @Override
    public List<LiveOrderListVo> selectLiveOrderListVo(LiveOrder liveOrder) {
        List<LiveOrderListVo> liveOrders = baseMapper.selectLiveOrderListVo(liveOrder.getUserId(),liveOrder.getStatus());
        List<Long> allOrderIds = liveOrders.stream().map(LiveOrderListVo::getOrderId)
                .filter(Objects::nonNull).collect(Collectors.toList());

        if(CollectionUtils.isEmpty(allOrderIds)) {
            return Collections.emptyList();
        }

        Map<Long, FsStoreDelivers> byOrderIdWithTypeBatch = fsStoreDeliversMapper
                .findByOrderIdWithTypeBatch(allOrderIds, 1);

        Map<Long,LiveAfterSales> liveAfterSalesMap = liveAfterSalesMapper.findByOrderIds(allOrderIds);

        List<LiveOrderItemVo> liveOrderItemVosList = liveOrderItemMapper.selectLiveOrderItemByOrderIds(allOrderIds);
        Map<Long, List<LiveOrderItemVo>> orderItemsMap = liveOrderItemVosList.stream()
                .collect(Collectors.groupingBy(
                        LiveOrderItemVo::getOrderId,
                        LinkedHashMap::new,
                        Collectors.toList()
                ));

        for (LiveOrderListVo order : liveOrders) {
            FsStoreDelivers delivers = byOrderIdWithTypeBatch.get(order.getOrderId());

            if(ObjectUtil.isNotNull(delivers)) {
                order.setDeliveryCode(delivers.getDeliverSn());
                order.setDeliveryName(delivers.getDeliverName());
                order.setDeliverySn(delivers.getDeliverId());
                order.setDeliveryStatus(delivers.getStatus());
                order.setDeliveryType(String.valueOf(delivers.getStateEx()));
            }else {
                order.setDeliveryCode(null);
                order.setDeliveryName(null);
                order.setDeliverySn(null);
                order.setDeliveryStatus(null);
                order.setDeliveryType(null);
            }
            if(ObjectUtil.isNotNull(liveAfterSalesMap)){
                LiveAfterSales liveAfterSales = liveAfterSalesMap.get(order.getOrderId());
                if(ObjectUtil.isNotNull(liveAfterSales)) {
                    order.setAfterSaleId(liveAfterSales.getId());
                }
            }

            if(ObjectUtil.isNotNull(orderItemsMap)){
                Long orderId = order.getOrderId();
                List<LiveOrderItemVo> liveOrderItemVos = orderItemsMap.get(orderId);
                if(CollectionUtils.isNotEmpty(liveOrderItemVos)) {
                    order.setOrderItemList(liveOrderItemVos);
                }
            }
        }
        return liveOrders;
    }

    @Override
    @Transactional
    public R buy(LiveOrder liveOrder) {
        String orderKey= redisCache.getCacheObject("orderKey:"+liveOrder.getOrderKey());
        if (StringUtils.isEmpty(orderKey)) {
            return R.error("订单已过期");
        }
        List<LiveCart> itemList = liveCartMapper.selectCheckedLiveCartByUserId(Long.valueOf(liveOrder.getUserId()));
        if (itemList == null || itemList.isEmpty()) {
            return R.error("请选择商品");
        }
        List<String> productIds = itemList.stream().map(LiveCart::getProductId).collect(Collectors.toList());
        // productIds 利用,进行拼接
        String productsId = String.join(",", productIds);
        List<FsStoreProduct> productList = fsStoreProductService.selectProductByIds(productsId);
        if (productList == null || productList.isEmpty()) {
            return R.error("商品不存在");
        }
        BigDecimal totalPrice = new BigDecimal("0");
        List<LiveOrderItem> liveOrderItemList = new ArrayList<>();
//        String orderSn = SnowflakeUtils.nextId();
        String orderSn = UUID.randomUUID().toString();
        log.info("订单生成："+orderSn);
        // 检查数据库存
        for (LiveCart item : itemList) {
            FsStoreProduct product = productList.stream().filter(p -> {
                        if (item.getProductId() != null) {
                            return p.getProductId() != null && p.getProductId().toString().equals(item.getProductId());
                        }
                        return false;}
            ).findFirst().orElse(null);
            if (product == null) {
                return R.error("商品不存在");
            }
            if (product.getStock() < item.getCartNum()) {
                return R.error("商品库存不足");
            }
            if (product.getIsShow() == 0) {
                return R.error("商品已下架");
            }
            product.setStock(product.getStock() - item.getCartNum());
            totalPrice = totalPrice.add(product.getPrice().multiply(new BigDecimal(item.getCartNum())));

            // 订单商品详情
            LiveOrderItemDTO dto=new LiveOrderItemDTO();
            dto.setImage(product.getImage());
            dto.setSku(String.valueOf(product.getStock()));
            dto.setBarCode(product.getBarCode());
            dto.setPrice(product.getPrice());
            dto.setProductName(product.getProductName());
            dto.setNum(Long.valueOf(item.getCartNum()));

            LiveOrderItem liveOrderItem = new LiveOrderItem();
            liveOrderItem.setOrderCode(orderSn);
            liveOrderItem.setOrderId(liveOrder.getOrderId());
            liveOrderItem.setCartId(item.getCartId());
            liveOrderItem.setProductId(product.getProductId());
            liveOrderItem.setNum(Long.valueOf(item.getCartNum()));
            liveOrderItem.setJsonInfo(JSON.toJSONString(dto));
            liveOrderItemList.add(liveOrderItem);

        }
        productList.forEach(product -> {
            FsStoreProduct fsStoreProduct = new FsStoreProduct();
            fsStoreProduct.setProductId(product.getProductId());
            fsStoreProduct.setStock(product.getStock());
            fsStoreProductService.updateFsStoreProduct(fsStoreProduct);});




        liveOrder.setOrderCode(orderSn);

        liveOrder.setCreateTime(new Date());
        liveOrder.setUpdateTime(new Date());
        liveOrder.setStatus(OrderInfoEnum.STATUS_1.getValue());
        liveOrder.setPayType("1");
        liveOrder.setTotalPrice(totalPrice);
        liveOrder.setPayMoney(liveOrder.getTotalPrice());


        if (baseMapper.insertLiveOrder(liveOrder) > 0) {
            for (LiveOrderItem liveOrderItem : liveOrderItemList) {
                liveOrderItem.setOrderId(liveOrder.getOrderId());
            }
            liveOrderItemMapper.insertBatchList(liveOrderItemList);
            // list Long  转为Long数组

            liveCartMapper.deleteLiveCartByCartIds(liveOrderItemList.stream().map(LiveOrderItem::getCartId).toArray(Long[]::new));
            return R.ok("下单成功").put("order",liveOrder);
        } else {
            return R.error("订单创建失败");
        }
    }

    @Override
    public synchronized R finishOrder(Long orderId) {
        return finishStoreOrder(orderId);
    }

    @Override
    public List<LiveOrder> selectLiveOrderByFinish() {
        return baseMapper.selectLiveOrderByFinish();
    }

    @Override
    public void autoFinishOrder(LiveOrderFinishParam param) {

    }

    @Override
    public LiveOrder getById(String orderId) {
        return baseMapper.selectLiveOrderByOrderId(orderId);
    }

    @Override
    @Transactional(rollbackFor = Exception.class,propagation = Propagation.REQUIRED)
    public R refundOrderMoney(Long orderId) {
        LiveOrder order = baseMapper.selectLiveOrderByOrderId(String.valueOf(orderId));
        if(order.getStatus()==-2){
            return R.error("已退款");
        }
//        if(order.getStatus()!=1&&order.getStatus()!=2){
//            return R.error("非法操作");
//        }
        if(StringUtils.isNotEmpty(order.getExtendOrderId())){
            ErpRefundUpdateRequest request=new ErpRefundUpdateRequest();
            request.setTid(order.getOrderCode());
            request.setOid(order.getOrderCode());
            request.setRefund_state(1);
            request.setOrderStatus(order.getStatus());

            // 根据仓库code找erp
            if(StringUtils.isNotBlank(order.getStoreHouseCode())){
                String erp = fsWarehousesMapper.selectErpByCode(order.getStoreHouseCode());
                ErpContextHolder.setErpType(erp);
            }
            BaseResponse response=erpOrderService.refundUpdateLive(request);
            if(ObjectUtil.isNull(response) || !response.getSuccess()){
                log.error("调用erp退款接口失败! {}",JSON.toJSONString(response));
                throw new CustomException("调用erp退款接口失败："+response.getErrorDesc());
            }
        }
        order.setStatus(-2);
        order.setRefundMoney(order.getPayMoney());
        order.setRefundStatus(String.valueOf(OrderInfoEnum.REFUND_STATUS_2.getValue()));
        liveUserLotteryRecordMapper.updateOrderStatusByOrderId(order.getOrderId(), -2);
        baseMapper.updateLiveOrder(order);

        //退库存
        //获取订单下的商品
        List<LiveOrderItem> orderItemVOS=liveOrderItemMapper.selectLiveOrderItemByOrderId(order.getOrderId());
        for(LiveOrderItem vo:orderItemVOS){
            if(vo.getIsAfterSales()==1){
                fsStoreProductService.incProductStock(vo.getNum(), vo.getProductId(), vo.getProductAttrValueId());
            }

        }
        if(order.getPayType().equals(3)){
            //货到付款
        }
        else{
            //将钱退还给用户
            List<LiveOrderPayment> payments=liveOrderPaymentMapper.selectLiveOrderPaymentByPay(5,order.getOrderId());
            if(payments!=null){
                for(LiveOrderPayment payment:payments){
                    PaymentHandler best = PaymentHandlerHolder.findBest(payment.getPayMode());
                    if(ObjectUtil.isNull(best)){
                        throw new CustomException("支付类型异常!");
                    }
                    PayProcessContext payProcessContext = new PayProcessContext();
                    payProcessContext.setOrderId(orderId);
                    payProcessContext.setPaymentId(payment.getPaymentId());
                    payProcessContext.setPayCode(payment.getPayCode());
                    payProcessContext.setUserId(Long.valueOf(order.getUserId()));
                    payProcessContext.setOrderPrefix("refundLive-");
                    best.refundLiveOrder(payProcessContext);
                }
            }
        }
        liveOrderLogsService.create(order.getOrderId(), OrderLogEnum.REFUND_ORDER_SUCCESS.getValue(),
                OrderLogEnum.REFUND_ORDER_SUCCESS.getDesc());
        //减去公司收入
        if(order.getCompanyId()!=null&&order.getCompanyId()>0&&order.getTuiMoneyStatus()!=null&&order.getTuiMoneyStatus()==1){
            companyService.subLiveCompanyMoney(order);
        }
        if(order.getTuiUserId()!=null&&order.getTuiUserId()>0){
            userService.subLiveTuiMoney(order);
        }
        return R.ok();
    }

    @Autowired
    private LiveAfterSalesLogsMapper liveAfterSalesLogsMapper;

    @Override
    @Transactional(rollbackFor = Exception.class,propagation = Propagation.REQUIRED)
    public R refundOrderMoney(Long orderId, LiveAfterSales liveAfterSales,String operator) {
        LiveOrder order = baseMapper.selectLiveOrderByOrderId(String.valueOf(orderId));
        if(order.getStatus()==-2){
            return R.error("已退款");
        }
        log.info("准备退款 订单: {}",JSON.toJSONString(order));
        order.setStatus(-2);
        order.setRefundMoney(order.getPayMoney());
        order.setRefundStatus(String.valueOf(OrderInfoEnum.REFUND_STATUS_2.getValue()));
        liveUserLotteryRecordMapper.updateOrderStatusByOrderId(order.getOrderId(), -2);
        baseMapper.updateLiveOrder(order);

        //退库存
        //获取订单下的商品
        List<LiveOrderItem> orderItemVOS=liveOrderItemMapper.selectLiveOrderItemByOrderId(order.getOrderId());
        for(LiveOrderItem vo:orderItemVOS){
            if(vo.getIsAfterSales()==1){
                fsStoreProductService.incProductStock(vo.getNum(), vo.getProductId(), vo.getProductAttrValueId());
            }

        }
        if(order.getPayType().equals(3)){
            //货到付款
        }
        else{
            //将钱退还给用户
            List<LiveOrderPayment> payments=liveOrderPaymentMapper.selectLiveOrderPaymentByPay(5,order.getOrderId());
            if(payments!=null){
                for(LiveOrderPayment payment:payments){
                    PaymentHandler best = PaymentHandlerHolder.findBest(payment.getPayMode());
                    if(ObjectUtil.isNull(best)){
                        throw new CustomException("支付类型异常!");
                    }
                    PayProcessContext payProcessContext = new PayProcessContext();
                    payProcessContext.setOrderId(orderId);
                    payProcessContext.setPaymentId(payment.getPaymentId());
                    payProcessContext.setPayCode(payment.getPayCode());
                    payProcessContext.setUserId(Long.valueOf(order.getUserId()));
                    payProcessContext.setOrderPrefix("refundLive-");
                    best.refundLiveOrder(payProcessContext);
                }
            }
        }
        liveOrderLogsService.create(order.getOrderId(), OrderLogEnum.REFUND_ORDER_SUCCESS.getValue(),
                OrderLogEnum.REFUND_ORDER_SUCCESS.getDesc());
        //减去公司收入
        if(order.getCompanyId()!=null&&order.getCompanyId()>0&&order.getTuiMoneyStatus()!=null&&order.getTuiMoneyStatus()==1){
            companyService.subLiveCompanyMoney(order);
        }
        if(order.getTuiUserId()!=null&&order.getTuiUserId()>0){
            userService.subLiveTuiMoney(order);
        }

        liveAfterSales.setStatus(4);
        liveAfterSales.setSalesStatus(3);
        liveAfterSalesMapper.updateLiveAfterSales(liveAfterSales);


        LiveAfterSalesLogs storeAfterSalesStatus = new LiveAfterSalesLogs();
        storeAfterSalesStatus.setStoreAfterSalesId(liveAfterSales.getId());
        storeAfterSalesStatus.setChangeType(3);
        storeAfterSalesStatus.setChangeMessage(AfterSalesStatusEnum.STATUS_4.getDesc());
        storeAfterSalesStatus.setChangeTime(Timestamp.valueOf(LocalDateTime.now()));
        storeAfterSalesStatus.setOperator(operator);
        liveAfterSalesLogsMapper.insertLiveAfterSalesLogs(storeAfterSalesStatus);


        return R.ok();
    }

    @Override
    public List<LiveOrder> selectUpdateExpress() {
        return baseMapper.selectUpdateExpress();
    }

    @Override
    @Transactional(propagation = Propagation.REQUIRED,rollbackFor = Exception.class)
    public void syncDeliveryOrder(LiveOrder order) {
        log.info("[发货任务] 当前单号: {}", order.getOrderCode());
        ErpOrderQueryRequert request = new ErpOrderQueryRequert();
        request.setCode(order.getExtendOrderId());
        // 根据仓库code找erp
        if(com.fs.common.utils.StringUtils.isNotBlank(order.getStoreHouseCode())){
            String erp = fsWarehousesMapper.selectErpByCode(order.getStoreHouseCode());
            ErpContextHolder.setErpType(erp);
        }
        ErpOrderQueryResponse response = erpOrderService.getOrderLive(request);
        if (CollectionUtils.isNotEmpty(response.getOrders())) {
            for (ErpOrderQuery orderQuery : response.getOrders()) {
                // 部分发货或者全部发货
                if (ObjectUtils.equals(orderQuery.getDelivery_state(), 1) || ObjectUtils.equals(orderQuery.getDelivery_state(), 2)) {

                    for (ErpDeliverys delivery : orderQuery.getDeliverys()) {
                        if (delivery.getDelivery()) {
                            this.deliveryOrder(order.getOrderCode(), delivery.getMail_no(),
                                    delivery.getExpress_code(), delivery.getExpress_name());
                        }
                    }

                }
            }
        }
    }

    @Override
    public List<Long> selectSyncExpressIds() {
        return baseMapper.selectSyncExpressIds();
    }

    @Override
    public List<Long> selectOrderIdByNoErp() {
        return baseMapper.selectOrderIdByNoErp();
    }

    @Override
    public void createOmsOrder(Long orderId)  throws ParseException {
        LiveOrder order = baseMapper.selectLiveOrderByOrderId(String.valueOf(orderId));
        if(ObjectUtil.equal(order.getCompanyId(),-2L)) {
            order.setCompanyId(null);
        }
        if(ObjectUtil.equal(order.getCompanyUserId(),-2L)) {
            order.setCompanyUserId(null);
        }
        if(ObjectUtil.equal(order.getCompanyId(),-1L)) {
            order.setCompanyId(null);
        }
        if(ObjectUtil.equal(order.getCompanyUserId(),-1L)) {
            order.setCompanyUserId(null);
        }

        if(StringUtils.isEmpty(order.getExtendOrderId())&&order.getStatus()!=2){
            return;
        }
        ErpOrder erpOrder=new ErpOrder();
        erpOrder.setBuyer_account(String.valueOf(order.getUserId()));
        erpOrder.setPlatform_code(order.getOrderCode());
        if (order.getCompanyId()!=null){
            erpOrder.setVip_code(order.getUserId().toString()+order.getCompanyId().toString());
        }else {
            erpOrder.setVip_code(order.getUserId().toString());
        }

        erpOrder.setSeller_memo(order.getRemark());
        List<ErpOrderPayment> payments=new ArrayList<>();
        ErpOrderPayment payment=new ErpOrderPayment();
        payment.setPay_type_code("weixin");
        payment.setPayment(order.getPayMoney().doubleValue());
        if(order.getPayTime()!=null){
            SimpleDateFormat sdf = new SimpleDateFormat("yyyy-MM-dd HH:mm:ss");
            String timeString = DateUtil.format(order.getPayTime(),"yyyy-MM-dd HH:mm:ss");
            Date date = sdf.parse(timeString); // 时间格式转为时间戳
            long timeLong = date.getTime();
            payment.setPaytime(new Timestamp(timeLong));
        }
        payments.add(payment);

        //1.新疆、西藏、内蒙古、海南的订单(代收+非代收）全部发EMS
        //2.全款订单选择中通，快递ID 452  ZTO 中通商城标快 ZTBK.17782167502
        //3.新疆  西藏 内蒙古 海南  全款订单走顺丰丰云配  【非全款】的就根据公司配置那来 配的哪个走哪个快递
        //4.把现在发中通的规则改成发顺丰风云配 CQRXSF.0235487868_241231
        //5.全款支付且应付金额小于等于100元，快递方式默认中通小件455 ZTO 中通小件 CQRXSF.0235487868_241231

        if(order.getCompanyId()!=null&&order.getStoreHouseCode()!=null&&order.getStoreHouseCode().equals("WHSP001")){
            //杭州家有仙妻实业有限公司 全部订单快递方式设置为商城德邦快递
            FsExpress express=fsExpressCacheService.selectFsExpressByOmsCode("SF-WHC");
            erpOrder.setExpress_code(express.getOmsCode());
            order.setDeliveryName(express.getName());
            order.setDeliverySn(express.getCode());
            if(order.getPayDelivery().compareTo(new BigDecimal(0))==0){

            }
            else{
                //物流代收金额
                ErpOrderPayment codPayment=new ErpOrderPayment();
                codPayment.setPay_type_code("cod");
                codPayment.setPayment(order.getPayDelivery().doubleValue());
                payments.add(codPayment);
                erpOrder.setCod(true);
            }
        } else if(order.getCompanyId()!=null && order.getCompanyId() > 0){
            Company company = companyService.selectCompanyById(order.getCompanyId());
            if (order.getPayDelivery().compareTo(new BigDecimal(0)) == 0) {  //没有物流代收(全款订单)
                FsExpress express = new FsExpress();
                //express=expressService.selectFsExpressByOmsCode(deliverOmsCode);
                if(order.getPayPrice().compareTo(new BigDecimal(100))<=0){
                    express=fsExpressCacheService.selectFsExpressByOmsCode(deliverOmsCode);
                }
                else{
                    boolean found = containsAddress(order.getUserAddress());
                    if(found){
                        express=fsExpressCacheService.selectFsExpressByOmsCode(deliverOmsCode);
                    }
                    else{
                        express=fsExpressCacheService.selectFsExpressByOmsCode(deliverOmsCode);
                    }
                }
                Asserts.notNull(express,"快递没有找到!");
                erpOrder.setExpress_code(express.getOmsCode());
                order.setDeliveryName(express.getName());
                order.setDeliverySn(express.getCode());
            }
            else {
                FsExpress express = new FsExpress();
                boolean found = containsAddress(order.getUserAddress());
                if(found){
                    if(StringUtils.isNotEmpty(company.getOmsCode())){
                        express = fsExpressCacheService.selectFsExpressByOmsCode(company.getOmsCode());
                    }else{
                        express=fsExpressCacheService.selectFsExpressByOmsCode("EMS.1");
                    }
                }
                else{
                    if(StringUtils.isNotEmpty(company.getOmsCode())){
                        express = fsExpressCacheService.selectFsExpressByOmsCode(company.getOmsCode());
                    }else{
                        express = fsExpressCacheService.selectFsExpressByOmsCode(deliverOmsCode);
                    }
                }
                erpOrder.setExpress_code(express.getOmsCode());
                order.setDeliveryName(express.getName());
                order.setDeliverySn(express.getCode());
                //物流代收金额
                ErpOrderPayment codPayment = new ErpOrderPayment();
                codPayment.setPay_type_code("cod");
                codPayment.setPayment(order.getPayDelivery().doubleValue());
                payments.add(codPayment);
                erpOrder.setCod(true);
            }
        }
        else{
            if(order.getPayDelivery().compareTo(new BigDecimal(0))==0){  //没有物流代收(全款订单)
                FsExpress express=new FsExpress();
                if(order.getPayPrice().compareTo(new BigDecimal(100))<=0){
                    express=fsExpressCacheService.selectFsExpressByOmsCode(deliverOmsCode);
                }else{
                    boolean found = containsAddress(order.getUserAddress());
                    if(found){
                        express=fsExpressCacheService.selectFsExpressByOmsCode(deliverOmsCode);
                    }
                    else{
                        express=fsExpressCacheService.selectFsExpressByOmsCode(deliverOmsCode);
                    }
                }
                erpOrder.setExpress_code(express.getOmsCode());
                order.setDeliveryName(express.getName());
                order.setDeliverySn(express.getCode());
            }
            else{
                ErpOrderPayment codPayment=new ErpOrderPayment();
                codPayment.setPay_type_code("cod");
                codPayment.setPayment(order.getPayDelivery().doubleValue());
                payments.add(codPayment);
                erpOrder.setCod(true);
                FsExpress express=new FsExpress();
                boolean found = containsAddress(order.getUserAddress());
                if(found){
                    express=fsExpressCacheService.selectFsExpressByOmsCode("EMS.1");
                }
                else {
                    express=fsExpressCacheService.selectFsExpressByOmsCode(deliverOmsCode);
                }
                erpOrder.setExpress_code(express.getOmsCode());
                order.setDeliveryName(express.getName());
                order.setDeliverySn(express.getCode());
            }
        }
        erpOrder.setPayments(payments);
        if(order.getCompanyId()!=null){
            Company company=companyService.selectCompanyById(order.getCompanyId());
            if(company!=null){
                erpOrder.setSeller_memo(company.getCompanyName());
            }
        }
        if(order.getCompanyUserId()!=null){
            CompanyUser companyUser=companyUserService.selectCompanyUserById(order.getCompanyUserId());
            if(companyUser!=null){
                CompanyDept dept=companyDeptService.selectCompanyDeptById(companyUser.getDeptId());
                if(dept!=null){
                    List<String> names=companyDeptService.selectCompanyDeptNamesByIds(dept.getAncestors());
                    if(names!=null&&names.size()>0){
                        //写备注
                        erpOrder.setSeller_memo(erpOrder.getSeller_memo()+"-"+StringUtils.join(names, ",")+","+dept.getDeptName() );
                    }
                }
                erpOrder.setSeller_memo(erpOrder.getSeller_memo()+"-"+companyUser.getNickName());
            }
        }

        if(!"WHSP001".equals(order.getStoreHouseCode())){
            erpOrder.setSeller_memo(erpOrder.getSeller_memo()+"-"+order.getDeliveryName());
        }
        ErpRemarkDTO remarkDTO=new ErpRemarkDTO();
        remarkDTO.setTotalPrice(order.getTotalPrice());
        remarkDTO.setPayPrice(order.getPayPrice());
        remarkDTO.setDeliveryMoney(order.getPayDelivery());
        remarkDTO.setPayMoney(order.getPayMoney());
        remarkDTO.setCouponMoney(BigDecimal.ZERO);
        remarkDTO.setOrderId(order.getOrderCode());
        remarkDTO.setYdMoney(order.getPayPrice().subtract(order.getPayMoney().subtract(order.getPayDelivery())));

        if(order.getPayTime()!=null){
            SimpleDateFormat sdf = new SimpleDateFormat("yyyy-MM-dd HH:mm:ss");
            String format = DateUtil.format(order.getPayTime(),"yyyy-MM-dd HH:mm:ss");

            remarkDTO.setPayTime(format);
        }
        erpOrder.setSeller_memo(erpOrder.getSeller_memo()+JSONUtil.toJsonStr(remarkDTO));

        erpOrder.setOrder_type_code("order");
        SimpleDateFormat sdf = new SimpleDateFormat("yyyy-MM-dd HH:mm:ss");
        erpOrder.setDeal_datetime(sdf.format(new Date()));
        List<LiveOrderItem> orderItems=liveOrderItemMapper.selectLiveOrderItemByOrderId(order.getOrderId());
        List<ErpOrderItem> details=new ArrayList<>();
        for(LiveOrderItem orderItem: orderItems){
            FsStoreCartDTO cartDTO= JSONUtil.toBean(orderItem.getJsonInfo(),FsStoreCartDTO.class);
            //如果是组合码，查询出真实的商品数据 然后写入
            if(StringUtils.isNotEmpty(cartDTO.getGroupBarCode())){
                FsStoreProductGroup group=storeProductGroupService.selectFsStoreProductGroupByBarCode(cartDTO.getGroupBarCode().trim());
                if(group!=null){
                    JSONArray jsonArray=JSONUtil.parseArray(group.getProducts());
                    List<StoreProductGroupDTO> productGroupDTOS=JSONUtil.toList(jsonArray, StoreProductGroupDTO.class);
                    if(productGroupDTOS!=null){
                        for(StoreProductGroupDTO dto:productGroupDTOS){
                            FsStoreProductAttrValue attrValue=fsStoreProductAttrValueCacheService.selectFsStoreProductAttrValueById(dto.getId());

                            ErpOrderItem item=new ErpOrderItem();
                            item.setItem_code(attrValue.getBarCode());
                            item.setPrice(attrValue.getPrice().toString());
                            item.setQty(dto.getCount()*cartDTO.getNum());
                            item.setRefund(0);
                            // 查询仓库代码
                            String warehouseCode = fsStoreProductCacheService.getWarehouseCodeByProductId(attrValue.getProductId());
                            if(StringUtils.isNotBlank(warehouseCode)){
                                item.setWarehouseCode(warehouseCode);
                            }
                            details.add(item);
                        }
                    }
                }
            }
            else{
                ErpOrderItem item=new ErpOrderItem();
                item.setItem_code(cartDTO.getBarCode().trim());
                item.setPrice(cartDTO.getPrice().toString());
                item.setQty(cartDTO.getNum());
                // 仓库代码
                FsStoreProduct fsStoreProduct = fsStoreProductService.selectFsStoreProductById(cartDTO.getProductId());
                if(ObjectUtil.isNotNull(fsStoreProduct)){
                    item.setWarehouseCode(cartDTO.getWarehouseCode());
                }
                item.setRefund(0);
                details.add(item);
            }
        }
        erpOrder.setDetails(details);
        erpOrder.setReceiver_name(order.getUserName());
        if(order.getUserPhone().length()>11){
            erpOrder.setReceiver_phone(order.getUserPhone());
        }
        else{
            erpOrder.setReceiver_mobile(order.getUserPhone());
        }
        String[] address=order.getUserAddress().split(" ");
        erpOrder.setReceiver_province(address[0]);
        erpOrder.setReceiver_city(address[1]);
        erpOrder.setReceiver_district(address[2]);
        //处理地址多空隔问题
        if(address.length>3){
            StringBuffer addrs=new StringBuffer();
            for(int i=3;i<address.length;i++){
                addrs.append(address[i]);
            }
            erpOrder.setReceiver_address(addrs.toString());
        }
        else if(address.length==3){
            erpOrder.setReceiver_address(address[2]);
        }
        //处理地址字符问题
        erpOrder.setReceiver_address(erpOrder.getReceiver_address().replace("+","加"));
        erpOrder.setReceiver_address(erpOrder.getReceiver_address().replace("\n",""));

//        // 如果订单是套餐
//        if(ObjectUtil.equal(order.getIsPackage(),1)){
//            JSONObject jsonObject = JSON.parseObject(order.getPackageJson());
//            if(StringUtils.isBlank(order.getPackageJson())){
//                log.error("套餐订单缺少套餐信息：{}", orderId);
//                return;
//            }
//            Long packageId = jsonObject.getLong("packageId");
//            // 根据套餐id找商品
//            FsStoreProductPackage fsStoreProductPackage = fsStoreProductPackageService.selectFsStoreProductPackageById(packageId);
//            if(ObjectUtil.isNull(fsStoreProductPackage)){
//                log.error("套餐id找不到! 套餐id:{} 订单id:{}",packageId, orderId);
//                return;
//            }
//            String products = fsStoreProductPackage.getProducts();
//            if(StringUtils.isBlank(products)){
//                log.error("套餐商品列表为空! 套餐id:{} 订单id:{}", packageId, orderId);
//            }
//            com.alibaba.fastjson.JSONArray objects = com.alibaba.fastjson.JSONArray.parseArray(products);
//            if(CollectionUtil.isEmpty(objects)){
//                log.error("套餐商品列表为空! 套餐id:{} 订单id:{}", packageId, orderId);
//                return;
//            }
//
//            JSONObject jsonObject1 = objects.getJSONObject(0);
//            Long id = jsonObject1.getLong("id");
//            FsStoreProductAttrValue attrValue=fsStoreProductAttrValueCacheService.selectFsStoreProductAttrValueById(id);
//            if(attrValue!=null) {
//                // 根据产品id找仓库id
//                String warehouseCode = fsStoreProductCacheService.getWarehouseCodeByProductId(attrValue.getProductId());
//                if(StringUtils.isBlank(warehouseCode)){
//                    log.error("套餐商品id找不到! 商品id:{} 订单id:{}", attrValue.getProductId(), orderId);
//                    return;
//                }
//                erpOrder.setWarehouse_code(warehouseCode);
//                order.setStoreHouseCode(warehouseCode);
//
//                // 根据仓库code找erp
//                String erp = fsWarehousesMapper.selectErpByCode(warehouseCode);
//                ErpContextHolder.setErpType(erp);
//
//            }
//
//        }
        // 如果不是套餐
//        else {
            Asserts.notNull(order.getItemJson(),"当前订单没有商品!");
            JSONObject jsonObject = JSON.parseObject(order.getItemJson());
            if(CollectionUtil.isEmpty(jsonObject)){
                log.error("订单商品列表为空! 订单id:{}", orderId);
                return;
            }
            Long productId = jsonObject.getLong("productId");
            Asserts.notNull(productId,"产品id不存在!");
            FsStoreProduct fsStoreProduct = fsStoreProductService.selectFsStoreProductById(productId);
            String warehouseCode = fsStoreProduct.getWarehouseCode();
            if(StringUtils.isBlank(warehouseCode)){
                log.error("当前订单 {} 的仓库id不存在!",order.getOrderId());
                return;
            }
            order.setStoreHouseCode(warehouseCode);
            erpOrder.setWarehouse_code(warehouseCode);

            // 根据仓库code找erp
            String erp = fsWarehousesMapper.selectErpByCode(warehouseCode);
            ErpContextHolder.setErpType(erp);
//        }


        // 设置erp shopCode
        String erpType = ErpContextHolder.getErpType();
        if(ErpTypeConstant.GY_ERP.equals(erpType)){
            erpOrder.setShop_code(sysConfig.getErpShopCode());
        } else {
            erpOrder.setShop_code(jstShopCode);
        }

        ErpOrderResponse response= erpOrderService.addLiveOrder(erpOrder);
        //写入日志
        log.info("ErpCreate:{} {}",order.getOrderCode(),JSONUtil.toJsonStr(response));
        //支付成功后 将订单号写入待发货的REDIS中
        redisCache.setCacheObject(DELIVERY+":"+response.getCode(),order.getOrderCode());
        //写入外部订单号
        order.setExtendOrderId(response.getCode());
        baseMapper.updateLiveOrder(order);

        ErpContextHolder.clear();
    }

    @Override
    public List<LiveOrder> selectDeliverPenddingData() {
        return baseMapper.selectDeliverPenddingData();
    }

    @Override
    @Transactional(rollbackFor = Exception.class,propagation = Propagation.REQUIRED)
    public void deliveryOrder(String orderCode, String deliveryId, String deliverCode, String deliverName) {
        LiveOrder order = baseMapper.selectFsUserVipOrderByOrderCode(orderCode);
        if(order!=null&& Objects.equals(order.getStatus(), 2)){
            // 更新订单状态
            order.setStatus(3);
            order.setDeliverySendTime(new Date());
            FsExpress express=fsExpressCacheService.selectFsExpressByOmsCode(deliverCode);

            order.setDeliveryName(deliverName);
            order.setDeliverySn(deliveryId);
            order.setDeliveryCode(express.getCode());
            liveUserLotteryRecordMapper.updateOrderStatusByOrderId(order.getOrderId(), 3);
            baseMapper.updateLiveOrder(order);
            if(ObjectUtil.isNotNull(express)) {
                FsStoreDelivers fsStoreDeliver = new FsStoreDelivers();
                fsStoreDeliver.setOrderId(order.getOrderId());
                fsStoreDeliver.setOrderCode(orderCode);
                fsStoreDeliver.setDeliverId(deliveryId);
                fsStoreDeliver.setDeliverSn(express.getCode());
                fsStoreDeliver.setDeliverName(express.getName());
                fsStoreDeliver.setCreateTime(LocalDateTime.now());
                fsStoreDeliver.setUpdateTime(LocalDateTime.now());
                fsStoreDeliver.setCreateBy("admin");
                fsStoreDeliver.setUpdateBy("admin");
                fsStoreDeliver.setType(1);
                fsStoreDeliversMapper.insert(fsStoreDeliver);
            }
            FsWxExpressTask fsWxExpressTask = new FsWxExpressTask();
            fsWxExpressTask.setUserId(Long.valueOf(order.getUserId()));
            fsWxExpressTask.setStatus(0);
            fsWxExpressTask.setRetryCount(0);
            fsWxExpressTask.setCreateTime(LocalDateTime.now());
            fsWxExpressTask.setUpdateTime(LocalDateTime.now());
            fsWxExpressTask.setOrderCode(order.getOrderCode());
            fsWxExpressTask.setExpressCompany(express.getCode());
            fsWxExpressTask.setExpressNo(deliveryId);

            LiveOrderPayment liveOrderPayment = liveOrderPaymentMapper.selectByBuissnessId(order.getOrderId());
            if (liveOrderPayment != null) {
                fsWxExpressTask.setPayCode(liveOrderPayment.getPayCode());
            }
            fsWxExpressTask.setType(1);
            fsWxExpressTaskMapper.insert(fsWxExpressTask);

            // 微信消息通知
            TemplateBean templateBean = TemplateBean.builder()
                    .orderId(order.getOrderId().toString())
                    .orderCode(order.getOrderCode())
                    .deliveryId(deliveryId)
                    .deliveryName(express.getName())
                    .userId(Long.valueOf(order.getUserId()))
                    .templateType(TemplateListenEnum.TYPE_2.getValue())
                    .build();
            publisher.publishEvent(new TemplateEvent(this, templateBean));

            //订阅物流回调
            String lastFourNumber = "";
            if (StringUtils.equals(express.getCode(),ShipperCodeEnum.SF.getValue())) {
                lastFourNumber = PhoneUtils.getLastFourNum(order.getUserPhone());
            }
            expressService.subscribeEspress(order.getOrderCode(),express.getCode(),deliveryId,lastFourNumber,1);
        }
    }


    @Override
    public LiveOrderComputeDTO computedReward(long l, LiveOrderComputedParam param) {
        String orderKey= redisCache.getCacheObject("orderKey:"+param.getOrderKey());
        if (StringUtils.isEmpty(orderKey)) {
            return null;
        }
        FsStoreProduct fsStoreProduct = fsStoreProductService.selectFsStoreProductById(param.getProductId());
        if(fsStoreProduct == null) return null;
        BigDecimal payPrice = BigDecimal.ZERO;
        BigDecimal payDelivery = BigDecimal.ZERO;
        BigDecimal totalPrice = fsStoreProduct.getPrice().multiply(new BigDecimal(param.getTotalNum()));
        if (param.getCityId() != null) {
            payDelivery = handleDeliveryMoney(param.getCityId(), fsStoreProduct, param.getTotalNum());
            totalPrice = totalPrice.add(payDelivery);
        }
        return LiveOrderComputeDTO.builder().payPrice(payPrice)
                .payDelivery(payDelivery)
                .deductionPrice(totalPrice)
                .totalPrice(totalPrice)
                .build();
    }


    @Override
    public LiveOrderComputeDTO computedOrder(long userId, LiveOrderComputedParam param) {
        String orderKey= redisCache.getCacheObject("orderKey:"+param.getOrderKey());
        if (StringUtils.isEmpty(orderKey)) {
            return null;
        }
        FsStoreProduct fsStoreProduct = fsStoreProductService.selectFsStoreProductById(param.getProductId());
        BigDecimal totalPrice = BigDecimal.ZERO;
        BigDecimal payPrice = fsStoreProduct.getPrice().multiply(new BigDecimal(param.getTotalNum()));
        totalPrice = totalPrice.add(payPrice);
        BigDecimal payDelivery = BigDecimal.ZERO;
        BigDecimal deductionPrice = BigDecimal.ZERO;
        if (param.getCityId() != null) {
            payDelivery = handleDeliveryMoney(param.getCityId(), fsStoreProduct, param.getTotalNum());
            payPrice = payPrice.add(payDelivery);
        }

        if(param.getCouponUserId()!=null){
            LiveCouponUser couponUser=liveCouponUserService.selectLiveCouponUserById(param.getCouponUserId());
            if(couponUser!=null&&couponUser.getStatus()==0){
                if(couponUser.getUseMinPrice().compareTo(payPrice) < 1){
                    payPrice=payPrice.subtract(couponUser.getCouponPrice());
                    deductionPrice = couponUser.getCouponPrice();
                }
            }
        }


        return LiveOrderComputeDTO.builder().payPrice(payPrice)
                .payDelivery(payDelivery)
                .deductionPrice(deductionPrice)
                .totalPrice(totalPrice)
                .build();
    }

    @Override
    public LiveOrder selectOrderIdByOrderCode(String platformCode) {
        return baseMapper.selectFsUserVipOrderByOrderCode(platformCode);
    }

    @Override
    public R auditPayRemain(Long orderId) {
        return R.ok();
//        LiveOrder order = liveOrderMapper.selectLiveOrderByOrderId(String.valueOf(orderId));
//        if(order.getIsPayRemain()==1){
//            FsStoreOrder storeOrder = new FsStoreOrder();
//            storeOrder.setId(order.getId());
//            storeOrder.setIsPayRemain(2);
//            storeOrder.setPayType("1");
//            storeOrder.setPayMoney(order.getPayPrice());
//            storeOrder.setPayDelivery(new BigDecimal(0));
//            fsStoreOrderMapper.updateFsStoreOrder(storeOrder);
//            return R.ok("操作成功");
//        }
//        else{
//            return R.error("非法操作");
//        }
//        return null;
    }

    @Override
    public R addTuiMoney(FsStoreOrderAddTuiMoneyParam param) {
        LiveOrder order = liveOrderMapper.selectLiveOrderByOrderId(String.valueOf(param.getOrderId()));
        if(order.getStatus()!=OrderInfoEnum.STATUS_3.getValue()) {
            return R.error("订单未完成，不能分佣金");
        }
        if (order.getCompanyId() != null && order.getCompanyId() > 0 && order.getPayDelivery().compareTo(new BigDecimal(0)) == 0) {
            if (order.getTuiMoneyStatus() == null || order.getTuiMoneyStatus() != 1) {
                companyService.addCompanyTuiLiveMoney(order);
                return R.ok();
            }
            else{
                return R.error("此订单已分佣，不能重复分佣");
            }
        }
        else{
            return R.error("此订单不能手动分佣");
        }
    }

    @Override
    public R updateExpress(Long orderId) {
        LiveOrder order = liveOrderMapper.selectLiveOrderByOrderId(String.valueOf(orderId));
        if(order.getStatus()!=1){
            return R.error("只有待发货状态可以同步");
        }
        if(order.getExtendOrderId()==null){
            return R.error("未生成管易云订单");
        }
        ErpOrderQueryRequert request = new ErpOrderQueryRequert();
        request.setCode(order.getExtendOrderId());
        // 根据仓库code找erp
        if(com.fs.common.utils.StringUtils.isNotBlank(order.getStoreHouseCode())){
            String erp = fsWarehousesMapper.selectErpByCode(order.getStoreHouseCode());
            ErpContextHolder.setErpType(erp);
        }
        ErpOrderQueryResponse response = erpOrderService.getOrderLive(request);
        if(response.getOrders()!=null&&response.getOrders().size()>0){
            for(ErpOrderQuery orderQuery : response.getOrders()){
                if(orderQuery.getDeliverys()!=null&&orderQuery.getDeliverys().size()>0){
                    for(ErpDeliverys delivery:orderQuery.getDeliverys()){
                        if(delivery.getDelivery()&& StringUtils.isNotEmpty(delivery.getMail_no())){
                            LiveOrder map=new LiveOrder();
                            map.setStatus(OrderInfoEnum.STATUS_2.getValue());
                            map.setOrderId(order.getOrderId());
                            map.setDeliverySn(response.getOrders().get(0).getDeliverys().get(0).getMail_no());
                            liveUserLotteryRecordMapper.updateOrderStatusByOrderId(order.getOrderId(), 2);
                            liveOrderMapper.updateLiveOrder(map);
                            liveOrderLogsService.create(order.getOrderId(), OrderLogEnum.DELIVERY_GOODS.getValue(),
                                    OrderLogEnum.DELIVERY_GOODS.getDesc());
                            TemplateBean templateBean = TemplateBean.builder()
                                    .orderId(order.getOrderId().toString())
                                    .orderCode(order.getOrderCode().toString())
                                    .deliveryId(order.getDeliverySn())
                                    .deliveryName(order.getDeliveryName())
                                    .userId(Long.valueOf(order.getUserId()))
                                    .templateType(TemplateListenEnum.TYPE_2.getValue())
                                    .build();
                            publisher.publishEvent(new TemplateEvent(this, templateBean));
                            return R.ok();
                        }
                    }

                }
            }
        }
        return R.error("未生成运单信息");
    }

    @Override
    public LiveOrder selectLiveOrderByExtendId(String extendOrderId) {
        return baseMapper.selectLiveOrderByExtendId(extendOrderId);
    }

    @Override
    @Transactional
    public R editTuiMoney(Long orderId) {
        LiveOrder order= liveOrderMapper.selectLiveOrderByOrderId(String.valueOf(orderId));
        if(order.getTuiMoney()!=null&&order.getTuiMoney().compareTo(new BigDecimal(0))==1){
            if(order.getTuiMoneyStatus().equals(0)){
                order.setTuiMoneyStatus(1);
                liveOrderLogsService.create(order.getOrderId(), OrderLogEnum.UNLOCK_TUI_MONEY.getValue(),
                        OrderLogEnum.UNLOCK_TUI_MONEY.getDesc());
                //写入公司余额
                Company company=companyService.selectCompanyById(order.getCompanyId());
                company.setMoney(company.getMoney().add(order.getTuiMoney()));
                companyService.updateCompany(company);
                //写入日志
                CompanyMoneyLogs log=new CompanyMoneyLogs();
                log.setCompanyId(order.getCompanyId());
                log.setRemark("订单佣金解冻");
                log.setMoney(order.getTuiMoney());
                log.setLogsType(4);
                log.setBalance(company.getMoney());
                log.setCreateTime(new Date());
                log.setBusinessId(order.getOrderId().toString());
                moneyLogsMapper.insertCompanyMoneyLogs(log);
                liveOrderMapper.updateLiveOrder(order);
                return R.ok("解冻成功");
            }
            else{
                order.setTuiMoneyStatus(0);
                //写入公司余额
                Company company=companyService.selectCompanyById(order.getCompanyId());
                company.setMoney(company.getMoney().subtract(order.getTuiMoney()));
                companyService.updateCompany(company);
                //写入日志
                CompanyMoneyLogs log=new CompanyMoneyLogs();
                log.setCompanyId(order.getCompanyId());
                log.setRemark("订单佣金冻结");
                log.setMoney(order.getTuiMoney().multiply(new BigDecimal(-1)));
                log.setLogsType(5);
                log.setBalance(company.getMoney());
                log.setCreateTime(new Date());
                log.setBusinessId(order.getOrderId().toString());
                moneyLogsMapper.insertCompanyMoneyLogs(log);
                liveOrderMapper.updateLiveOrder(order);
                return R.ok("updateLiveOrder");
            }

        }
        else {
            return R.error("推广佣金不存在");
        }
    }

    @Override
    public LiveOrder selectLiveOrderByOrderCode(String orderCode) {
        return liveOrderMapper.selectLiveOrderByOrderCode(orderCode);
    }

    @Override
    public R getExpressMulti(LiveOrder order) {
        //顺丰轨迹查询处理
        String lastFourNumber = PhoneUtils.getLastFourNum(order.getUserPhone());
        // 获取该订单关联的物流信息
        List<FsStoreDelivers> fsStoreDelivers = fsStoreDeliversMapper.findByOrderIdWithType(order.getOrderId(),1);
        if(CollectionUtils.isEmpty(fsStoreDelivers)){
            return R.ok("当前订单号暂无物流信息");
        }

        List<ExpressInfoDTO> result = new ArrayList<>();
        for (FsStoreDelivers fsStoreDeliver : fsStoreDelivers) {
            ExpressInfoDTO dto=expressService.getExpressInfo(order.getOrderCode(),
                    fsStoreDeliver.getDeliverSn(),
                    fsStoreDeliver.getDeliverId(),
                    lastFourNumber);
            result.add(dto);
        }

        return R.ok().put("data",result);
    }

    @Override
    public R getExpress(LiveOrder order) {
        //顺丰轨迹查询处理
        String lastFourNumber = "";
        if (order.getDeliverySn().equals(ShipperCodeEnum.SF.getValue())) {
            lastFourNumber = PhoneUtils.getLastFourNum(order.getUserPhone());
        }
        ExpressInfoDTO dto=expressService.getExpressInfo(order.getOrderCode(),order.getDeliveryCode(),order.getDeliverySn(),lastFourNumber);
        dto.setShipperName(order.getDeliveryName());
        FsExpress express=expressService.selectFsExpressByName(order.getDeliveryName());
        return R.ok().put("data", dto).put("express",express).put("deliveryId",order.getDeliverySn());
    }

    @Override
    public void orderCancel() {

        List<LiveOrder> fsStoreOrders = liveOrderMapper.selectFsOutDateOrder();
        for (LiveOrder order : fsStoreOrders) {
            try{
                this.cancelOrder(order);
            }catch (Exception e){
                log.error("直播超时订单结束失败！",e);
            }
        }
    }

    private BigDecimal handleDeliveryMoney(Long cityId, FsStoreProduct fsStoreProduct, String totalNumSize) {
        BigDecimal storePostage = BigDecimal.ZERO;
        List<Long> citys = new ArrayList<>();
        citys.add(cityId);
        citys.add(0l);
        String ids = String.valueOf(fsStoreProduct.getTempId());
        List<FsShippingTemplates> shippingTemplatesList = shippingTemplatesService.selectFsShippingTemplatesByIds(ids);
        String cityIds = String.join(",", citys.stream()
                .map(String::valueOf).collect(Collectors.toList()));
        List<FsShippingTemplatesRegion> shippingTemplatesRegionList = shippingTemplatesRegionService.selectFsShippingTemplatesRegionListByTempIdsAndCityIds(ids,cityIds);
        Map<Long, Integer> shippingTemplatesMap = shippingTemplatesList
                .stream()
                .collect(Collectors.toMap(FsShippingTemplates::getId,
                        FsShippingTemplates::getType));
        //提取运费模板有相同值覆盖
        Map<Long, FsShippingTemplatesRegion> shippingTemplatesRegionMap =
                shippingTemplatesRegionList.stream()
                        .collect(Collectors.toMap(FsShippingTemplatesRegion::getTempId,
                                YxShippingTemplatesRegion -> YxShippingTemplatesRegion,
                                (key1, key2) -> key2));
        Long tempId = Long.valueOf(fsStoreProduct.getTempId());
        double num = 0d;
        Integer templateType = shippingTemplatesMap.get(tempId);
        List<FsStoreProductAttrValue> productAttrValues = fsStoreProductAttrValueMapper.selectFsStoreProductAttrValueByProductId(fsStoreProduct.getProductId());
        if(productAttrValues == null || productAttrValues.isEmpty()) {
            return storePostage;
        }
        FsStoreProductAttrValue productAttrValue = productAttrValues.get(0);
        Integer totalNum = Integer.valueOf(totalNumSize);
        // TYPE_1: 按件数计算
        if (ShippingTempEnum.TYPE_1.getValue().equals(templateType)) {
            num = totalNum.doubleValue();
        }
        // TYPE_2: 按重量计算（数量 × 重量）
        else if (ShippingTempEnum.TYPE_2.getValue().equals(templateType)) {
            num = NumberUtil.mul(totalNum, productAttrValue.getWeight()).doubleValue();
        }
        // TYPE_3: 按体积计算（数量 × 体积）
        else if (ShippingTempEnum.TYPE_3.getValue().equals(templateType)) {
            num = NumberUtil.mul(totalNum, productAttrValue.getVolume()).doubleValue();
        }
        FsShippingTemplatesRegion shippingTemplatesRegion = shippingTemplatesRegionMap.get(tempId);
        if (shippingTemplatesRegion == null) {
            log.error("没有找到运费模板");
            return storePostage;
        }
        BigDecimal price = NumberUtil.round(NumberUtil.mul(totalNum, fsStoreProduct.getPrice()), 2);

        TemplateDTO templateDTO = TemplateDTO.builder()
                .number(num)  // 累计数量（件数/重量/体积）
                .price(price)  // 累计金额
                .first(shippingTemplatesRegion.getFirst().doubleValue())  // 首件数量
                .firstPrice(shippingTemplatesRegion.getFirstPrice())  // 首件运费
                .continues(shippingTemplatesRegion.getContinues().doubleValue())  // 续件数量
                .continuePrice(shippingTemplatesRegion.getContinuePrice())  // 续件运费
                .tempId(tempId)  // 模板ID
                .cityId(cityId)  // 城市ID
                .build();
        //只满足首件
        if (Double.compare(templateDTO.getNumber(), templateDTO.getFirst()) <= 0) {
            storePostage = NumberUtil.round(NumberUtil.add(storePostage,
                    templateDTO.getFirstPrice()), 2);
        } else {
            BigDecimal firstPrice = NumberUtil.add(storePostage, templateDTO.getFirstPrice());

            if (templateDTO.getContinues() <= 0) {
                storePostage = firstPrice;
            } else {
                //续件平均值且向上取整数
                double average = Math.ceil(NumberUtil.div(NumberUtil.sub(templateDTO.getNumber(),
                                templateDTO.getFirst()),
                        templateDTO.getContinues().doubleValue()));
                //最终邮费
                storePostage = NumberUtil.add(firstPrice, NumberUtil.mul(average,
                        templateDTO.getContinuePrice()));
            }

        }

        return storePostage;
    }

    public  boolean containsAddress(String companyName) {
        String[] items= {"新疆","西藏","内蒙古","海南"};
        boolean found = false;
        for (String item : items) {
            if (companyName.contains(item)) {
                found = true;
                break;
            }
        }
        return found;
    }

    @Transactional(rollbackFor = Exception.class,propagation = Propagation.REQUIRED)
    public R finishStoreOrder(Long orderId){
        LiveOrder order= baseMapper.selectLiveOrderByOrderId(String.valueOf(orderId));
        if(order.getStatus()==OrderInfoEnum.STATUS_3.getValue()){
            order.setFinishTime(new Date());
            order.setStatus(4);
            liveUserLotteryRecordMapper.updateOrderStatusByOrderId(order.getOrderId(), 4);
            baseMapper.updateLiveOrder(order);
            liveOrderLogsService.create(order.getOrderId(), OrderLogEnum.FINISH_ORDER.getValue(),
                    OrderLogEnum.FINISH_ORDER.getDesc());

            //写入公司余额 条件是只有全款订单才分，非全款后台导入
            if(order.getCompanyId()!=null&&order.getCompanyId()>0&&order.getPayDelivery().compareTo(new BigDecimal(0))==0){
                if(order.getTuiMoneyStatus()==null||order.getTuiMoneyStatus()!=1){
                    companyService.addCompanyMoney(order);
                }
            }
            //模板消息支付成功发布事件
            TemplateBean templateBean = TemplateBean.builder()
                    .orderId(order.getOrderId().toString())
                    .orderCode(order.getOrderCode())
                    .remark("您的订单已签收成功")
                    .finishTime(order.getFinishTime())
                    .userId(Long.valueOf(order.getUserId()))
                    .templateType(TemplateListenEnum.TYPE_3.getValue())
                    .build();
            publisher.publishEvent(new TemplateEvent(this, templateBean));
            return R.ok("操作成功");
        }
        else {
            return R.error("非法操作");
        }
    }

    /**
     * 新增订单
     *
     * @param liveOrder 订单
     * @return 结果
     */
    @Override
    @Transactional
    public Long insertLiveOrder(LiveOrder liveOrder)
    {
        //创建时间
        liveOrder.setCreateTime(DateUtils.getNowDate());
        //订单状态 默认1
        liveOrder.setStatus(1);
        //支付状态 默认0
        liveOrder.setIsPay("0");
        //支付类型 默认1微信
        liveOrder.setPayType("1");
        baseMapper.insertLiveOrder(liveOrder);
        return liveOrder.getOrderId();
    }

    /**
     * 修改订单
     *
     * @param liveOrder 订单
     * @return 结果
     */
    @Override
    @Transactional
    public int updateLiveOrder(LiveOrder liveOrder)
    {
        liveOrder.setUpdateTime(DateUtils.getNowDate());
        liveUserLotteryRecordMapper.updateOrderStatusByOrderId(liveOrder.getOrderId(), liveOrder.getStatus());
        return baseMapper.updateLiveOrder(liveOrder);
    }

    /**
     * 批量删除订单
     *
     * @param orderIds 需要删除的订单主键
     * @return 结果
     */
    /*@Override
    public int deleteLiveOrderByOrderIds(String[] orderIds)
    {
        return baseMapper.deleteLiveOrderByOrderIds(orderIds);
    }*/

    /**
     * 删除订单信息
     *
     * @param
     * @return 结果
     */
    /*@Override
    public int deleteLiveOrderByOrderId(String orderId)
    {
        return baseMapper.deleteLiveOrderByOrderId(orderId);
    }*/

    @Override
    @Transactional
    public void handlePay(LiveOrder liveOrder) {
        //订单状态
        //插入订单详情
        //插入操作日志

    }

    @Override
    public R liveOrderUser(String liveId) {
        LiveOrderQueryVO liveOrder = new LiveOrderQueryVO();
        liveOrder.setLiveId(Long.parseLong(liveId));
        liveOrder.setStatus(1);
        List<LiveOrder>  list =baseMapper.selectLiveOrderList(liveOrder);
        if (list == null || list.isEmpty())
            return R.ok().put("count", 0);
        int count = list.size();
        String userName = list.get(0).getUserName();
        return R.ok().put("count",count).put("userName",userName);
    }

    @Override
    public R getLiveOrderTimeGranularity(LiveOrderVo liveOrder) {
        LocalDateTime startTime;
        LocalDateTime finishTime;
        Live live = liveMapper.selectLiveByLiveId(Long.valueOf(liveOrder.getLiveId()));
        if (live.getFinishTime() == null) {
            live.setFinishTime(LocalDateTime.now());
        }
        int step = Integer.parseInt(liveOrder.getTimeGranularity());
        if ("all".equals(liveOrder.getTimeOptions())) {
            startTime = DateUtils.getLiveOrderStartTime(live.getStartTime(), step);
            finishTime = live.getFinishTime();
        } else {
            int i = Integer.parseInt(liveOrder.getTimeOptions());
            startTime = DateUtils.getLiveOrderStartTime(live.getFinishTime().minusHours(i), step);
            Date date1 = Date.from(startTime.atZone(ZoneId.systemDefault()).toInstant());
            liveOrder.setCreateTime(date1);
            finishTime = live.getFinishTime();
        }
        List<LiveOrder> liveOrderList = baseMapper.getLiveOrderTimeGranularity(liveOrder);
        LinkedList<LocalDateTime> hourlySlots = DateUtils.splitTimeByStep(startTime, finishTime, ChronoUnit.MINUTES, step);
        LinkedList<String> resultXLine = new LinkedList<>();
        LinkedList<Integer> hourlySlotsValue = new LinkedList<>();
        boolean crossDay = DateUtils.isCrossDay(startTime, finishTime);
        for (LocalDateTime hourlySlot : hourlySlots) {
            hourlySlotsValue.add((int) liveOrderList.stream()
                    .filter(item -> item.getCreateTime().toInstant().atZone(ZoneId.systemDefault()).toLocalDateTime()
                            .isAfter(hourlySlot) &&
                            item.getCreateTime().toInstant().atZone(ZoneId.systemDefault()).toLocalDateTime()
                                    .isBefore(hourlySlot.plus(step, ChronoUnit.MINUTES))).count());
            if (crossDay) {
                resultXLine.add(hourlySlot.format(DateTimeFormatter.ofPattern("MM月dd日 HH:mm")));
            } else {
                resultXLine.add(hourlySlot.format(DateTimeFormatter.ofPattern("HH:mm")));
            }
        }
        R result = R.ok();
        result.put("hourlySlots", resultXLine);
        result.put("hourlySlotsValue", hourlySlotsValue);
        return result;

    }

    @Override
    @Transactional
    public R syncExpress(Long id) {
        LiveOrder order = baseMapper.selectLiveOrderByOrderId(String.valueOf(id));
        String lastFourNumber = "";
        if (order.getDeliveryCode().equals(ShipperCodeEnum.SF.getValue())) {
            lastFourNumber = order.getUserPhone();
            if (lastFourNumber.length() == 11) {
                lastFourNumber = StrUtil.sub(lastFourNumber, lastFourNumber.length(), -4);
            }else if(lastFourNumber.length() >11){
                String jm = ParseUtils.parsePhone(lastFourNumber);
                lastFourNumber = StrUtil.sub(jm, jm.length(), -4);
            }
        }
        ExpressInfoDTO dto=expressService.getExpressInfo(order.getOrderCode(),order.getDeliveryCode(),order.getDeliverySn(),lastFourNumber);
        log.info("快递鸟查询dto:{}", JSONUtil.toJsonStr(dto));
        if (!dto.isSuccess()){
            return R.error(dto.getReason());
        }
        if("0".equals(dto.getStateEx())&&"0".equals(dto.getState())){
            lastFourNumber = "19923690275";
            if (order.getDeliveryCode().equals(ShipperCodeEnum.SF.getValue())) {
                lastFourNumber = order.getUserPhone();
                if (lastFourNumber.length() == 11) {
                    lastFourNumber = StrUtil.sub(lastFourNumber, lastFourNumber.length(), -4);
                }
            }
            dto=expressService.getExpressInfo(order.getOrderCode(),order.getDeliveryCode(),order.getDeliverySn(),lastFourNumber);
        }
        LiveOrder updateEntity = new LiveOrder();
        updateEntity.setOrderId(order.getOrderId());
        updateEntity.setDeliveryStatus(Integer.parseInt(dto.getState()));
        updateEntity.setDeliveryType(dto.getStateEx());
        baseMapper.updateLiveOrder(updateEntity);
        //如果是正常签收，更新订单状态
        if(dto.getState().equals("3")&&(dto.getStateEx().equals("301")||dto.getStateEx().equals("302")||dto.getStateEx().equals("304")||dto.getStateEx().equals("311"))){
            this.getGoods(order.getOrderId());
        }
        return R.ok();
    }

    @Override
    public int getGoods(Long orderId) {

        LiveOrder order = baseMapper.selectLiveOrderByOrderId(String.valueOf(orderId));
        if (order==null)throw new CustomException("订单不存在");
        if (order.getStatus()!= OrderInfoEnum.STATUS_3.getValue())throw new CustomException("非法更改");
        LiveOrder updateEntity = new LiveOrder();
        updateEntity.setOrderId(order.getOrderId());
        updateEntity.setUpdateTime(new DateTime());
        updateEntity.setFinishTime(new Date());
        updateEntity.setStatus(OrderInfoEnum.STATUS_3.getValue());
        log.info("确认收货："+orderId);
//        log.info("确认收货："+orderId);
//        if (order.getCompanyId()!=null&&order.getTuiMoneyStatus()==0&&order.getPayType()==1){
//            log.info("分佣："+orderId);
//            companyService.addCompanyMoney(order);
//            o1.setTuiMoneyTime(new Date());
//        }
//        fsUserWatchService.addUserWatch(order);
//        int i = fsStoreOrderMapper.updateFsStoreOrder(o1);
//        fsStoreOrderLogsService.create(order.getOrderId(), OrderLogEnum.FINISH_ORDER.getValue(),
//                OrderLogEnum.FINISH_ORDER.getDesc());

        int i = baseMapper.updateLiveOrder(updateEntity);
        liveUserLotteryRecordMapper.updateOrderStatusByOrderId(order.getOrderId(), OrderInfoEnum.STATUS_3.getValue());

        return i;
    }

    @Override
    public void updateDeliveryOrder(Long orderId, String deliveryId, String deliverCode, String expressName) {
        LiveOrder existOrder = baseMapper.selectLiveOrderByOrderId(String.valueOf(orderId));
        if (existOrder != null) {
            FsExpress fsExpress = expressService.selectFsExpressByOmsCode(deliverCode);
            if (fsExpress != null) {
                LiveOrder updateEntity = new LiveOrder();
                updateEntity.setOrderId(existOrder.getOrderId());
                updateEntity.setDeliveryName(expressName);
                updateEntity.setDeliverySn(deliveryId);
                updateEntity.setDeliverySendTime(new Date());
                baseMapper.updateLiveOrder(updateEntity);
                // 订阅物流回调
                String lastFourNumber = "";
                if (fsExpress.getCode().equals(ShipperCodeEnum.SF.getValue())) {
                    lastFourNumber = existOrder.getUserPhone();
                    if (lastFourNumber.length() == 11) {
                        lastFourNumber = StrUtil.sub(lastFourNumber, lastFourNumber.length(), -4);
                    }
                }
                expressService.subscribeEspress(existOrder.getOrderCode(),fsExpress.getCode(),deliveryId,lastFourNumber,1);
            }
        }
    }

    @Autowired
    private FsStoreProductMapper fsStoreProductMapper;
    @Override
    public List<LiveGoodsVo> selectLiveOrderItemList(String orderId) {
        LiveOrder liveOrder = baseMapper.selectLiveOrderByOrderId(orderId);
        Asserts.notNull(liveOrder, String.format("该订单 %s 没有找到！", orderId));
        List<LiveGoodsVo> liveGoodsVos = liveGoodsMapper.selectProductListByOrder(liveOrder);

        if (CollectionUtils.isEmpty(liveGoodsVos)) {
            return liveGoodsVos;
        }
        List<String> productIds = liveGoodsVos.stream()
                .map(LiveGoodsVo::getProductId)
                .filter(Objects::nonNull)
                .map(String::valueOf)
                .distinct()
                .collect(Collectors.toList());
        if (CollectionUtils.isEmpty(productIds)) {
            return liveGoodsVos;
        }

        Map<Long, FsStoreProduct> productWarehouseMap =
                fsStoreProductMapper.selectWarehouseCodeByProductIds(productIds);

        liveGoodsVos.forEach(goodsVo -> {
            Long productId = goodsVo.getProductId();
            if (productId != null) {
                FsStoreProduct storeProduct = productWarehouseMap.get(productId);
                if (storeProduct != null) {
                    goodsVo.setWarehouseCode(storeProduct.getWarehouseCode());
                }
            }
        });
        return liveGoodsVos;

    }


    @Override
    public R createRewardLiveOrder(LiveOrder liveOrder) {
        String orderKey= redisCache.getCacheObject("orderKey:"+liveOrder.getOrderKey());
        if (StringUtils.isEmpty(orderKey)) {
            return R.error("订单已过期");
        }
        LiveUserLotteryRecord liveUserLotteryRecord = liveUserLotteryRecordMapper.selectLiveUserLotteryRecordById(liveOrder.getRecordId());
        if(liveUserLotteryRecord == null) return R.error("未查询到中奖记录，请联系管理员处理！");
        if(liveOrder.getLiveId() == null) return R.error("直播ID不能为空");
        if(liveOrder.getProductId() == null) return R.error("购物商品ID不能为空");
        if(liveOrder.getUserName() == null) return R.error("用户名不能为空");
        if(liveOrder.getUserPhone() == null) return R.error("用户手机号不能为空");
        if(liveOrder.getUserAddress() == null) return R.error("用户地址不能为空");
        if(liveOrder.getTotalNum() == null) return R.error("商品数量不能为空");

        Live live = liveMapper.selectLiveByLiveId(liveOrder.getLiveId());
        if(live == null) return R.error("当前直播不存在");
        FsStoreProduct fsStoreProduct = fsStoreProductService.selectFsStoreProductById(liveOrder.getProductId());
        LiveGoods goods = liveGoodsMapper.selectLiveGoodsByProductId(liveOrder.getLiveId(), liveOrder.getProductId());
        if(goods == null) return R.error("当前商品不存在");

        // 更改店铺库存
        fsStoreProduct.setStock(fsStoreProduct.getStock()-Integer.parseInt(liveOrder.getTotalNum()));
        fsStoreProductService.updateFsStoreProduct(fsStoreProduct);
        // 更新直播间库存
        goods.setStock(goods.getStock()-Integer.parseInt(liveOrder.getTotalNum()));
        liveGoodsMapper.updateLiveGoods(goods);

        //判断是否是三种特定产品
        if (fsStoreProduct.getProductId() != null && (fsStoreProduct.getProductId().equals(3168L)
                || fsStoreProduct.getProductId().equals(3184L)
                || fsStoreProduct.getProductId().equals(3185L))) {
            liveOrder.setStoreHouseCode("YDSP001");
        } else {
            liveOrder.setStoreHouseCode("CQDS001");
        }

        LiveUserFirstEntry liveUserFirstEntry = liveUserFirstEntryService.selectEntityByLiveIdUserId(liveOrder.getLiveId(), Long.parseLong(liveOrder.getUserId()));
        liveOrder.setCompanyId(liveUserFirstEntry.getCompanyId());
        liveOrder.setCompanyUserId(liveUserFirstEntry.getCompanyUserId());
        liveOrder.setTuiUserId(liveUserFirstEntry.getCompanyUserId());

        String orderSn = SnowflakeUtils.nextId();
        log.info("订单生成："+orderSn);
        liveOrder.setOrderCode(orderSn);
        BigDecimal totalPrice = fsStoreProduct.getPrice().multiply(new BigDecimal(liveOrder.getTotalNum()));
        // 直播不需要服务费 0915 1735 左
//        String config=configService.selectConfigByKey("store.config");
//        StoreConfig storeConfig= JSONUtil.toBean(config,StoreConfig.class);
//        BigDecimal serviceFee=new BigDecimal(0);
//        if(storeConfig.getServiceFee()!=null){
//            if(liveOrder.getCompanyUserId()==null||liveOrder.getCompanyUserId()==0){
//                serviceFee=storeConfig.getServiceFee();
//            }
//        }
//        payPrice = payPrice.add(serviceFee);
        // 生成
        BigDecimal deliveryMoney = handleDeliveryMoney(liveOrder);
        totalPrice = totalPrice.add(deliveryMoney);
        liveOrder.setDiscountMoney(totalPrice);


        liveOrder.setItemJson(JSON.toJSONString(fsStoreProduct));
        liveOrder.setCreateTime(new Date());
        liveOrder.setUpdateTime(new Date());
        liveOrder.setPayDelivery(deliveryMoney);
        liveOrder.setProductId(fsStoreProduct.getProductId());
        liveOrder.setStatus(OrderInfoEnum.STATUS_1.getValue());
        liveOrder.setPayType("1");
        liveOrder.setTotalPrice(totalPrice);
        liveOrder.setPayMoney(BigDecimal.ZERO);
        try {
            if (baseMapper.insertLiveOrder(liveOrder) > 0) {
                liveUserLotteryRecord.setOrderId(liveOrder.getOrderId());
                liveUserLotteryRecord.setOrderStatus(liveOrder.getStatus());
                liveUserLotteryRecordMapper.updateLiveUserLotteryRecord(liveUserLotteryRecord);
                LiveOrderItemDTO dto=new LiveOrderItemDTO();
                dto.setImage(fsStoreProduct.getImage());
                dto.setSku(String.valueOf(fsStoreProduct.getStock()));

                FsStoreProductAttrValue fsStoreProductAttrValue = fsStoreProductAttrValueMapper.selectFsStoreProductAttrValueByProductId(fsStoreProduct.getProductId()).stream().filter(attrValue -> StringUtils.isNotEmpty(attrValue.getBarCode())).findFirst().orElse(null);
                if (fsStoreProductAttrValue != null) {
                    dto.setBarCode(fsStoreProductAttrValue.getBarCode());
                    dto.setGroupBarCode(fsStoreProductAttrValue.getGroupBarCode());
                }

                dto.setPrice(fsStoreProduct.getPrice());
                dto.setProductName(fsStoreProduct.getProductName());
                dto.setNum(Long.valueOf(liveOrder.getTotalNum()));

                LiveOrderItem liveOrderItem = new LiveOrderItem();
                liveOrderItem.setOrderCode(liveOrder.getOrderCode());
                liveOrderItem.setOrderId(liveOrder.getOrderId());
                liveOrderItem.setProductId(liveOrder.getProductId());
                liveOrderItem.setNum(Long.valueOf(liveOrder.getTotalNum()));
                liveOrderItem.setJsonInfo(JSON.toJSONString(dto));
                liveOrderItemMapper.insertLiveOrderItem(liveOrderItem);
                redisCache.deleteObject("orderKey:" + liveOrder.getOrderKey());
                return R.ok("下单成功").put("order",liveOrder);
            } else {
                return R.error("订单创建失败");
            }
        } catch (Exception e) {
            // 异常处理
            return R.error("订单创建失败：" + e.getMessage());
        }
    }

    @Override
    @Transactional(rollbackFor = Throwable.class,propagation = Propagation.REQUIRED)
    public R payConfirmReward(LiveOrder liveOrder) {
        Long orderId = liveOrder.getOrderId();
        if(orderId==null) return R.error("订单ID不存在");
        Object savePoint = TransactionAspectSupport.currentTransactionStatus().createSavepoint();
        try {
            liveOrder = baseMapper.selectLiveOrderByOrderId(String.valueOf(orderId));
            if(liveOrder==null || !liveOrder.getStatus().equals(1)){
                throw new CustomException("当前订单未找到或者订单状态不为待支付! orderId:" + orderId);
            }
            FsUser user = userMapper.selectFsUserByUserId(Long.valueOf(liveOrder.getUserId()));
            if(user == null) return R.error("用户不存在");
            String json = configService.selectConfigByKey("store.pay");
            FsPayConfig fsPayConfig = JSON.parseObject(json, FsPayConfig.class);
            String payCode =  SnowflakeUtils.nextId();
            if(StringUtils.isEmpty(payCode)){
                return R.error("订单生成失败，请重试");
            }
            LiveOrderPayment storePayment = liveOrderPaymentMapper.selectByBuissnessId(liveOrder.getOrderId());
            if (storePayment != null) {
                storePayment.setStatus(1);
                liveOrderPaymentMapper.updateLiveOrderPayment(storePayment);
            } else {
                storePayment = new LiveOrderPayment();
                storePayment.setStatus(1);
                storePayment.setPayMode(fsPayConfig.getType());
                storePayment.setBusinessCode(liveOrder.getOrderCode());
                storePayment.setPayCode(payCode);
                storePayment.setPayMoney(liveOrder.getPayMoney());
//                storePayment.setPayMoney(new BigDecimal("0.01"));
                storePayment.setCreateTime(new Date());
                storePayment.setPayTypeCode("weixin");
                storePayment.setBusinessType(5);
                storePayment.setRemark("直播商品订单支付");
                storePayment.setOpenId(user.getMaOpenId());
                storePayment.setUserId(user.getUserId());
                storePayment.setBusinessId(liveOrder.getOrderId().toString());
                liveOrderPaymentMapper.insertLiveOrderPayment(storePayment);
            }
            if (storePayment!=null){
                if(storePayment.getStatus().equals(0)){
                    LiveOrderPayment paymentMap=new LiveOrderPayment();
                    paymentMap.setPaymentId(storePayment.getPaymentId());
                    paymentMap.setStatus(1);
                    paymentMap.setPayTime(new Date());
                    liveOrderPaymentMapper.updateLiveOrderPayment(paymentMap);
                }
            }
            else{
                log.info("支付单号不存在:"+payCode);
                throw new CustomException("当前支付记录未找到!");
            }
            if(liveOrder.getStatus()!=1){
                TransactionAspectSupport.currentTransactionStatus().setRollbackOnly();
                return R.error("当前订单未找到或者订单状态不为待支付!");
            }
            //增加用户购买次数
            userService.incPayCount(Long.valueOf(liveOrder.getUserId()));

            liveOrder.setStatus(2);
            liveOrder.setPayTime(new Date());
            liveUserLotteryRecordMapper.updateOrderStatusByOrderId(liveOrder.getOrderId(), 2);
            baseMapper.updateLiveOrder(liveOrder);
            return R.ok("支付成功");
        }catch (Exception e){
            log.info("抽奖订单支付错误:"+e.getMessage());
            TransactionAspectSupport.currentTransactionStatus().rollbackToSavepoint(savePoint);
            LiveOrderPaymentError err = new LiveOrderPaymentError();
            err.setOrderNo(String.valueOf(orderId));
            err.setStatus(0);
            err.setMsg("抽奖订单支付错误:"+e.getMessage());
            err.setCreateTime(DateUtils.getNowDate());
            liveOrderPaymentErrorMapper.insertLiveOrderPaymentError(err);
            return R.error("支付失败");
        }
    }


    @Override
    @Transactional(rollbackFor = Throwable.class,propagation = Propagation.REQUIRED)
    public R createLiveOrder(LiveOrder liveOrder) {
//        FsUser user=userMapper.selectFsUserByUserId(Long.valueOf(liveOrder.getUserId()));
//        if(user.getStatus()!=1){
//            return R.error("非法用户操作");
//        }
        String orderKey= redisCache.getCacheObject("orderKey:"+liveOrder.getOrderKey());
        if (StringUtils.isEmpty(orderKey)) {
            return R.error("订单已过期");
        }
        if(liveOrder.getLiveId() == null) return R.error("直播ID不能为空");
        if(liveOrder.getProductId() == null) return R.error("购物商品ID不能为空");
        if(liveOrder.getUserName() == null) return R.error("用户名不能为空");
        if(liveOrder.getUserPhone() == null) return R.error("用户手机号不能为空");
        if(liveOrder.getUserAddress() == null) return R.error("用户地址不能为空");
        if(liveOrder.getTotalNum() == null) return R.error("商品数量不能为空");

        Live live = liveMapper.selectLiveByLiveId(liveOrder.getLiveId());
        if(live == null) return R.error("当前直播不存在");
        FsStoreProduct fsStoreProduct = fsStoreProductService.selectFsStoreProductById(liveOrder.getProductId());
        LiveGoods goods = liveGoodsMapper.selectLiveGoodsByProductId(liveOrder.getLiveId(), liveOrder.getProductId());
        if(fsStoreProduct == null) return R.error("店铺已下架商品，购买失败");
        if(fsStoreProduct.getIsShow() == 0 || goods.getStatus() == 0) return R.error("商品已下架，购买失败");
        if(fsStoreProduct.getStock() < Integer.parseInt(liveOrder.getTotalNum()) || goods.getStock() < Integer.parseInt(liveOrder.getTotalNum())) return R.error("抱歉，这款商品已被抢光，暂时无库存～");

        // 更改店铺库存
        fsStoreProduct.setStock(fsStoreProduct.getStock()-Integer.parseInt(liveOrder.getTotalNum()));
        fsStoreProductService.updateFsStoreProduct(fsStoreProduct);
        // 更新直播间库存
        goods.setStock(goods.getStock()-Integer.parseInt(liveOrder.getTotalNum()));
        liveGoodsMapper.updateLiveGoods(goods);

        //判断是否是三种特定产品
        if (fsStoreProduct.getProductId() != null && (fsStoreProduct.getProductId().equals(3168L)
                || fsStoreProduct.getProductId().equals(3184L)
                || fsStoreProduct.getProductId().equals(3185L))) {
            liveOrder.setStoreHouseCode("YDSP001");
        } else {
            liveOrder.setStoreHouseCode("CQDS001");
        }

        LiveUserFirstEntry liveUserFirstEntry = liveUserFirstEntryService.selectEntityByLiveIdUserId(liveOrder.getLiveId(), Long.parseLong(liveOrder.getUserId()));
        liveOrder.setCompanyId(liveUserFirstEntry.getCompanyId());
        liveOrder.setCompanyUserId(liveUserFirstEntry.getCompanyUserId());
        liveOrder.setTuiUserId(liveUserFirstEntry.getCompanyUserId());

        String orderSn = SnowflakeUtils.nextId();
        log.info("订单生成："+orderSn);
        liveOrder.setOrderCode(orderSn);
        BigDecimal payPrice = fsStoreProduct.getPrice().multiply(new BigDecimal(liveOrder.getTotalNum()));
        // 直播不需要服务费 0915 1735 左
//        String config=configService.selectConfigByKey("store.config");
//        StoreConfig storeConfig= JSONUtil.toBean(config,StoreConfig.class);
//        BigDecimal serviceFee=new BigDecimal(0);
//        if(storeConfig.getServiceFee()!=null){
//            if(liveOrder.getCompanyUserId()==null||liveOrder.getCompanyUserId()==0){
//                serviceFee=storeConfig.getServiceFee();
//            }
//        }
//        payPrice = payPrice.add(serviceFee);
        // 生成
        BigDecimal deliveryMoney = handleDeliveryMoney(liveOrder);
        payPrice = payPrice.add(deliveryMoney);
        liveOrder.setDiscountMoney(BigDecimal.ZERO);

        //优惠券处理
        if(liveOrder.getCouponUserId()!=null){
            LiveCouponUser couponUser=liveCouponUserService.selectLiveCouponUserById(liveOrder.getCouponUserId());
            if(couponUser!=null&&couponUser.getStatus()==0){
                if (!couponUser.getUserId().toString().equals(liveOrder.getUserId())){
                    return R.error("非法操作");
                }
                if(couponUser.getUseMinPrice().compareTo(payPrice) < 1){
                    liveOrder.setUserCouponId(couponUser.getId());
                    liveOrder.setDiscountMoney(couponUser.getCouponPrice());
                    //更新优惠券状态
                    couponUser.setStatus(1);
                    couponUser.setUseTime(new Date());
                    liveCouponUserService.updateLiveCouponUser(couponUser);
                }
            }
        }

        liveOrder.setItemJson(JSON.toJSONString(fsStoreProduct));
        liveOrder.setCreateTime(new Date());
        liveOrder.setUpdateTime(new Date());
        liveOrder.setPayDelivery(deliveryMoney);
        liveOrder.setProductId(fsStoreProduct.getProductId());
        liveOrder.setStatus(OrderInfoEnum.STATUS_1.getValue());
        liveOrder.setPayType("1");
        liveOrder.setTotalPrice(payPrice);
        liveOrder.setPayMoney(liveOrder.getTotalPrice().subtract(liveOrder.getDiscountMoney()));
        try {
            if (baseMapper.insertLiveOrder(liveOrder) > 0) {
                LiveOrderItemDTO dto=new LiveOrderItemDTO();
                dto.setImage(fsStoreProduct.getImage());
                dto.setSku(String.valueOf(fsStoreProduct.getStock()));

                FsStoreProductAttrValue fsStoreProductAttrValue = fsStoreProductAttrValueMapper.selectFsStoreProductAttrValueByProductId(fsStoreProduct.getProductId()).stream().filter(attrValue -> StringUtils.isNotEmpty(attrValue.getBarCode())).findFirst().orElse(null);
                if (fsStoreProductAttrValue != null) {
                    dto.setBarCode(fsStoreProductAttrValue.getBarCode());
                    dto.setGroupBarCode(fsStoreProductAttrValue.getGroupBarCode());
                }

                dto.setPrice(fsStoreProduct.getPrice());
                dto.setProductName(fsStoreProduct.getProductName());
                dto.setNum(Long.valueOf(liveOrder.getTotalNum()));

                LiveOrderItem liveOrderItem = new LiveOrderItem();
                liveOrderItem.setOrderCode(liveOrder.getOrderCode());
                liveOrderItem.setOrderId(liveOrder.getOrderId());
                liveOrderItem.setProductId(liveOrder.getProductId());
                liveOrderItem.setNum(Long.valueOf(liveOrder.getTotalNum()));
                liveOrderItem.setJsonInfo(JSON.toJSONString(dto));
                liveOrderItemMapper.insertLiveOrderItem(liveOrderItem);
                redisCache.deleteObject("orderKey:" + liveOrder.getOrderKey());
                return R.ok("下单成功").put("order",liveOrder);
            } else {
                return R.error("订单创建失败");
            }
        } catch (Exception e) {
            // 异常处理
            return R.error("订单创建失败：" + e.getMessage());
        }
    }

    private BigDecimal handleDeliveryMoney(LiveOrder liveOrder) {
        BigDecimal storePostage = BigDecimal.ZERO;
        List<Long> citys = new ArrayList<>();
        citys.add(liveOrder.getCityId());
        citys.add(0l);
        FsStoreProduct fsStoreProduct = fsStoreProductService.selectFsStoreProductById(liveOrder.getProductId());
        String ids = String.valueOf(fsStoreProduct.getTempId());
        List<FsShippingTemplates> shippingTemplatesList = shippingTemplatesService.selectFsShippingTemplatesByIds(ids);
        String cityIds = String.join(",", citys.stream()
                .map(String::valueOf).collect(Collectors.toList()));
        List<FsShippingTemplatesRegion> shippingTemplatesRegionList = shippingTemplatesRegionService.selectFsShippingTemplatesRegionListByTempIdsAndCityIds(ids,cityIds);
        Map<Long, Integer> shippingTemplatesMap = shippingTemplatesList
                .stream()
                .collect(Collectors.toMap(FsShippingTemplates::getId,
                        FsShippingTemplates::getType));
        //提取运费模板有相同值覆盖
        Map<Long, FsShippingTemplatesRegion> shippingTemplatesRegionMap =
                shippingTemplatesRegionList.stream()
                        .collect(Collectors.toMap(FsShippingTemplatesRegion::getTempId,
                                YxShippingTemplatesRegion -> YxShippingTemplatesRegion,
                                (key1, key2) -> key2));
        Long tempId = Long.valueOf(fsStoreProduct.getTempId());
        double num = 0d;
        Integer templateType = shippingTemplatesMap.get(tempId);
        List<FsStoreProductAttrValue> productAttrValues = fsStoreProductAttrValueMapper.selectFsStoreProductAttrValueByProductId(fsStoreProduct.getProductId());
        if(productAttrValues == null || productAttrValues.isEmpty()) {
            return storePostage;
        }
        FsStoreProductAttrValue productAttrValue = productAttrValues.get(0);
        Integer totalNum = Integer.valueOf(liveOrder.getTotalNum());
        // TYPE_1: 按件数计算
        if (ShippingTempEnum.TYPE_1.getValue().equals(templateType)) {
            num = totalNum.doubleValue();
        }
        // TYPE_2: 按重量计算（数量 × 重量）
        else if (ShippingTempEnum.TYPE_2.getValue().equals(templateType)) {
            num = NumberUtil.mul(totalNum, productAttrValue.getWeight()).doubleValue();
        }
        // TYPE_3: 按体积计算（数量 × 体积）
        else if (ShippingTempEnum.TYPE_3.getValue().equals(templateType)) {
            num = NumberUtil.mul(totalNum, productAttrValue.getVolume()).doubleValue();
        }
        FsShippingTemplatesRegion shippingTemplatesRegion = shippingTemplatesRegionMap.get(tempId);
        if (shippingTemplatesRegion == null) {
            log.error("没有找到运费模板");
            return storePostage;
        }
        BigDecimal price = NumberUtil.round(NumberUtil.mul(totalNum, fsStoreProduct.getPrice()), 2);

        TemplateDTO templateDTO = TemplateDTO.builder()
                .number(num)  // 累计数量（件数/重量/体积）
                .price(price)  // 累计金额
                .first(shippingTemplatesRegion.getFirst().doubleValue())  // 首件数量
                .firstPrice(shippingTemplatesRegion.getFirstPrice())  // 首件运费
                .continues(shippingTemplatesRegion.getContinues().doubleValue())  // 续件数量
                .continuePrice(shippingTemplatesRegion.getContinuePrice())  // 续件运费
                .tempId(tempId)  // 模板ID
                .cityId(liveOrder.getCityId())  // 城市ID
                .build();
        //只满足首件
        if (Double.compare(templateDTO.getNumber(), templateDTO.getFirst()) <= 0) {
            storePostage = NumberUtil.round(NumberUtil.add(storePostage,
                    templateDTO.getFirstPrice()), 2);
        } else {
            BigDecimal firstPrice = NumberUtil.add(storePostage, templateDTO.getFirstPrice());

            if (templateDTO.getContinues() <= 0) {
                storePostage = firstPrice;
            } else {
                //续件平均值且向上取整数
                double average = Math.ceil(NumberUtil.div(NumberUtil.sub(templateDTO.getNumber(),
                                templateDTO.getFirst()),
                        templateDTO.getContinues().doubleValue()));
                //最终邮费
                storePostage = NumberUtil.add(firstPrice, NumberUtil.mul(average,
                        templateDTO.getContinuePrice()));
            }

        }

        return storePostage;
    }

    @Override
    public R confirmOrder(LiveOrderConfirmParam param) {
        String uuid = IdUtil.randomUUID();
        redisCache.setCacheObject("orderKey:"+uuid,uuid,200, TimeUnit.MINUTES);
        return R.ok().put("orderKey",uuid);
    }

    @Override
    public List<LiveOrder> selectNotPushedLiveOrder() {
        return baseMapper.selectNotPushedLiveOrder();
    }


    @Override
    @Transactional(rollbackFor = Exception.class,propagation = Propagation.REQUIRED)
    public R cancelOrder(LiveOrder order) {
        if(order.getStatus() == 1){
            LiveOrder liveOrder = baseMapper.selectLiveOrderByOrderId(String.valueOf(order.getOrderId()));
            if(liveOrder == null) return R.error("订单不存在");
            liveUserLotteryRecordMapper.updateOrderStatusByOrderId(order.getOrderId(), -3);
            baseMapper.cancelOrder(order.getOrderId());
            liveOrderLogsService.create(order.getOrderId(), OrderLogEnum.CANCEL_ORDER.getValue(),
                    OrderLogEnum.CANCEL_ORDER.getDesc());
            // 恢复库存
            FsStoreProduct fsStoreProduct = fsStoreProductService.selectFsStoreProductById(liveOrder.getProductId());
            LiveGoods goods = liveGoodsMapper.selectLiveGoodsByProductId(liveOrder.getLiveId(), liveOrder.getProductId());
            fsStoreProduct.setStock(fsStoreProduct.getStock()+Integer.parseInt(liveOrder.getTotalNum()));
            fsStoreProductService.updateFsStoreProduct(fsStoreProduct);
            goods.setStock(goods.getStock()+Long.parseLong(liveOrder.getTotalNum()));
            liveGoodsMapper.updateLiveGoods(goods);
            this.refundCoupon(order);

            return R.ok("操作成功");
        }else {
            return R.error("非法操作");
        }
    }

    private void refundCoupon(LiveOrder order) {
        if(order.getCouponUserId()!=null){
            LiveCouponUser couponUser=liveCouponUserService.selectLiveCouponUserById(order.getCouponUserId());
            if(couponUser!=null){
                couponUser.setStatus(0);
                couponUser.setUseTime(null);
                liveCouponUserService.updateLiveCouponUser(couponUser);
            }
        }
    }


    /**
     * 订单操作记录
     * */
    @Transactional
    public void handleOrderStatus(LiveOrder liveOrder) {

    }
}
