【功能优化】 支付回调相关接口增加请求头参数
parent
a1fbbe35fa
commit
a9f9b36d71
|
@ -64,7 +64,8 @@ public class PayNotifyController {
|
|||
@PermitAll
|
||||
public String notifyOrder(@PathVariable("channelId") Long channelId,
|
||||
@RequestParam(required = false) Map<String, String> params,
|
||||
@RequestBody(required = false) String body) {
|
||||
@RequestBody(required = false) String body,
|
||||
@RequestHeader Map<String, String> headers) {
|
||||
log.info("[notifyOrder][channelId({}) 回调数据({}/{})]", channelId, params, body);
|
||||
// 1. 校验支付渠道是否存在
|
||||
PayClient payClient = channelService.getPayClient(channelId);
|
||||
|
@ -74,7 +75,7 @@ public class PayNotifyController {
|
|||
}
|
||||
|
||||
// 2. 解析通知数据
|
||||
PayOrderRespDTO notify = payClient.parseOrderNotify(params, body);
|
||||
PayOrderRespDTO notify = payClient.parseOrderNotify(params, body, headers);
|
||||
orderService.notifyOrder(channelId, notify);
|
||||
return "success";
|
||||
}
|
||||
|
@ -84,7 +85,8 @@ public class PayNotifyController {
|
|||
@PermitAll
|
||||
public String notifyRefund(@PathVariable("channelId") Long channelId,
|
||||
@RequestParam(required = false) Map<String, String> params,
|
||||
@RequestBody(required = false) String body) {
|
||||
@RequestBody(required = false) String body,
|
||||
@RequestHeader Map<String, String> headers) {
|
||||
log.info("[notifyRefund][channelId({}) 回调数据({}/{})]", channelId, params, body);
|
||||
// 1. 校验支付渠道是否存在
|
||||
PayClient payClient = channelService.getPayClient(channelId);
|
||||
|
@ -94,7 +96,7 @@ public class PayNotifyController {
|
|||
}
|
||||
|
||||
// 2. 解析通知数据
|
||||
PayRefundRespDTO notify = payClient.parseRefundNotify(params, body);
|
||||
PayRefundRespDTO notify = payClient.parseRefundNotify(params, body, headers);
|
||||
refundService.notifyRefund(channelId, notify);
|
||||
return "success";
|
||||
}
|
||||
|
@ -104,7 +106,8 @@ public class PayNotifyController {
|
|||
@PermitAll
|
||||
public String notifyTransfer(@PathVariable("channelId") Long channelId,
|
||||
@RequestParam(required = false) Map<String, String> params,
|
||||
@RequestBody(required = false) String body) {
|
||||
@RequestBody(required = false) String body,
|
||||
@RequestHeader Map<String, String> headers) {
|
||||
log.info("[notifyTransfer][channelId({}) 回调数据({}/{})]", channelId, params, body);
|
||||
// 1. 校验支付渠道是否存在
|
||||
PayClient payClient = channelService.getPayClient(channelId);
|
||||
|
@ -114,7 +117,7 @@ public class PayNotifyController {
|
|||
}
|
||||
|
||||
// 2. 解析通知数据
|
||||
PayTransferRespDTO notify = payClient.parseTransferNotify(params, body);
|
||||
PayTransferRespDTO notify = payClient.parseTransferNotify(params, body, headers);
|
||||
payTransferService.notifyTransfer(channelId, notify);
|
||||
return "success";
|
||||
}
|
||||
|
|
|
@ -89,7 +89,7 @@ public class WalletPayClient extends AbstractPayClient<NonePayClientConfig> {
|
|||
}
|
||||
|
||||
@Override
|
||||
protected PayOrderRespDTO doParseOrderNotify(Map<String, String> params, String body) {
|
||||
protected PayOrderRespDTO doParseOrderNotify(Map<String, String> params, String body, Map<String, String> headers) {
|
||||
throw new UnsupportedOperationException("钱包支付无支付回调");
|
||||
}
|
||||
|
||||
|
@ -144,7 +144,7 @@ public class WalletPayClient extends AbstractPayClient<NonePayClientConfig> {
|
|||
}
|
||||
|
||||
@Override
|
||||
protected PayRefundRespDTO doParseRefundNotify(Map<String, String> params, String body) {
|
||||
protected PayRefundRespDTO doParseRefundNotify(Map<String, String> params, String body, Map<String, String> headers) {
|
||||
throw new UnsupportedOperationException("钱包支付无退款回调");
|
||||
}
|
||||
|
||||
|
@ -178,7 +178,7 @@ public class WalletPayClient extends AbstractPayClient<NonePayClientConfig> {
|
|||
}
|
||||
|
||||
@Override
|
||||
protected PayTransferRespDTO doParseTransferNotify(Map<String, String> params, String body) throws Throwable {
|
||||
protected PayTransferRespDTO doParseTransferNotify(Map<String, String> params, String body, Map<String, String> headers) throws Throwable {
|
||||
throw new UnsupportedOperationException("未实现");
|
||||
}
|
||||
|
||||
|
|
|
@ -39,9 +39,10 @@ public interface PayClient {
|
|||
*
|
||||
* @param params HTTP 回调接口 content type 为 application/x-www-form-urlencoded 的所有参数
|
||||
* @param body HTTP 回调接口的 request body
|
||||
* @param headers HTTP 回调接口的 request headers
|
||||
* @return 支付订单信息
|
||||
*/
|
||||
PayOrderRespDTO parseOrderNotify(Map<String, String> params, String body);
|
||||
PayOrderRespDTO parseOrderNotify(Map<String, String> params, String body, Map<String, String> headers);
|
||||
|
||||
/**
|
||||
* 获得支付订单信息
|
||||
|
@ -66,9 +67,10 @@ public interface PayClient {
|
|||
*
|
||||
* @param params HTTP 回调接口 content type 为 application/x-www-form-urlencoded 的所有参数
|
||||
* @param body HTTP 回调接口的 request body
|
||||
* @param headers HTTP 回调接口的 request headers
|
||||
* @return 支付订单信息
|
||||
*/
|
||||
PayRefundRespDTO parseRefundNotify(Map<String, String> params, String body);
|
||||
PayRefundRespDTO parseRefundNotify(Map<String, String> params, String body, Map<String, String> headers);
|
||||
|
||||
/**
|
||||
* 获得退款订单信息
|
||||
|
@ -103,8 +105,9 @@ public interface PayClient {
|
|||
*
|
||||
* @param params HTTP 回调接口 content type 为 application/x-www-form-urlencoded 的所有参数
|
||||
* @param body HTTP 回调接口的 request body
|
||||
* @param headers HTTP 回调接口的 request headers
|
||||
* @return 转账信息
|
||||
*/
|
||||
PayTransferRespDTO parseTransferNotify(Map<String, String> params, String body);
|
||||
PayTransferRespDTO parseTransferNotify(Map<String, String> params, String body, Map<String, String> headers);
|
||||
|
||||
}
|
||||
|
|
|
@ -101,9 +101,9 @@ public abstract class AbstractPayClient<Config extends PayClientConfig> implemen
|
|||
throws Throwable;
|
||||
|
||||
@Override
|
||||
public final PayOrderRespDTO parseOrderNotify(Map<String, String> params, String body) {
|
||||
public final PayOrderRespDTO parseOrderNotify(Map<String, String> params, String body, Map<String, String> headers) {
|
||||
try {
|
||||
return doParseOrderNotify(params, body);
|
||||
return doParseOrderNotify(params, body, headers);
|
||||
} catch (ServiceException ex) { // 业务异常,都是实现类已经翻译,所以直接抛出即可
|
||||
throw ex;
|
||||
} catch (Throwable ex) {
|
||||
|
@ -113,7 +113,7 @@ public abstract class AbstractPayClient<Config extends PayClientConfig> implemen
|
|||
}
|
||||
}
|
||||
|
||||
protected abstract PayOrderRespDTO doParseOrderNotify(Map<String, String> params, String body)
|
||||
protected abstract PayOrderRespDTO doParseOrderNotify(Map<String, String> params, String body, Map<String, String> headers)
|
||||
throws Throwable;
|
||||
|
||||
@Override
|
||||
|
@ -155,9 +155,9 @@ public abstract class AbstractPayClient<Config extends PayClientConfig> implemen
|
|||
protected abstract PayRefundRespDTO doUnifiedRefund(PayRefundUnifiedReqDTO reqDTO) throws Throwable;
|
||||
|
||||
@Override
|
||||
public final PayRefundRespDTO parseRefundNotify(Map<String, String> params, String body) {
|
||||
public final PayRefundRespDTO parseRefundNotify(Map<String, String> params, String body, Map<String, String> headers) {
|
||||
try {
|
||||
return doParseRefundNotify(params, body);
|
||||
return doParseRefundNotify(params, body, headers);
|
||||
} catch (ServiceException ex) { // 业务异常,都是实现类已经翻译,所以直接抛出即可
|
||||
throw ex;
|
||||
} catch (Throwable ex) {
|
||||
|
@ -167,7 +167,7 @@ public abstract class AbstractPayClient<Config extends PayClientConfig> implemen
|
|||
}
|
||||
}
|
||||
|
||||
protected abstract PayRefundRespDTO doParseRefundNotify(Map<String, String> params, String body)
|
||||
protected abstract PayRefundRespDTO doParseRefundNotify(Map<String, String> params, String body, Map<String, String> headers)
|
||||
throws Throwable;
|
||||
|
||||
@Override
|
||||
|
@ -220,9 +220,9 @@ public abstract class AbstractPayClient<Config extends PayClientConfig> implemen
|
|||
}
|
||||
|
||||
@Override
|
||||
public final PayTransferRespDTO parseTransferNotify(Map<String, String> params, String body) {
|
||||
public final PayTransferRespDTO parseTransferNotify(Map<String, String> params, String body, Map<String, String> headers) {
|
||||
try {
|
||||
return doParseTransferNotify(params, body);
|
||||
return doParseTransferNotify(params, body, headers);
|
||||
} catch (ServiceException ex) { // 业务异常,都是实现类已经翻译,所以直接抛出即可
|
||||
throw ex;
|
||||
} catch (Throwable ex) {
|
||||
|
@ -232,7 +232,7 @@ public abstract class AbstractPayClient<Config extends PayClientConfig> implemen
|
|||
}
|
||||
}
|
||||
|
||||
protected abstract PayTransferRespDTO doParseTransferNotify(Map<String, String> params, String body)
|
||||
protected abstract PayTransferRespDTO doParseTransferNotify(Map<String, String> params, String body, Map<String, String> headers)
|
||||
throws Throwable;
|
||||
|
||||
@Override
|
||||
|
|
|
@ -79,7 +79,7 @@ public abstract class AbstractAlipayPayClient extends AbstractPayClient<AlipayPa
|
|||
}
|
||||
|
||||
@Override
|
||||
public PayOrderRespDTO doParseOrderNotify(Map<String, String> params, String body) throws Throwable {
|
||||
public PayOrderRespDTO doParseOrderNotify(Map<String, String> params, String body, Map<String, String> headers) throws Throwable {
|
||||
// 1. 校验回调数据
|
||||
Map<String, String> bodyObj = HttpUtil.decodeParamMap(body, StandardCharsets.UTF_8);
|
||||
AlipaySignature.rsaCheckV1(bodyObj, config.getAlipayPublicKey(),
|
||||
|
@ -175,7 +175,7 @@ public abstract class AbstractAlipayPayClient extends AbstractPayClient<AlipayPa
|
|||
}
|
||||
|
||||
@Override
|
||||
public PayRefundRespDTO doParseRefundNotify(Map<String, String> params, String body) {
|
||||
public PayRefundRespDTO doParseRefundNotify(Map<String, String> params, String body, Map<String, String> headers) {
|
||||
// 补充说明:支付宝退款时,没有回调,这点和微信支付是不同的。并且,退款分成部分退款、和全部退款。
|
||||
// ① 部分退款:是会有回调,但是它回调的是订单状态的同步回调,不是退款订单的回调
|
||||
// ② 全部退款:Wap 支付有订单状态的同步回调,但是 PC/扫码又没有
|
||||
|
@ -327,7 +327,7 @@ public abstract class AbstractAlipayPayClient extends AbstractPayClient<AlipayPa
|
|||
|
||||
// TODO @chihuo:这里是不是也要实现,支付宝的。
|
||||
@Override
|
||||
protected PayTransferRespDTO doParseTransferNotify(Map<String, String> params, String body) throws Throwable {
|
||||
protected PayTransferRespDTO doParseTransferNotify(Map<String, String> params, String body, Map<String, String> headers) throws Throwable {
|
||||
throw new UnsupportedOperationException("未实现");
|
||||
}
|
||||
|
||||
|
|
|
@ -58,17 +58,17 @@ public class MockPayClient extends AbstractPayClient<NonePayClientConfig> {
|
|||
}
|
||||
|
||||
@Override
|
||||
protected PayTransferRespDTO doParseTransferNotify(Map<String, String> params, String body) throws Throwable {
|
||||
protected PayTransferRespDTO doParseTransferNotify(Map<String, String> params, String body, Map<String, String> headers) throws Throwable {
|
||||
throw new UnsupportedOperationException("未实现");
|
||||
}
|
||||
|
||||
@Override
|
||||
protected PayRefundRespDTO doParseRefundNotify(Map<String, String> params, String body) {
|
||||
protected PayRefundRespDTO doParseRefundNotify(Map<String, String> params, String body, Map<String, String> headers) {
|
||||
throw new UnsupportedOperationException("模拟支付无退款回调");
|
||||
}
|
||||
|
||||
@Override
|
||||
protected PayOrderRespDTO doParseOrderNotify(Map<String, String> params, String body) {
|
||||
protected PayOrderRespDTO doParseOrderNotify(Map<String, String> params, String body, Map<String, String> headers) {
|
||||
throw new UnsupportedOperationException("模拟支付无支付回调");
|
||||
}
|
||||
|
||||
|
|
|
@ -18,10 +18,7 @@ import cn.iocoder.yudao.framework.pay.core.client.dto.transfer.WxPayTransferPart
|
|||
import cn.iocoder.yudao.framework.pay.core.client.impl.AbstractPayClient;
|
||||
import cn.iocoder.yudao.framework.pay.core.enums.order.PayOrderStatusRespEnum;
|
||||
import cn.iocoder.yudao.framework.pay.core.enums.transfer.PayTransferTypeEnum;
|
||||
import com.github.binarywang.wxpay.bean.notify.WxPayNotifyV3Result;
|
||||
import com.github.binarywang.wxpay.bean.notify.WxPayOrderNotifyResult;
|
||||
import com.github.binarywang.wxpay.bean.notify.WxPayRefundNotifyResult;
|
||||
import com.github.binarywang.wxpay.bean.notify.WxPayRefundNotifyV3Result;
|
||||
import com.github.binarywang.wxpay.bean.notify.*;
|
||||
import com.github.binarywang.wxpay.bean.request.*;
|
||||
import com.github.binarywang.wxpay.bean.result.*;
|
||||
import com.github.binarywang.wxpay.bean.transfer.QueryTransferBatchesRequest;
|
||||
|
@ -157,12 +154,12 @@ public abstract class AbstractWxPayClient extends AbstractPayClient<WxPayClientC
|
|||
}
|
||||
|
||||
@Override
|
||||
public PayOrderRespDTO doParseOrderNotify(Map<String, String> params, String body) throws WxPayException {
|
||||
public PayOrderRespDTO doParseOrderNotify(Map<String, String> params, String body, Map<String, String> headers) throws WxPayException {
|
||||
switch (config.getApiVersion()) {
|
||||
case API_VERSION_V2:
|
||||
return doParseOrderNotifyV2(body);
|
||||
case API_VERSION_V3:
|
||||
return doParseOrderNotifyV3(body);
|
||||
return doParseOrderNotifyV3(body, headers);
|
||||
default:
|
||||
throw new IllegalArgumentException(String.format("未知的 API 版本(%s)", config.getApiVersion()));
|
||||
}
|
||||
|
@ -179,9 +176,10 @@ public abstract class AbstractWxPayClient extends AbstractPayClient<WxPayClientC
|
|||
response.getOutTradeNo(), body);
|
||||
}
|
||||
|
||||
private PayOrderRespDTO doParseOrderNotifyV3(String body) throws WxPayException {
|
||||
private PayOrderRespDTO doParseOrderNotifyV3(String body, Map<String, String> headers) throws WxPayException {
|
||||
// 1. 解析回调
|
||||
WxPayNotifyV3Result response = client.parseOrderNotifyV3Result(body, null);
|
||||
SignatureHeader header = getRequestHeader(headers);
|
||||
WxPayNotifyV3Result response = client.parseOrderNotifyV3Result(body, header);
|
||||
WxPayNotifyV3Result.DecryptNotifyResult result = response.getResult();
|
||||
// 2. 构建结果
|
||||
Integer status = parseStatus(result.getTradeState());
|
||||
|
@ -190,6 +188,21 @@ public abstract class AbstractWxPayClient extends AbstractPayClient<WxPayClientC
|
|||
result.getOutTradeNo(), body);
|
||||
}
|
||||
|
||||
private SignatureHeader getRequestHeader(Map<String, String> headers) {
|
||||
// 获取通知签名
|
||||
String signature = headers.get("wechatpay-signature");
|
||||
String nonce = headers.get("wechatpay-nonce");
|
||||
String serial = headers.get("wechatpay-serial");
|
||||
String timestamp = headers.get("wechatpay-timestamp");
|
||||
|
||||
SignatureHeader signatureHeader = new SignatureHeader();
|
||||
signatureHeader.setSignature(signature);
|
||||
signatureHeader.setNonce(nonce);
|
||||
signatureHeader.setSerial(serial);
|
||||
signatureHeader.setTimeStamp(timestamp);
|
||||
return signatureHeader;
|
||||
}
|
||||
|
||||
@Override
|
||||
protected PayOrderRespDTO doGetOrder(String outTradeNo) throws Throwable {
|
||||
try {
|
||||
|
@ -321,12 +334,12 @@ public abstract class AbstractWxPayClient extends AbstractPayClient<WxPayClientC
|
|||
}
|
||||
|
||||
@Override
|
||||
public PayRefundRespDTO doParseRefundNotify(Map<String, String> params, String body) throws WxPayException {
|
||||
public PayRefundRespDTO doParseRefundNotify(Map<String, String> params, String body, Map<String, String> headers) throws WxPayException {
|
||||
switch (config.getApiVersion()) {
|
||||
case API_VERSION_V2:
|
||||
return doParseRefundNotifyV2(body);
|
||||
case API_VERSION_V3:
|
||||
return parseRefundNotifyV3(body);
|
||||
return parseRefundNotifyV3(body, headers);
|
||||
default:
|
||||
throw new IllegalArgumentException(String.format("未知的 API 版本(%s)", config.getApiVersion()));
|
||||
}
|
||||
|
@ -344,9 +357,10 @@ public abstract class AbstractWxPayClient extends AbstractPayClient<WxPayClientC
|
|||
return PayRefundRespDTO.failureOf(result.getOutRefundNo(), response);
|
||||
}
|
||||
|
||||
private PayRefundRespDTO parseRefundNotifyV3(String body) throws WxPayException {
|
||||
private PayRefundRespDTO parseRefundNotifyV3(String body, Map<String, String> headers) throws WxPayException {
|
||||
// 1. 解析回调
|
||||
WxPayRefundNotifyV3Result response = client.parseRefundNotifyV3Result(body, null);
|
||||
SignatureHeader header = getRequestHeader(headers);
|
||||
WxPayRefundNotifyV3Result response = client.parseRefundNotifyV3Result(body, header);
|
||||
WxPayRefundNotifyV3Result.DecryptNotifyResult result = response.getResult();
|
||||
// 2. 构建结果
|
||||
if (Objects.equals("SUCCESS", result.getRefundStatus())) {
|
||||
|
@ -357,10 +371,10 @@ public abstract class AbstractWxPayClient extends AbstractPayClient<WxPayClientC
|
|||
}
|
||||
|
||||
@Override
|
||||
public PayTransferRespDTO doParseTransferNotify(Map<String, String> params, String body) throws WxPayException {
|
||||
public PayTransferRespDTO doParseTransferNotify(Map<String, String> params, String body, Map<String, String> headers) throws WxPayException {
|
||||
switch (config.getApiVersion()) {
|
||||
case API_VERSION_V3:
|
||||
return parseTransferNotifyV3(body);
|
||||
return parseTransferNotifyV3(body, headers);
|
||||
case API_VERSION_V2:
|
||||
throw new UnsupportedOperationException("V2 版本暂不支持,建议使用 V3 版本");
|
||||
default:
|
||||
|
@ -368,10 +382,11 @@ public abstract class AbstractWxPayClient extends AbstractPayClient<WxPayClientC
|
|||
}
|
||||
}
|
||||
|
||||
private PayTransferRespDTO parseTransferNotifyV3(String body) throws WxPayException {
|
||||
private PayTransferRespDTO parseTransferNotifyV3(String body, Map<String, String> headers) throws WxPayException {
|
||||
// 1. 解析回调
|
||||
SignatureHeader header = getRequestHeader(headers);
|
||||
// TODO @luchi:这个可以复用 wxjava 里的类么?
|
||||
WxPayTransferPartnerNotifyV3Result response = client.baseParseOrderNotifyV3Result(body, null, WxPayTransferPartnerNotifyV3Result.class, WxPayTransferPartnerNotifyV3Result.TransferNotifyResult.class);
|
||||
WxPayTransferPartnerNotifyV3Result response = client.baseParseOrderNotifyV3Result(body, header, WxPayTransferPartnerNotifyV3Result.class, WxPayTransferPartnerNotifyV3Result.TransferNotifyResult.class);
|
||||
WxPayTransferPartnerNotifyV3Result.TransferNotifyResult result = response.getResult();
|
||||
// 2. 构建结果
|
||||
if (Objects.equals("FINISHED", result.getBatchStatus())) {
|
||||
|
|
Loading…
Reference in New Issue