Wechat Mini App Payment

API Playground

Tips: Get your Wallet ID, User ID and API key via Latipay Merchant Portal > Account > Show hidden values
Tips: Create a minimum amount product (e.g. $ 0.01 NZD/AUD) for testing.

TLTR

  1. use wx js api to login and get code in mini app
  2. use weixin api for getting openid with the code in your server
  3. send a request to latipay with the openid in your server
  4. use wx mini app payment api to make a payment in mini app

API Details

1 - Login in Mini App

https://developers.weixin.qq.com/miniprogram/dev/api/api-login.html#wxloginobject

Use wx js api to login and get code in mini app.

1
2
3
4
5
6
7
8
9
10
11
12
wx.login({
success: function(res) {
const code = res.code;
if (code) {
// this is wechat mini app code for current user
// then request to your own server for openid

} else {

}
}
});

2 - Get openId in your Backend

Use the code and weixin api to get the openid in your backend.

1
GET https://api.weixin.qq.com/sns/jscode2session?appid={your mini APP ID}&secret={your mini app SECRET}&js_code={code here}&grant_type=authorization_code
1
2
3
4
{
"openid": "OPENID",
"session_key": "SESSIONKEY",
}

3 - Latipay Payment Interface

1
2
POST https://api.latipay.net/v2/miniapppay
Content-Type: application/json;charset=UTF-8

API Playground

Name Type Description Optional
user_id String The Latipay user account which is using for processing the transactions. NO
wallet_id String The wallet ID that using for online transactions. NO
amount String A decimal amount. NO
notify_url String Merchant webserver’s URL that the payment result will send to. NO
merchant_reference String A unique id identifying the order in Merchant’s system. NO
product_name String The name of the product or service being sold. NO
app_id String Wechat mini app id NO
open_id String Wechat mini app openid for current wechat user. NO
signature String The SHA-256 HMAC API signature. NO

Example

1
2
3
4
5
6
7
8
9
10
11
12
13
{
"user_id": "U000334333",
"wallet_id": "W00000001",
"amount": "120.00",
"notify_url": "https://merchantsite.com/latipay/notify",
"merchant_reference": "Order898237426347832",
"product_name": "Online Ticket",
"app_id": "wx721398712681232",
"open_id": "obRdo5H-72b_PH2Lvr5_Dw9bXKHs",

"signature":
"8d1bea078eaacdae8388852851ec39e2e8561cdce64f359421d85ed4844496ec"
}

JS code example:

1
2
3
4
5
6
7
8
Object.keys(data)
.filter(
item => data[item] != null && data[item] != undefined && data[item] !== ''
)
.sort()
.map(item => `${item}=${data[item]}`)
.join('&')
.concat(api_key);

Example

1
2
3
4
message: amount=120.00&app_id=wx721398712681232&callback_url=https://merchantsite.com/confirm&ip=122.122.122.1&merchant_reference=dsi39ej430sks03&payment_method=alipay&product_name=Pinot Noir, Otago&return_url=https://merchantsite.com/checkout&user_id=U000334333&version=2.0&wallet_id=W00000001111222333
secret(your api_key): 111222333

signature: 5c732083dbae8b6402bb329a0d1862de2f2337e4bc5b1ee721218fc2c3271db9
1
2
3
4
5
6
7
8
9
10
11
12
{
payment: {
nonceStr: "..",
paySign: "..",
signType: "..",
timeStamp: "..",
packageStr: "..",
},
paydata: {
order_id: '..'
}
}
Name Type Description
nonceStr String for wechat mini app payment
paySign String for wechat mini app payment
signType String for wechat mini app payment, should be ‘MD5’
timeStamp String for wechat mini app payment
packageStr String for wechat mini app payment
order_id String A unique transaction identifier generated by Latipay.

4 - Wechat mini app payment

This is the payment api in wechat document: https://developers.weixin.qq.com/miniprogram/dev/api/api-pay.html

1
2
3
4
5
6
7
8
9
10
11
12
13
14
wx.requestPayment({
nonceStr: payment.nonceStr,
paySign: payment.paySign,
signType: payment.signType,
timeStamp: payment.timeStamp,
package: payment.packageStr, //the key is package

success: function(res) {

},
fail: function(res) {

}
});

Demo

In your wechat mini app:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
//1. login
wx.login({
success: function(res) {
const code = res.code;
if (!code) { ... }

//2. create your own order and reqeust payment to Latipay
wx.request({
url: 'https://yourwebsite/crate_order_and_pay',
method: 'POST',
data: {
code: code,
amount: '1.0',
product_name: 'Ticket',
},
success: function(data) {

//3. make a payment
wx.requestPayment({
...data,
success: function(res) {

});
})
}
})

In your backend:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
server.createPostAPI('/create_order_and_pay', function(req, res){
//1. create your own order and get unique id
const uniqueId = db.createOrder({...})

//2. get openid from wechat
//GET https://api.weixin.qq.com/sns/jscode2session?appid={your mini APP ID}&secret={your mini app SECRET}&js_code={code here}&grant_type=authorization_code
const openId = weixin.api.getOpenId(code)


//3. SHA-256 HMAC signature
const data = {
user_id: 'U000000001',
wallet_id: 'W000000001',
amount: '1.0',
product_name: 'Ticket',
notify_url: 'https://yourwebsite/latipay/notify',

merchant_reference: uniqueId,
open_id: openId
}

const signature = SHA256HMAC(data, apiKey)
data.signature = signature

//4. send request to latipay
api.post(
path: "https://api.latipay.net/v2/miniapppay",
header:{
"Content-Type": "application/json;charset=UTF-8"
},
body: data,
success: function(data){
const latipayId = data.paydata.order_id //recommend to save it for your order.

//5. return to your mini app
const payment = data.payment
res.json({
nonceStr: payment.nonceStr,
paySign: payment.paySign,
signType: payment.signType,
timeStamp: payment.timeStamp,
package: payment.packageStr, //the key is package
})
})
})