# 微信支付
微信云托管通过开放接口服务封装了微信支付原有的接口,所以在使用前需要开启「开放接口服务」
要了解微信支付接口的运作和使用理论,请前往使用指南
我们也给出了一个Nodejs案例、PHP案例,具体可以前往查看学习。
如果在接口请求时出现302、400,返回空值等情况,可以在请求时加header content-type:'application/json'
解决。
如果在请求时返回 { return_code: 'FAIL', return _msg: '受理关系不存在}
,则需要前往微信云托管控制台 - 设置 - 其他设置 - 微信支付配置绑定商户号到已授权状态。
具体方法的详细文档如下:
# 一、支付接口
接口名称 | 接口 | 需要 OpenID |
---|---|---|
统一下单 | http://api.weixin.qq.com/_/pay/unifiedorder | ✅ |
查询订单 | http://api.weixin.qq.com/_/pay/queryorder | |
关闭订单 | http://api.weixin.qq.com/_/pay/closeorder | |
下载对账单 | http://api.weixin.qq.com/_/pay/downloadbill | |
申请退款 | http://api.weixin.qq.com/_/pay/refund | ✅ |
查询退款 | http://api.weixin.qq.com/_/pay/queryrefund |
# 二、分账接口
接口名称 | 接口 | 需要 OpenID |
---|---|---|
添加分账接收方 | http://api.weixin.qq.com/_/pay/profitsharingaddreceiver | |
删除分账接收方 | http://api.weixin.qq.com/_/pay/profitsharingremovereceiver | |
请求单次分账 | http://api.weixin.qq.com/_/pay/profitsharing | |
请求多次分账 | http://api.weixin.qq.com/_/pay/multiprofitsharing | |
完结分账 | http://api.weixin.qq.com/_/pay/profitsharingfinish | |
查询分账结果 | http://api.weixin.qq.com/_/pay/profitsharingquery | |
分账回退 | http://api.weixin.qq.com/_/pay/profitsharingreturn | |
回退结果查询 | http://api.weixin.qq.com/_/pay/profitsharingreturnquery |
# 三、结果回调
# 四、代码示例-Node.js
以下代码实现了下单到退款的基本业务逻辑,只是用于参考,实际接入请根据自己的业务情况改造,比如将触发订单由流程决定,添加校验逻辑等。
完整例子可以前往Github仓库
# 1. 服务端代码
const express = require('express')
const request = require('request')
const app = express()
app.use(express.json())
const mchId = process.env.mch_id || '1XXXXXXXXX' // 这里商户号需要替换成自己的
// 也可以在部署时设定环境变量【mch_id】为商户号
// 统一下单
app.post('/unifiedOrder', async function (req, res) {
const ip = req.headers['x-forwarded-for'] // 小程序直接callcontainer请求会存在
const openid = req.headers['x-wx-openid'] // 小程序直接callcontainer请求会存在
// 如果是业务异步流程需自己替换openid来源
const { text, noid, fee } = req.body
const payreq = {
body: text, // 订单描述
out_trade_no: noid, // 自定义订单号
sub_mch_id: mchId, // 微信支付商户号
total_fee: fee, // 金额,单位:分
openid: openid, // 用户唯一身份ID
spbill_create_ip: ip, // 用户客户端IP地址
env_id: req.headers['x-wx-env'], // 接收回调的环境ID
callback_type: 2, // 云托管服务接收回调,填2
container: {
service: req.headers['x-wx-service'], // 回调的服务名称
path: '/' // 回调的路径
}
}
console.log('[unifiedOrder]请求体', payreq)
const info = await callpay('unifiedorder', payreq)
console.log('[unifiedOrder]响应体', info)
res.send(info)
})
// 查询订单
app.post('/queryorder', async function (req, res) {
const { noid } = req.body
const payreq = {
out_trade_no: noid, // 自定义订单号
sub_mch_id: mchId // 微信支付商户号
}
console.log('[queryorder]请求体', payreq)
const info = await callpay('queryorder', payreq)
console.log('[queryorder]响应体', info)
res.send(info)
})
// 关闭订单
app.post('/closeorder', async function (req, res) {
const { noid } = req.body
const payreq = {
out_trade_no: noid, // 自定义订单号
sub_mch_id: mchId // 微信支付商户号
}
console.log('[closeorder]请求体', payreq)
const info = await callpay('closeorder', payreq)
console.log('[closeorder]响应体', info)
res.send(info)
})
// 发起退款
app.post('/refund', async function (req, res) {
const { text, noid, fee } = req.body
const payreq = {
body: text, // 订单描述
out_trade_no: noid, // 自定义订单号
out_refund_no: `R_${noid}`, // 自定义退款单号
sub_mch_id: mchId, // 微信支付商户号
total_fee: fee, // 订单金额,单位:分
refund_fee: fee, // 退款金额,单位:分
refund_desc: `${text}_退款`, // 订单退款描述
env_id: req.headers['x-wx-env'], // 接收回调的环境ID
callback_type: 2, // 云托管服务接收回调,填2
container: {
service: req.headers['x-wx-service'], // 回调的服务名称
path: '/' // 回调的路径
}
}
console.log('[refund]请求体', payreq)
const info = await callpay('refund', payreq)
console.log('[refund]响应体', info)
res.send(info)
})
// 查询退款
app.post('/queryrefund', async function (req, res) {
const { noid } = req.body
const payreq = {
out_trade_no: noid, // 自定义订单号
sub_mch_id: mchId // 微信支付商户号
}
console.log('[queryrefund]请求体', payreq)
const info = await callpay('queryrefund', payreq)
console.log('[queryrefund]响应体', info)
res.send(info)
})
// 接收回调信息
app.all('/', function (req, res) {
console.log('回调请求头', req.headers)
console.log('回调收到内容', req.body || req.query)
res.send('success')
})
app.listen(80, function () {
console.log('服务启动成功!')
})
function callpay (action, paybody) {
return new Promise((resolve, reject) => {
request({
url: `http://api.weixin.qq.com/_/pay/${action}`,
method: 'POST',
headers: {
'content-type': 'application/json'
},
body: JSON.stringify(paybody)
}, function (error, res) {
if (error) {
resolve(error)
} else {
resolve(res.body)
}
})
})
}
# 2.在小程序中调用
wx.cloud.callContainer({
config: {
env: "prod-xxxxxx" // 替换自己的环境ID
},
path: "/order",
header: {
"X-WX-SERVICE": "pay", // 替换自己的服务
"content-type": "application/json"
},
method: "POST",
data: {
text: "测试支付", // 自定义
noid: "2021WERUN1647840687637", // 自定义
fee: 1 // 分,金额自定义
}
})
# 3.在公众号中调用
公众号(服务号)中调用前,需要在管理后台(https://mp.weixin.qq.com)开通配置微信支付,具体配置过程跟小程序一致。
然后在网页中初始化公众号SDK,获取choosePay接口权限。
从服务端中获取支付payment信息,传入choosePay接口发起调用即可。
具体可以参见代码案例:github仓库文件夹