跳转到内容

Refund

适用于 EC 和 In-Store(线下)场景。

如果您希望将资金退还给用户(例如,用户退货),您需要 refund 该笔支付。

您只能在支付已被 captured 之后才能进行 refund。尚未 captured 的支付必须改用 cancel。详见 Cancel 章节。

您可以 refund 全部已 captured 金额,也可以 refund 部分已 captured 金额。如果多次部分 refund 的总额不超过已 captured 金额,您也可以进行多次部分 refund。

最长 refund 时限为支付完成后的 365 天。

Make a refund request

Step 1: Make a refund request

当您收到 payment.statusCaptured 的 capture 结果时,可以从您的服务器向 EVO Cloud 端点

/g2/v1/payment/mer/{sid}/refund

发起 HTTP POST 请求以 refund 初始 payment,并指定以下参数。

查询参数必填说明
merchantTransIDM初始 Payment 的 merchantTransInfo.merchantTransID
Body 参数必填说明
merchantTransInfoM本次 refund 的引用信息,包含唯一的 merchantTransIDmerchantTransTime(发起请求的时间)。
transAmountMrefund 支付的币种与金额。金额须符合该币种的最小货币单位。
initiatingReasonO可在该字段中说明本次请求的原因。
webhookO用于接收通知的 URL。指定后可在支付成功后从 EVO Cloud 接收通知。
paymentMethodO支付方式对象。
paymentMethod.typeO本文档场景下须为 card
metadataO您可在请求中自定义的引用信息,将在响应中原样回显。

paymentMethod 对象的更多细节:

1.paymentMethod.type:请求中设置为 card

2.paymentMethod.card.encryptedCardInfo:加密后的卡信息。如果使用 EVO Cloud 客户端方案安全加密用户卡信息,前端会从 EVO Cloud SDK 获取该值,需发送至您的服务器,再由服务器原样转发至 EVO Cloud。

3.paymentMethod.card.cardInfo:卡信息原始数据。如果将原始卡数据采集并发送至 EVO Cloud,需要在此对象中指定 cardNumberexpiryDatecvc(可选)、track2holderName。对于部分 UnionPay 借记卡,expiryDate 也为可选。 (如果 paymentMethod.card.encryptedCardInfopaymentMethod.card.cardInfo 同时存在,将以 paymentMethod.card.cardInfo 为准。)

4.paymentMethod.card字段

字段路径必填/选填条件说明
paymentMethod.cardMpaymentMethod.type=card卡相关交易对象。
paymentMethod.card.encryptedCardInfoO已批准加密卡集成方案加密卡信息。
paymentMethod.card.cardInfoO已批准卡信息集成方案卡信息容器。
paymentMethod.card.cardInfo.cardNumberM手动/MOTO 或最终 schema 要求卡号。在示例或测试数据中请勿使用真实值。
paymentMethod.card.cardInfo.expiryDateOMOTO 必填过期日期,MMYY 格式。
paymentMethod.card.posEntryModeOPOS 卡通道卡数据输入方式。
paymentMethod.card.pinFlagO终端支持 PINtrue 表示终端可接受 PIN;false 表示不接受。
paymentMethod.card.termReadabilityO提供终端能力时终端卡数据输入能力。
paymentMethod.card.icCardCondCodeOUnionPay IC 场景UnionPay 卡条件码。
paymentMethod.card.noSecretNoSignFlagOUnionPay 场景UnionPay 无密/无签标识。
paymentMethod.card.cardInfo.track1O磁条或特定通道要求Track 1 数据。最终字段名以已批准的 schema 为准。
paymentMethod.card.cardInfo.track2O磁条、ICC、contactless 或 fallback 场景Track 2 数据。禁止以明文存储或记录。
paymentMethod.card.cardInfo.cardSequenceNumOICC 或 contactless 场景IC 卡序列号。
paymentMethod.card.cardInfo.icCardDataOICC 或 contactless 场景EMV/ICC TLV 数据。
paymentMethod.card.pinOPIN 交易PIN 容器(如最终 schema 中包含)。
paymentMethod.card.pin.encryptedPinMPIN 交易加密后的 PIN block。禁止以明文记录或持久化。
paymentMethod.card.pin.pinEncryptMethodMPIN 交易已批准的 PIN 加密方式,例如支持时的 3DES
paymentMethod.card.pin.checkValueO启用密钥版本查询用于识别适用工作密钥版本的值(如支持)。

5.Card posEntryMode 模式

posEntryMode 模式交易活动典型条件数据
magnetic磁条读取track2
ICC接触式芯片插入track2 、icCardData 、cardSequenceNum
contactlessNFC EMV 挥卡track2 、icCardData 、cardSequenceNum
contactless magnetic使用磁条通道的 contactless 交易track2
fallbackEMV 回退至磁条track2
manual手工输入卡cardNumber 、expiryDate
MOTO邮购/电话订购cardNumber 、expiryDate

最终 API schema 是字段名、长度、条件必填与 PSP 特定限制的权威依据。

以下为 10 USD Refund 请求示例:

js
1.curl -X POST https://{EVO_Cloud_DOMAIN_NAME.com}/g2/v1/payment/mer/{sid}/refund?merchantTransID={YOUR_TRANS_ID_OF_INITIAL_PAYMENT}\  
2.-H "Content-Type: application/json" \  
3.-H "DateTime: 2021-12-31T08:30:59+0800" \  
4.-H "MsgID: 2d21a5715c034efb7e0aa383b885fc7a" \  
5.-H "SignType: SHA256" \  
6.-H "Authorization: YOUR_MESSAGE_SIGNATURE" \  
7.-d '{  
8.    "merchantTransInfo": {  
9.        "merchantTransID": "YOUR_TRANS_ID_OF_INITIAL_REFUND",  
10.        "merchantTransTime": "2021-12-31T08:35:59+08:00"  
11.    },  
12.    "transAmount": {  
13.        "currency": "USD",  
14.        "value": "10.00"  
15.    },
16.      "paymentMethod": {
17.         "type": "card",
18.         "card": {
19.             "posEntryMode": "ICC",
20.             "pinFlag": true,
21.             "cardInfo": {
22.                 "cardNumber": "6222021234567890123",
23.                 "track2": "6222021234567890123=26122011234567890123",
24.                 "icCardData": "9F02069F03069F1A029F26089F27019F36029F37049F1008",
25.                 "cardSequenceNum": "001"
26.             },
27.             "pin": {
28.                 "encryptedPin": "base64encodedPinBlock==",
29.                 "pinEncryptMethod": "3DES",
30.                 "checkValue": "A1B2C3"
31.             }
32.         }
33.     },
34.    "webhook": "https://YOUR_COMPANY.com/WEBHOOK",  
35.    "initiatingReason": "Goods returned by customers",  
36.    "metadata": "This is a metadata"  ,
37.     "transInitiator": {
38.         "platform": "POS",
39.         "terminalID": "30100101",
40.         "paymentScenario": "inStore"
41.     }
42.}'

如果请求成功,响应中将包含一个 refund 对象和一个 payment 对象,分别展示 refund 和原始 payment 的状态及相关信息。

refund 对象详细信息:

  1. refund.status:本次 refund 的状态,必填。取值可为 SuccessFailedReceived。如果 refund.statusReceived,您需要再发起一次 HTTP GET 请求以获取 refund 的最终状态(详见 Step 2),或等待 EVO Cloud 的通知 webhook。

  2. refund.transAmount:refund 的币种与金额,必填。从您的请求中原样回显。

  3. refund.merchantTransInfo:本次 refund 的引用对象,由您的服务器生成,必填。从您的请求中原样回显。

  4. refund.evoTransInfo:本次 refund 的引用对象,由 EVO Cloud 生成,必填。包含 evoTransIDevoTransTime,以及部分 PSP(如 Visa 或 Mastercard)的可选字段 traceNumretrievalReferenceNum

  5. refund.pspTransInfo:本次 refund 的引用对象,由 PSP 生成,可选。包含 pspTransIDpspTransTimeauthorizationCode。如果 PSP 返回,EVO Cloud 会将该信息从 PSP 转发至您的服务器。

  6. refund.billingAmountrefund.billingFXRate:refund 的用户账单币种与金额,以及 refund.transAmount.currencyrefund.billingAmount.currency 之间的汇率,可选。如果 PSP 返回,EVO Cloud 会将该信息从 PSP 转发至您的服务器。适用于 PSP 进行货币换算的 E-Wallet 支付,或您启用了 DCC 功能的卡支付。详情请联系 EVO Cloud 客户经理。

  7. refund.convertTransAmountrefund.convertTransFXRate:EVO Cloud 在将交易发送至 PSP 时,基于 transAmounttransAmount.currency 到目标币种的汇率计算出的币种与金额,以及 refund.transAmount.currencyrefund.convertTransAmount.currency 之间的汇率,可选。如果您在 EVO Cloud 启用了货币换算功能且本次 refund 适用,将提供该汇率。详情请联系 EVO Cloud 客户经理。

以下为成功响应示例:

js
1.{  
2.    "result": {  
3.        "code": "S0000",  
4.        "message": "Success"  
5.    },  
6.    "paymentMethod": {  
7.        "card": {  
8.            "first6No": "476134",  
9.            "last4No": "0019",  
10.            "paymentBrand": "Visa",  
11.            "fundingType": "credit"  
12.        }  
13.    },  
14.    "payment": {  
15.        "status": "Refunding",  
16.        "merchantTransInfo": {  
17.            "merchantTransID": "f2d45e3397704f2a818b7b74bc94e7ce",  
18.            "merchantTransTime": "2021-12-31T08:30:59+08:00"  
19.        },  
20.        "evoTransInfo": {  
21.            "evoTransID": "8a0d5cd24b5b4156b94010cee115bceb",  
22.            "evoTransTime": "2021-12-31T00:30:59Z"  
23.        },  
24.        "pspTransInfo": {  
25.            "pspTransTime": "2021-12-31T08:30:59+08:00",  
26.            "authorizationCode": "091410",  
27.            "retrievalReferenceNum": "135616370503"  
28.        },  
29.        "transAmount": {  
30.            "currency": "USD",  
31.            "value": "10.00"  
32.        }  
33.    },  
34.    "refund": {  
35.        "status": "Received",  
36.        "merchantTransInfo": {  
37.            "merchantTransID": "YOUR_TRANS_ID_OF_INITIAL_REFUND",  
38.            "merchantTransTime": "2021-12-31T08:35:59+08:00"  
39.        },  
40.        "evoTransInfo": {  
41.            "evoTransID": "2cf248d44a0f4ed5991fa4f77879d71e",  
42.            "evoTransTime": "2021-12-31T08:35:59+08:00"  
43.        },  
44.        "transAmount": {  
45.            "currency": "USD",  
46.            "value": "10.00"  
47.        }  
48.    },  
49.    "pspData": {  
50.        "name": "Visa"  
51.    },  
52.    "metadata": "This is a metadata"  
}

Step 2: Retrieve the refund result

如果收到 refund.statusReceived,且您未使用 notification webhook,可以从 EVO Cloud 查询最终结果。

从您的服务器向 EVO Cloud 端点

/g2/v1/payment/mer/{sid}/refund

发起 HTTP GET 请求。

查询参数必填说明
merchantTransIDM初始 refund 的 merchantTransInfo.merchantTransID

以下为查询 refund 结果示例:

js
1.curl https://{EVO_Cloud_DOMAIN_NAME.com}/g2/v1/payment/mer/{sid}/refund?merchantTransID={YOUR_TRANS_ID_OF_INITIAL_REFUND} \  
2.-H "Content-Type: application/json" \  
3.-H "DateTime: 2021-12-31T08:30:59+0800" \  
4.-H "MsgID: 2d21a5715c034efb7e0aa383b885fc7a" \  
5.-H "SignType: SHA256" \  
6.-H "Authorization: YOUR_MESSAGE_SIGNATURE"

以下为 GET 响应示例。POST 响应与 GET 响应类似。

js
1.{  
2.    "result": {  
3.        "code": "S0000",  
4.        "message": "Success"  
5.    },  
6.    "paymentMethod": {  
7.        "card": {  
8.            "first6No": "476134",  
9.            "last4No": "0019",  
10.            "paymentBrand": "Visa",  
11.            "fundingType": "credit"  
12.        }  
13.    },  
14.    "payment": {  
15.        "status": "Refunded",  
16.        "merchantTransInfo": {  
17.            "merchantTransID": "f2d45e3397704f2a818b7b74bc94e7ce",  
18.            "merchantTransTime": "2021-12-31T08:30:59+08:00"  
19.        },  
20.        "evoTransInfo": {  
21.            "evoTransID": "8a0d5cd24b5b4156b94010cee115bceb",  
22.            "evoTransTime": "2021-12-31T00:30:59Z"  
23.        },  
24.        "pspTransInfo": {  
25.            "pspTransTime": "2021-12-31T08:30:59+08:00",  
26.            "authorizationCode": "091410",  
27.            "retrievalReferenceNum": "135616370503"  
28.        },  
29.        "transAmount": {  
30.            "currency": "USD",  
31.            "value": "10.00"  
32.        }  
33.    },  
34.    "refund": {  
35.        "status": "Success",  
36.        "merchantTransInfo": {  
37.            "merchantTransID": "YOUR_TRANS_ID_OF_INITIAL_REFUND",  
38.            "merchantTransTime": "2021-12-31T08:35:59+08:00"  
39.        },  
40.        "evoTransInfo": {  
41.            "evoTransID": "2cf248d44a0f4ed5991fa4f77879d71e",  
42.            "evoTransTime": "2021-12-31T08:35:59+08:00"  
43.        },  
44.        "pspTransInfo": {  
45.            "pspTransTime": "2021-12-31T08:30:59+08:00"  
46.        },  
47.        "transAmount": {  
48.            "currency": "USD",  
49.            "value": "10.00"  
50.        }  
51.    },  
52.    "pspData": {  
53.        "name": "Visa"  
54.    },  
55.    "metadata": "This is a metadata"  
56.}

Make a cancel instead

如果您发起 refund 请求并收到 result.codeB0012,请再次核对响应消息中 payment.status 显示的原始交易状态。如果为 authorised,则表示该笔支付尚未被 captured,您无法 refund 该笔支付。这种情况下,您需要改用 cancel。详见 Cancel 章节。

Error handling

For HTTP POST request to EVO Cloud: 建议在请求发送后至少等待 45 秒。如果在规定时间内未收到响应,需要从 EVO Cloud 查询结果。请参阅 Step 2 发起请求。 For HTTP GET request to EVO Cloud: 可以多次发起请求直到获取结果,建议相邻两次请求之间至少等待 45 秒。如果多次请求后仍无法获取结果,可以改为发起一次新的 cancel 请求。