admin
2019-11-03 788deca1b4a24f8a24e49c24f7d89975a1d74bbe
商城订单退款处理
1个文件已删除
6个文件已修改
2个文件已添加
279 ■■■■ 已修改文件
fanli/src/main/java/com/yeshi/fanli/dto/mq/order/OrderTopicTagEnum.java 4 ●●● 补丁 | 查看 | 原始文档 | blame | 历史
fanli/src/main/java/com/yeshi/fanli/entity/shop/BanLiShopOrder.java 5 ●●●● 补丁 | 查看 | 原始文档 | blame | 历史
fanli/src/main/java/com/yeshi/fanli/service/impl/shop/BanLiShopOrderPayServiceImpl.java 59 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
fanli/src/main/java/com/yeshi/fanli/service/impl/shop/BanLiShopOrderServiceImpl.java 11 ●●●● 补丁 | 查看 | 原始文档 | blame | 历史
fanli/src/main/java/com/yeshi/fanli/service/inter/shop/BanLiShopOrderPayService.java 8 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
fanli/src/main/java/com/yeshi/fanli/util/shop/BanLiShopOrderUtil.java 51 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
fanli/src/main/java/com/yeshi/fanli/util/shop/BanLiShopUtil.java 24 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
utils/src/main/java/org/yeshi/utils/exception/WXOrderException.java 28 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
utils/src/main/java/org/yeshi/utils/wx/WXPayUtil.java 89 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
fanli/src/main/java/com/yeshi/fanli/dto/mq/order/OrderTopicTagEnum.java
@@ -1,5 +1,6 @@
package com.yeshi.fanli.dto.mq.order;
import com.yeshi.fanli.dto.mq.order.body.BanLiShopOrderMQMsg;
import com.yeshi.fanli.util.annotation.UserActive;
public enum OrderTopicTagEnum {
@@ -7,7 +8,8 @@
    orderUpdate(UserActive.class), // 订单修改
    orderFanLiActual(UserActive.class), // 订单实时到账
    orderFanLiDelay(UserActive.class), // 订单到账延时消息
    banLiShopOrderDelay(UserActive.class);// 板栗商城下单
    banLiShopOrderDelay(BanLiShopOrderMQMsg.class),// 板栗商城下单
    banLiShopOrderRefund(BanLiShopOrderMQMsg.class);//板栗商城订单退款
    private final Class<?> clazz;
fanli/src/main/java/com/yeshi/fanli/entity/shop/BanLiShopOrder.java
@@ -17,12 +17,15 @@
    public final static int PAY_STATE_NOPAY = 0;// 未支付
    public final static int PAY_STATE_PAID = 1;// 已支付
    public final static int PAY_STATE_REFUND = 2;// 以退款
    public final static int STATE_INVALID = -1;// 失效
    public final static int STATE_NO_PAY = 0;// 未支付
    public final static int STATE_PART_PAY = 1;// 部分支付
    public final static int STATE_PAID = 5;// 已支付,待审核
    public final static int STATE_REJECT = 10;// 审核拒绝
    public final static int STATE_REJECT = 10;// 审核拒绝,退款中
    public final static int STATE_REJECT_REFUND_SUCCESS = 11;// 审核拒绝-退款成功
    public final static int STATE_REJECT_REFUND_FAIL = 12;// 审核拒绝-退款失败
    public final static int STATE_SUCCESS = 20;// 交易成功
    @Column(name = "so_id")
fanli/src/main/java/com/yeshi/fanli/service/impl/shop/BanLiShopOrderPayServiceImpl.java
@@ -7,6 +7,9 @@
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;
import org.yeshi.utils.entity.wx.WXAPPInfo;
import org.yeshi.utils.exception.WXOrderException;
import org.yeshi.utils.wx.WXPayUtil;
import com.yeshi.fanli.entity.redpack.RedPackDetail;
import com.yeshi.fanli.entity.shop.BanLiShopGoods;
@@ -23,6 +26,7 @@
import com.yeshi.fanli.service.inter.shop.BanLiShopGoodsSetService;
import com.yeshi.fanli.service.inter.shop.BanLiShopOrderPayService;
import com.yeshi.fanli.service.inter.shop.BanLiShopOrderService;
import com.yeshi.fanli.util.Constant;
import com.yeshi.fanli.util.factory.RedPackDetailFactory;
@Service
@@ -101,7 +105,7 @@
        if (order.getMoneyPayment() == null)
            throw new BanLiShopOrderException(2, "不需要采用现金支付");
        if (order.getMoneyPaymentState() != null && order.getMoneyPaymentState() == BanLiShopOrder.PAY_STATE_PAID) {
        if (order.getMoneyPaymentState() != null && order.getMoneyPaymentState() != BanLiShopOrder.PAY_STATE_NOPAY) {
            throw new BanLiShopOrderException(3, "重复支付");
        }
@@ -145,4 +149,57 @@
        }
    }
    @Transactional
    @Override
    public void refund(Long orderId) throws BanLiShopOrderException {
        // 订单退款
        // 查询订单是否已经被拒绝
        BanLiShopOrder order = banLiShopOrderService.selectByPrimaryKeyForUpdate(orderId);
        if (order == null)
            throw new BanLiShopOrderException(1, "订单不存在");
        if (order.getState() != BanLiShopOrder.STATE_REJECT)
            throw new BanLiShopOrderException(2, "订单未被拒绝/订单已退款");
        BanLiShopOrder update = new BanLiShopOrder();
        update.setId(order.getId());
        if (order.getHongBaoPaymentState() != null && order.getHongBaoPaymentState() == BanLiShopOrder.PAY_STATE_PAID) {
            BanLiShopGoods goods = banLiShopGoodsService.selectByPrimaryKey(order.getGoods().getId());
            BanLiShopGoodsClass goodsClass = banLiShopGoodsClassService
                    .selectByPrimaryKey(goods.getGoodsClass().getId());
            BanLiShopGoodsSets set = banLiShopGoodsSetService.selectByPrimaryKey(order.getGoodsSet().getId());
            // 红包退款
            RedPackDetail detail = null;
            try {
                detail = RedPackDetailFactory.createShopOrderDrawBack(orderId, order.getUid(), goodsClass.getName(),
                        set.getName(), order.getHongBaoPayment());
            } catch (RedPackDetailException e) {
                e.printStackTrace();
            }
            if (detail == null)
                throw new BanLiShopOrderException(4, "红包详情失败");
            try {
                redPackBalanceService.addRedPack(order.getUid(), order.getHongBaoPayment(), detail);
            } catch (RedPackBalanceException e) {
                throw new BanLiShopOrderException(5, "红包退款失败");
            }
            update.setHongBaoPaymentState(BanLiShopOrder.PAY_STATE_REFUND);
        }
        // TODO 微信支付退款
        if (order.getMoneyPaymentState() != null && order.getMoneyPaymentState() == BanLiShopOrder.PAY_STATE_PAID) {
            try {
                boolean success = WXPayUtil.refund(order.getOrderNo(), order.getMoneyPayment(), order.getMoneyPayment(),
                        null, new WXAPPInfo(), null, null);
                if (success) {
                    update.setMoneyPaymentState(BanLiShopOrder.PAY_STATE_REFUND);
                } else
                    throw new BanLiShopOrderException(6, "微信支付退款失败");
            } catch (WXOrderException e) {
                throw new BanLiShopOrderException(6, "微信支付退款失败");
            }
        }
    }
}
fanli/src/main/java/com/yeshi/fanli/service/impl/shop/BanLiShopOrderServiceImpl.java
@@ -35,7 +35,7 @@
import com.yeshi.fanli.util.Constant;
import com.yeshi.fanli.util.factory.RedPackDetailFactory;
import com.yeshi.fanli.util.rocketmq.MQTopicName;
import com.yeshi.fanli.util.shop.BanLiShopUtil;
import com.yeshi.fanli.util.shop.BanLiShopOrderUtil;
@Service
public class BanLiShopOrderServiceImpl implements BanLiShopOrderService {
@@ -106,7 +106,7 @@
        banLiShopOrderMapper.insertSelective(order);
        // 添加订单号
        String orderNo = BanLiShopUtil.createOrderNo(order.getId());
        String orderNo = BanLiShopOrderUtil.createOrderNo(order.getId());
        // 更新订单号
        BanLiShopOrder update = new BanLiShopOrder();
        update.setId(order.getId());
@@ -284,6 +284,7 @@
        }
    }
    @Transactional
    @Override
    public void rejectOrder(Long id, String msg) throws BanLiShopOrderException {
        // 判断订单是否处于付款状态
@@ -295,7 +296,11 @@
            throw new BanLiShopOrderException(1, "订单未处于待审核状态");
        // TODO 订单退款
        BanLiShopOrder update = new BanLiShopOrder();
        update.setState(BanLiShopOrder.STATE_REJECT);
        update.setStateDesc(msg);
        update.setUpdateTime(new Date());
        banLiShopOrderMapper.updateByPrimaryKeySelective(update);
    }
}
fanli/src/main/java/com/yeshi/fanli/service/inter/shop/BanLiShopOrderPayService.java
@@ -29,4 +29,12 @@
     * @throws BanLiShopOrderException
     */
    public void payOrderByMoney(Long orderId, BigDecimal money) throws BanLiShopOrderException;
    /**
     * 订单退款
     *
     * @param orderId
     * @throws BanLiShopOrderException
     */
    public void refund(Long orderId) throws BanLiShopOrderException;
}
fanli/src/main/java/com/yeshi/fanli/util/shop/BanLiShopOrderUtil.java
New file
@@ -0,0 +1,51 @@
package com.yeshi.fanli.util.shop;
import com.yeshi.fanli.util.TimeUtil;
public class BanLiShopOrderUtil {
    /**
     * 制造订单号
     *
     * @param orderId
     * @return
     */
    public static String createOrderNo(Long orderId) {
        String orderNo = TimeUtil.getGernalTime(System.currentTimeMillis(), "yyyyMMdd");
        String orderIdStr = orderId + "";
        int length = 8 - orderIdStr.length();
        for (int i = 0; i < length; i++) {
            orderIdStr = "0" + orderIdStr;
        }
        orderNo += orderIdStr;
        return orderNo;
    }
    /**
     * 根据商城订单号获取微信支付的商户订单号
     *
     * @param orderNo
     * @return
     */
    public static String getWXPayOrderNo(String orderNo) {
        return "banlishop-" + orderNo;
    }
    /**
     * 根据微信支付商户订单号获取商城订单
     *
     * @param wxPayOrderNo
     * @return
     */
    public static String getOrderNoFromWXPayOrderNo(String wxPayOrderNo) {
        if (wxPayOrderNo == null)
            return null;
        wxPayOrderNo = wxPayOrderNo.trim();
        if (wxPayOrderNo.startsWith("banlishop-"))
            return wxPayOrderNo.replace("banlishop-", "").trim();
        else
            return null;
    }
}
fanli/src/main/java/com/yeshi/fanli/util/shop/BanLiShopUtil.java
File was deleted
utils/src/main/java/org/yeshi/utils/exception/WXOrderException.java
New file
@@ -0,0 +1,28 @@
package org.yeshi.utils.exception;
public class WXOrderException extends Exception {
    private static final long serialVersionUID = 1L;
    private int code;
    private String msg;
    public int getCode() {
        return code;
    }
    public String getMsg() {
        return msg;
    }
    public WXOrderException(int code, String msg) {
        this.code = code;
        this.msg = msg;
    }
    public WXOrderException() {
    }
    @Override
    public String getMessage() {
        return this.msg;
    }
}
utils/src/main/java/org/yeshi/utils/wx/WXPayUtil.java
@@ -10,6 +10,7 @@
import org.yeshi.utils.entity.wx.RedPackParams;
import org.yeshi.utils.entity.wx.WXAPPInfo;
import org.yeshi.utils.entity.wx.WXPlaceOrderParams;
import org.yeshi.utils.exception.WXOrderException;
import org.yeshi.utils.exception.WXPlaceOrderParamsException;
/**
@@ -20,6 +21,21 @@
 */
public class WXPayUtil {
    /**
     * 付款到零钱
     *
     * @param appId
     * @param openId
     * @param mchId
     * @param key
     * @param pwd
     * @param cert
     * @param orderNo
     * @param money
     * @param desc
     * @param ip
     * @return
     */
    public static String payToOpenId(String appId, String openId, String mchId, String key, String pwd,
            InputStream cert, String orderNo, BigDecimal money, String desc, String ip) {
        Map<String, String> map = new HashMap<>();
@@ -164,8 +180,8 @@
        if (StringUtil.isNullOrEmpty(params.getTradeType()))
            throw new WXPlaceOrderParamsException(8, "请传入tradeType");
//        if (StringUtil.isNullOrEmpty(params.getOpenId()))
//            throw new WXPlaceOrderParamsException(9, "请传入openId");
        // if (StringUtil.isNullOrEmpty(params.getOpenId()))
        // throw new WXPlaceOrderParamsException(9, "请传入openId");
        Map<String, String> map = new HashMap<String, String>();
        map.put("appid", params.getInfo().getAppId());
@@ -189,4 +205,73 @@
        return resultMap;
    }
    /**
     * 订单退款
     *
     * @param orderNo-订单号
     * @param orderMoney-订单总资金
     * @param refundMoney-退款金额
     * @param reason-退款原因
     * @param appInfo
     * @param pwd-证书密码
     * @param cert-证书
     */
    public static boolean refund(String orderNo, BigDecimal orderMoney, BigDecimal refundMoney, String reason,
            WXAPPInfo appInfo, String pwd, InputStream cert) throws WXOrderException {
        Map<String, String> map = new HashMap<String, String>();
        map.put("appid", appInfo.getAppId());
        map.put("mch_id", appInfo.getMchId());
        map.put("nonce_str", StringUtil.getRandomCode(32));
        map.put("out_trade_no", orderNo);
        map.put("out_refund_no", orderNo);// 商户退款单号
        map.put("total_fee", orderMoney.multiply(new BigDecimal(100)).intValue() + "");// 订单金额
        map.put("refund_fee", orderMoney.multiply(new BigDecimal(100)).intValue() + "");// 退款金额
        if (!StringUtil.isNullOrEmpty(reason))
            map.put("refund_desc", reason);
        map.put("sign", WXUtil.getSignMD5(map, appInfo.getMchKey()));
        try {
            String result = HttpUtil.httpsPost("https://api.mch.weixin.qq.com/secapi/pay/refund",
                    WXUtil.loadWXMessage(map), pwd, cert);
            System.out.println("订单退款结果:" + result);
            Map<String, String> resultMap = WXUtil.parseXML(result);
            if ("SUCCESS".equalsIgnoreCase(resultMap.get("return_code"))
                    && "SUCCESS".equalsIgnoreCase(resultMap.get("result_code")))
                return true;
            throw new WXOrderException(100, "微信支付接口出错:" + result);
        } catch (Exception e) {
            e.printStackTrace();
        }
        return false;
    }
    /**
     * 查询订单号是否支付成功
     *
     * @param orderNo
     * @param app
     * @return
     * @throws WXOrderException
     */
    public static boolean isPaySuccess(String orderNo, WXAPPInfo app) throws WXOrderException {
        Map<String, String> map = new HashMap<String, String>();
        map.put("appid", app.getAppId());
        map.put("mch_id", app.getMchId());
        map.put("nonce_str", StringUtil.getRandomCode(32));
        map.put("out_trade_no", orderNo);
        map.put("sign", WXUtil.getSignMD5(map, app.getMchKey()));
        String result = HttpUtil.post("https://api.mch.weixin.qq.com/pay/orderquery", WXUtil.loadWXMessage(map));
        System.out.println("订单查询结果:" + result);
        Map<String, String> resultMap = WXUtil.parseXML(result);
        if ("SUCCESS".equalsIgnoreCase(resultMap.get("return_code"))
                && "SUCCESS".equalsIgnoreCase(resultMap.get("result_code"))) {
            if ("SUCCESS".equalsIgnoreCase(resultMap.get("trade_state")))// 支付成功
                return true;
            else
                return false;
        } else {
            throw new WXOrderException(100, "微信支付接口出错:" + result);
        }
    }
}