package cn.pluss.platform.refundOrder.impl;


import cn.pluss.platform.api.ResultCode;
import cn.pluss.platform.entity.MerchantBaseInfo;
import cn.pluss.platform.entity.MerchantChannelStatus;
import cn.pluss.platform.entity.MerchantOrder;
import cn.pluss.platform.entity.MerchantRefundOrder;
import cn.pluss.platform.exception.MsgException;
import cn.pluss.platform.mapper.MerchantOrderMapper;
import cn.pluss.platform.mapper.MerchantRefundOrderMapper;
import cn.pluss.platform.merchant.MerchantBaseInfoService;
import cn.pluss.platform.merchantChannelStatus.MerchantChannelStatusService;
import cn.pluss.platform.notify.NotifyMessageService;
import cn.pluss.platform.pay.PayService;
import cn.pluss.platform.realFans.RealFansService;
import cn.pluss.platform.refundOrder.MerchantRefundOrderService;
import cn.pluss.platform.ryx.pay.RyxPayService;
import cn.pluss.platform.sxf.pay.SxfPayService;
import cn.pluss.platform.util.MD5Util;
import cn.pluss.platform.util.SignUtils;
import cn.pluss.platform.util.StringUtil;
import com.alibaba.fastjson.JSONObject;
import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;
import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
import lombok.Setter;
import lombok.extern.slf4j.Slf4j;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.beans.factory.annotation.Qualifier;
import org.springframework.context.annotation.Lazy;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;

import javax.annotation.Resource;
import java.math.BigDecimal;
import java.text.SimpleDateFormat;
import java.util.Date;
import java.util.List;
import java.util.Map;


@Service
@Transactional
@Slf4j
public class MerchantRefundOrderServiceImpl extends ServiceImpl<MerchantRefundOrderMapper, MerchantRefundOrder> implements MerchantRefundOrderService {


    @Autowired
    private MerchantRefundOrderMapper merchantRefundOrderMapper;

    @Setter(onMethod_ = {@Autowired,@Lazy})
    private MerchantChannelStatusService merchantChannelStatusService;

    @Setter(onMethod_ = {@Autowired,@Lazy})
    private MerchantBaseInfoService merchantBaseInfoService;

    @Setter(onMethod_ = {@Autowired})
    private SxfPayService sxfPayService;
    @Setter(onMethod_ = {@Autowired})
    private RyxPayService ryxPayService;

    @Setter(onMethod_ = {@Autowired, @Qualifier("ysPayOldService")})
    private PayService ysPayOldService;

    @Setter(onMethod_ = {@Autowired,@Lazy})
    private RealFansService realFansService;

    @Setter(onMethod_ = {@Lazy, @Autowired})
    private NotifyMessageService notifyMessageService;

    @Resource
    private MerchantOrderMapper merchantOrderMapper;




    @Override
    public List<MerchantRefundOrder> queryRefundOrderJoinPage(Map<String, Object> map) {
        return merchantRefundOrderMapper.queryRefundOrderJoinPage(map);
    }

    @Override
    public Integer queryRefundOrderJoinPageCount(Map<String, Object> map) {
        return merchantRefundOrderMapper.queryRefundOrderJoinPageCount(map);
    }

    @Override
    public Page<MerchantRefundOrder> pageDate(Page<MerchantRefundOrder> page, MerchantRefundOrder refundOrder) {
        return merchantRefundOrderMapper.pageDate(page,refundOrder);
    }
    /**
     * @description:统计首页退款数据
     * @date: 2021/10/19 15:11
     * @return java.util.Map<java.lang.String,java.lang.Object>
     */
    @Override
    public Map<String, Object> getPlatformRefundData() {
        return merchantRefundOrderMapper.getPlatformRefundData();
    }

    /**
     * @description:订单退款
     * @date: 2021/11/22 14:09
     * @param params:
     * @param order:
     */
    @Override
    public MerchantRefundOrder apiRefundOrder(JSONObject params, MerchantOrder order) {
        MerchantChannelStatus channel = null;
        if("2".equals(order.getAisleSwitch())){
            channel = merchantChannelStatusService.getByMerchantCode(order.getMerchantCode(), 1);
        }else{
            channel = merchantChannelStatusService.getByMerchantCode(order.getMerchantCode(), Integer.valueOf(order.getAisleSwitch()));
        }
        MsgException.checkNull(channel,"通道信息异常");

        Map<String,Object> result = null;
        if (channel.getChannel() == 1) {
            result = sxfPayService.refundPay(order, channel.getMerchantId());
        } else if (channel.getChannel() == 2) {
            MsgException.throwException("通道已关闭！");
        } else if (channel.getChannel() == 3) {
            result = ryxPayService.refundPay(order, channel.getMerchantId());
        } else if (channel.getChannel() == 4) {
            result = ysPayOldService.refundPay(order, channel.getMerchantId());
        }else {
            MsgException.throwException("未知通道！");
        }
        if (ResultCode.SUCCESS.code() != (Integer) result.get("code")) {
            throw new MsgException((String) result.get("msg"));
        }
        MerchantRefundOrder refundOrder = new MerchantRefundOrder();
        if(StringUtil.isNotEmpty(order.getMarketAmt()) && order.getMarketAmt().doubleValue() > 0
                && ("1".equals(order.getRefundType()) || StringUtil.isEmpty(order.getRefundType()))){
            MerchantOrder update = new MerchantOrder();
            update.setId(order.getId());
            update.setMarketAmt(new BigDecimal("0.00"));
            merchantOrderMapper.updateById(update);
        }else if(StringUtil.isNotEmpty(order.getMarketAmt()) && order.getMarketAmt().doubleValue() > 0 && "2".equals(order.getRefundType())){
            MerchantOrder update = new MerchantOrder();
            update.setId(order.getId());
            BigDecimal uesAmt = BigDecimal.valueOf(order.getConsumeFee()).subtract(order.getRefundAmt());
            BigDecimal market = uesAmt.multiply(order.getRate().divide(BigDecimal.valueOf(10000))).setScale(2,BigDecimal.ROUND_HALF_DOWN);
            update.setMarketAmt(market);
            merchantOrderMapper.updateById(update);
        }
        refundOrder.convert(order, result,channel.getMerchantId(),order.getRefundAmt(),params);
        order.setId(null);
        order.setUpdateTime(new Date());
        order.setStatus("2");
        order.setMarketAmt(BigDecimal.ZERO);
        realFansService.removeProfit(order,order.getRefundAmt(),order.getUseRefundAmt());
        order.setOrderNumber(order.getOrderNumber() + "_" + StringUtil.genRandomNum(5));
        merchantOrderMapper.insert(order);
        merchantRefundOrderMapper.insert(refundOrder);
        return refundOrder;
    }


    @Override
    public MerchantRefundOrder apiRefundQuery(JSONObject params) {
        String mercRefundNo = params.getString("mercRefundNo");
        QueryWrapper<MerchantRefundOrder> queryWrapper = new QueryWrapper<MerchantRefundOrder>().eq("mercRefundNo",mercRefundNo);
        MerchantRefundOrder refundOrder = baseMapper.selectOne(queryWrapper);
        MsgException.checkNull(refundOrder,"退款单号有误！");
        if(!"1".equals(refundOrder.getStatus())){
            MerchantChannelStatus channel = null;
            if("2".equals(refundOrder.getAisleSwitch())){
                channel = merchantChannelStatusService.getByMerchantCode(refundOrder.getMerchantCode(), 1);
            }else{
                channel = merchantChannelStatusService.getByMerchantCode(refundOrder.getMerchantCode(), Integer.valueOf(refundOrder.getAisleSwitch()));
            }
            MsgException.checkNull(channel,"通道信息异常");
            JSONObject result = null;
            if (channel.getChannel() == 1) {
                result = sxfPayService.refundQuery(refundOrder);
            } else if (channel.getChannel() == 2) {
                MsgException.throwException("通道已关闭！");
            } else if (channel.getChannel() == 3) {
                result = ryxPayService.refundQuery(refundOrder);
            } else if (channel.getChannel() == 4) {
                result = ysPayOldService.refundQuery(refundOrder);
            }else {
                MsgException.throwException("未知通道！");
            }
            if(result != null && StringUtil.isNotEmpty(result.getString("status"))){
                refundOrder.setStatus(result.getString("status"));
            }
            return refundOrder;
        }else{
            return refundOrder;
        }
    }

    @Override
    public void updateOrderAndSendNotify(MerchantRefundOrder refundOrder) {
        this.updateById(refundOrder);
        if(StringUtil.isNotEmpty(refundOrder.getNotifyUrl())){
            sendLowerRefundNotifyCallback(refundOrder);
        }
    }

    private void sendLowerRefundNotifyCallback(MerchantRefundOrder refundOrder) {
        JSONObject notifyMap = new JSONObject();
        notifyMap.put("msgType","02");
        notifyMap.put("mercRefundNo",refundOrder.getMercRefundNo());
        notifyMap.put("refundNo",refundOrder.getRefundNo());
        notifyMap.put("orderNumber",refundOrder.getOrderNumber());
        notifyMap.put("oPayAmt",refundOrder.getPayAmt());
        notifyMap.put("refundAmt",refundOrder.getRefundAmt());
        notifyMap.put("refundTime",new SimpleDateFormat("yyyy-MM-dd HH:mm:ss").format(refundOrder.getCreateTime()));
        notifyMap.put("status",refundOrder.getStatus());
        String key = "4c8d277b0f274604af68e590cc0b3e6b";
        MerchantBaseInfo merchant = merchantBaseInfoService.getMerchantBaseInfoByMerchantCode(refundOrder.getMerchantCode());
        if(merchant != null && StringUtil.isNotEmpty(merchant.getMd5Key())){
            key = merchant.getMd5Key();
        }
        String signStr = SignUtils.getSignContent(notifyMap) + "&key="+key;
        String nSign = MD5Util.MD5Encode(signStr, "UTF-8");
        notifyMap.put("sign",nSign);
        try {
            MerchantOrder order = new MerchantOrder().setMercNotifyUrl(refundOrder.getNotifyUrl());
            notifyMessageService.sendNotifyMessage(order,notifyMap);
        } catch (Exception e) {
            log.info("====================>进入下游推送异步通知异常，异常信息:{}<====================",e);
        }
    }
}
