mall + pay:
1. 增加支付宝退款查询接口
This commit is contained in:
parent
ac5646b84d
commit
5b066ea693
@ -67,4 +67,13 @@ public interface PayClient {
|
||||
*/
|
||||
PayRefundRespDTO parseRefundNotify(Map<String, String> params, String body);
|
||||
|
||||
/**
|
||||
* 获得退款订单信息
|
||||
*
|
||||
* @param outTradeNo 外部订单号
|
||||
* @param outRefundNo 外部退款号
|
||||
* @return 退款订单信息
|
||||
*/
|
||||
PayRefundRespDTO getRefund(String outTradeNo, String outRefundNo);
|
||||
|
||||
}
|
||||
|
@ -94,7 +94,7 @@ public abstract class AbstractPayClient<Config extends PayClientConfig> implemen
|
||||
throws Throwable;
|
||||
|
||||
@Override
|
||||
public PayOrderRespDTO parseOrderNotify(Map<String, String> params, String body) {
|
||||
public final PayOrderRespDTO parseOrderNotify(Map<String, String> params, String body) {
|
||||
try {
|
||||
return doParseOrderNotify(params, body);
|
||||
} catch (Throwable ex) {
|
||||
@ -108,7 +108,7 @@ public abstract class AbstractPayClient<Config extends PayClientConfig> implemen
|
||||
throws Throwable;
|
||||
|
||||
@Override
|
||||
public PayOrderRespDTO getOrder(String outTradeNo) {
|
||||
public final PayOrderRespDTO getOrder(String outTradeNo) {
|
||||
try {
|
||||
return doGetOrder(outTradeNo);
|
||||
} catch (Throwable ex) {
|
||||
@ -124,7 +124,7 @@ public abstract class AbstractPayClient<Config extends PayClientConfig> implemen
|
||||
// ============ 退款相关 ==========
|
||||
|
||||
@Override
|
||||
public PayRefundRespDTO unifiedRefund(PayRefundUnifiedReqDTO reqDTO) {
|
||||
public final PayRefundRespDTO unifiedRefund(PayRefundUnifiedReqDTO reqDTO) {
|
||||
ValidationUtils.validate(reqDTO);
|
||||
// 执行统一退款
|
||||
PayRefundRespDTO resp;
|
||||
@ -145,7 +145,7 @@ public abstract class AbstractPayClient<Config extends PayClientConfig> implemen
|
||||
protected abstract PayRefundRespDTO doUnifiedRefund(PayRefundUnifiedReqDTO reqDTO) throws Throwable;
|
||||
|
||||
@Override
|
||||
public PayRefundRespDTO parseRefundNotify(Map<String, String> params, String body) {
|
||||
public final PayRefundRespDTO parseRefundNotify(Map<String, String> params, String body) {
|
||||
try {
|
||||
return doParseRefundNotify(params, body);
|
||||
} catch (Throwable ex) {
|
||||
@ -158,6 +158,20 @@ public abstract class AbstractPayClient<Config extends PayClientConfig> implemen
|
||||
protected abstract PayRefundRespDTO doParseRefundNotify(Map<String, String> params, String body)
|
||||
throws Throwable;
|
||||
|
||||
@Override
|
||||
public final PayRefundRespDTO getRefund(String outTradeNo, String outRefundNo) {
|
||||
try {
|
||||
return doGetRefund(outTradeNo, outRefundNo);
|
||||
} catch (Throwable ex) {
|
||||
log.error("[getRefund][客户端({}) outTradeNo({}) outRefundNo({}) 查询退款单异常]",
|
||||
getId(), outTradeNo, outRefundNo, ex);
|
||||
throw buildPayException(ex);
|
||||
}
|
||||
}
|
||||
|
||||
protected abstract PayRefundRespDTO doGetRefund(String outTradeNo, String outRefundNo)
|
||||
throws Throwable;
|
||||
|
||||
// ========== 各种工具方法 ==========
|
||||
|
||||
private PayException buildPayException(Throwable ex) {
|
||||
|
@ -17,11 +17,14 @@ import com.alipay.api.AlipayApiException;
|
||||
import com.alipay.api.AlipayConfig;
|
||||
import com.alipay.api.AlipayResponse;
|
||||
import com.alipay.api.DefaultAlipayClient;
|
||||
import com.alipay.api.domain.AlipayTradeFastpayRefundQueryModel;
|
||||
import com.alipay.api.domain.AlipayTradeQueryModel;
|
||||
import com.alipay.api.domain.AlipayTradeRefundModel;
|
||||
import com.alipay.api.internal.util.AlipaySignature;
|
||||
import com.alipay.api.request.AlipayTradeFastpayRefundQueryRequest;
|
||||
import com.alipay.api.request.AlipayTradeQueryRequest;
|
||||
import com.alipay.api.request.AlipayTradeRefundRequest;
|
||||
import com.alipay.api.response.AlipayTradeFastpayRefundQueryResponse;
|
||||
import com.alipay.api.response.AlipayTradeQueryResponse;
|
||||
import com.alipay.api.response.AlipayTradeRefundResponse;
|
||||
import lombok.SneakyThrows;
|
||||
@ -29,6 +32,7 @@ import lombok.extern.slf4j.Slf4j;
|
||||
|
||||
import java.nio.charset.StandardCharsets;
|
||||
import java.time.LocalDateTime;
|
||||
import java.util.Collections;
|
||||
import java.util.Map;
|
||||
import java.util.Objects;
|
||||
import java.util.function.Supplier;
|
||||
@ -102,7 +106,7 @@ public abstract class AbstractAlipayPayClient extends AbstractPayClient<AlipayPa
|
||||
|
||||
// 2.1 执行请求
|
||||
AlipayTradeQueryResponse response = client.execute(request);
|
||||
if (!response.isSuccess()) {
|
||||
if (!response.isSuccess()) { // 不成功,例如说订单不存在
|
||||
return PayOrderRespDTO.closedOf(response.getSubCode(), response.getSubMsg(),
|
||||
outTradeNo, response);
|
||||
}
|
||||
@ -142,16 +146,15 @@ public abstract class AbstractAlipayPayClient extends AbstractPayClient<AlipayPa
|
||||
request.setBizModel(model);
|
||||
|
||||
// 2.1 执行请求
|
||||
AlipayTradeRefundResponse response = client.execute(request);
|
||||
AlipayTradeRefundResponse response = client.execute(request);
|
||||
if (!response.isSuccess()) {
|
||||
return PayRefundRespDTO.failureOf(reqDTO.getOutRefundNo(), response);
|
||||
}
|
||||
// 2.2 创建返回结果
|
||||
// 支付宝只要退款调用返回 success,就认为退款成功,不需要回调。具体可见 parseNotify 方法的说明。
|
||||
// 另外,支付宝没有退款单号,所以不用设置
|
||||
if (response.isSuccess()) {
|
||||
return PayRefundRespDTO.successOf(null, LocalDateTimeUtil.of(response.getGmtRefundPay()),
|
||||
reqDTO.getOutRefundNo(), response);
|
||||
} else {
|
||||
return PayRefundRespDTO.failureOf(reqDTO.getOutRefundNo(), response);
|
||||
}
|
||||
return PayRefundRespDTO.successOf(null, LocalDateTimeUtil.of(response.getGmtRefundPay()),
|
||||
reqDTO.getOutRefundNo(), response);
|
||||
}
|
||||
|
||||
@Override
|
||||
@ -164,6 +167,35 @@ public abstract class AbstractAlipayPayClient extends AbstractPayClient<AlipayPa
|
||||
throw new UnsupportedOperationException("支付宝无退款回调");
|
||||
}
|
||||
|
||||
@Override
|
||||
protected PayRefundRespDTO doGetRefund(String outTradeNo, String outRefundNo) throws AlipayApiException {
|
||||
// 1.1 构建 AlipayTradeFastpayRefundQueryModel 请求
|
||||
AlipayTradeFastpayRefundQueryModel model = new AlipayTradeFastpayRefundQueryModel();
|
||||
model.setOutTradeNo(outTradeNo);
|
||||
model.setOutRequestNo(outRefundNo);
|
||||
model.setQueryOptions(Collections.singletonList("gmt_refund_pay"));
|
||||
// 1.2 构建 AlipayTradeFastpayRefundQueryRequest 请求
|
||||
AlipayTradeFastpayRefundQueryRequest request = new AlipayTradeFastpayRefundQueryRequest();
|
||||
request.setBizModel(model);
|
||||
|
||||
// 2.1 执行请求
|
||||
AlipayTradeFastpayRefundQueryResponse response = client.execute(request);
|
||||
if (!response.isSuccess()) {
|
||||
// 明确不存在的情况,应该就是失败,可进行关闭
|
||||
if (ObjectUtils.equalsAny(response.getSubCode(), "TRADE_NOT_EXIST", "ACQ.TRADE_NOT_EXIST")) {
|
||||
return PayRefundRespDTO.failureOf(outRefundNo, response);
|
||||
}
|
||||
// 可能存在“ACQ.SYSTEM_ERROR”系统错误等情况,所以返回 WAIT 继续等待
|
||||
return PayRefundRespDTO.waitingOf(null, outRefundNo, response);
|
||||
}
|
||||
// 2.2 创建返回结果
|
||||
if (Objects.equals(response.getRefundStatus(), "REFUND_SUCCESS")) {
|
||||
return PayRefundRespDTO.successOf(null, LocalDateTimeUtil.of(response.getGmtRefundPay()),
|
||||
outRefundNo, response);
|
||||
}
|
||||
return PayRefundRespDTO.waitingOf(null, outRefundNo, response);
|
||||
}
|
||||
|
||||
// ========== 各种工具方法 ==========
|
||||
|
||||
protected String formatAmount(Integer amount) {
|
||||
|
@ -307,6 +307,11 @@ public abstract class AbstractWxPayClient extends AbstractPayClient<WxPayClientC
|
||||
return PayRefundRespDTO.failureOf(result.getOutRefundNo(), response);
|
||||
}
|
||||
|
||||
@Override
|
||||
protected PayRefundRespDTO doGetRefund(String outTradeNo, String outRefundNo) {
|
||||
return null;
|
||||
}
|
||||
|
||||
// ========== 各种工具方法 ==========
|
||||
|
||||
static String formatDateV2(LocalDateTime time) {
|
||||
|
@ -4,6 +4,7 @@ import cn.hutool.core.map.MapUtil;
|
||||
import cn.hutool.core.util.StrUtil;
|
||||
import cn.iocoder.yudao.framework.pay.core.client.dto.order.PayOrderRespDTO;
|
||||
import cn.iocoder.yudao.framework.pay.core.client.dto.order.PayOrderUnifiedReqDTO;
|
||||
import cn.iocoder.yudao.framework.pay.core.client.dto.refund.PayRefundRespDTO;
|
||||
import cn.iocoder.yudao.framework.pay.core.enums.channel.PayChannelEnum;
|
||||
import cn.iocoder.yudao.framework.pay.core.enums.order.PayOrderDisplayModeEnum;
|
||||
import com.github.binarywang.wxpay.bean.order.WxPayMpOrderResult;
|
||||
|
@ -70,6 +70,12 @@ public class PayRefundDO extends BaseDO {
|
||||
* 关联 {@link PayOrderDO#getId()}
|
||||
*/
|
||||
private Long orderId;
|
||||
/**
|
||||
* 支付订单编号
|
||||
*
|
||||
* 冗余 {@link PayOrderDO#getNo()}
|
||||
*/
|
||||
private String orderNo;
|
||||
|
||||
// ========== 商户相关字段 ==========
|
||||
/**
|
||||
|
Loading…
Reference in New Issue
Block a user