preface
Since I was in the transaction payment department of the company, I was basically in charge of the front-end payment page of the To C end
Generally speaking, a normal transaction process, the user will go through several stages:
- Browse the list
- Viewing product details
- Click to buy or add to cart
- Commodity settlement (confirmation of purchase)
- Cashier (to make payment)
- Pay for success
The cashier desk as the last kilometer of successful transactions, its heavy responsibility can be imagined
Let’s take a look at the checkout counters of common websites on the market:
Bilibili Member Purchase:
The touch screen end
PC
The app end
For class network:
The touch screen end
PC
The app end
It can be seen that the cashier page generally ADAPTS to three terminals: PC, touch screen and APP. Therefore, mainstream third-party payment platforms (wechat, Alipay, Huabei Instalment, JINGdong Baitiao) also need to support payment in these three scenarios
Next, we will analyze the realization of different payment channels in different terminals
As payment involves the core business of the department, we will not take the company’s online cashier to explain. Payment interaction process, mainly referring to Bilibili membership purchase and MOOC (no interest related)
Note: This paper only considers the implementation of front-end payment business and back-end payment business, not for the time being. If you are interested, please refer to the Evolution history of Payment Channel Routing System.
Alipay (Huabei Instalment)
Alipay development documents
Spend bai installment is pay treasure to expand actually, principle is basically consistent, do not repeat cumbersome
PC
Interaction Mode 1:
Click Alipay on the PC, and a new page (window.open()) opens, which points to the official cashier page of Alipay
Interaction Mode 2:
Click alipay to pay on the PC, and a TWO-DIMENSIONAL code is displayed on the web page. Users need to open the Alipay app to scan the code for payment
B station provides a very clever idea: wechat, Alipay, QQ three payment TWO-DIMENSIONAL code unified into a two-dimensional code. (The principle will be explained later. The essence is to call JSAPI of different containers.)
In both modes of interaction, when you click the pay button, you actually send the current order number and some relevant information to the backend
const payNum = '123abc';
ajax({
url: '/api/alipay'./ / API
type: 'POST'.data: {
payNum: payNum, / / order number
other: 'demo'.// Other parameters
}).then((res) = > {
const { payUrl } = res;
// Interactive method 1:
// payUrl if it is the cashier of Alipay, a new page will be opened
/ / payUrl generally is https://mapi.alipay.com/gateway.do this, usually take return_url parameters and various other data, finally be redirected to pay treasure to the register page
window.open(payUrl);
// Interaction mode 2:
// payUrl If it is the scan code address of Alipay, then create a two-dimensional code popup window
/ / payUrl generally is https://qr.alipay.com/bax06893swswc4inaknv505d this, the last page is redirected to the pay treasure to the cashier, the cashier can arouse the alipay app
qrcode({
width: 175.height: 175.url: payUrl
});
}).catch((err) = > {
console.log('Commit failed')})Copy the code
As the payment is asynchronous, the front end needs to check whether the order is successfully paid
As for interaction mode 1, since the payment page has been transferred to the cashier desk of Alipay, the cashier desk of Alipay will automatically jump back to the return_URL after the payment at the cashier desk of Alipay is successful (Return_URL is the parameter we brought when we jumped to the cashier desk of Alipay at the beginning, which generally points to the payment success page).
However, since we use the new page opened by window.open, when the user comes back to our cashier, we need to open a pop-up box and actively ask the user whether the payment has been successful. If the user clicks “Complete payment”, we need to query whether the order has been paid successfully.
// Open the alipay cashier
window.open(payUrl);
// Open a popup window in the current page and ask the user whether the payment is successful
createFinishWindow()
Copy the code
As for interaction mode 2, the payment is still carried out by scanning code on the current page, so after the two-dimensional code pop-up window is created, we immediately need to poll to query the order status
const payNum = '123abc'
// Create a qr code popover
qrcode({
width: 175.height: 175.url: payUrl
});
// Query order status
function getPayStatus() {
ajax({
url: '/api/getPayStatus'.// Payment status API
data: {
payNum: payNum, / / order number
other: 'demo'.// Other parameters
},
type: 'POST'
).then((res) = > {
if (res.payStatus === 0) {
// Pay successfully, jump to success page
window.location.href = `/success/${payNum}`;
clearTimeout(statusTimeId);
} else {
// Not paid, continue polling
statusTimeId = setTimeout(getPayStatus, 3000);
}
}).catch((err) = > {
// The interface reported an error and continued polling
statusTimeId = setTimeout(getPayStatus, 3000); })}let statusTimeId = setTimeout(getPayStatus, 3000);
Copy the code
The touch screen end
Interaction mode:
Click alipay to pay on the touch screen, and the page will directly jump to the Alipay cashier. The page will try to evoke the Alipay app on the phone
In fact, on the touch side, the principle is basically the same as on the PC side, except that on the touch side, you may need to create a form instead of jumping directly to the link (of course, it depends on the implementation of the back end).
const payNum = '123abc';
// Simulate form submission
function formSubmit(formData, url) {
const form = $('<form method="post" target="_self"></form>');
form.attr('action', url);
let input;
$.each(formData, function (i, v) {
input = $('<input type="hidden">');
input.attr("name", i);
input.attr("value", v);
form.append(input);
});
$(document.body).append(form);
form.submit();
form.remove();
}
ajax({
url: '/api/alipay'./ / API
type: 'POST'.data: {
payNum: payNum, / / order number
other: 'demo'.// Other parameters
}).then((res) = > {
const { formData, url } = res;
if (formData) {
// The front-end needs to build the form itself
formSubmit(formData, url)
} else {
// Direct jump link (the form is already assembled on the back end)
window.location.href = url;
}
}).catch((err) = > {
console.log('Commit failed')})Copy the code
After the payment is successful, alipay will redirect to the return_url address in the same way
Note: Alipay cannot be invoked in the wechat browser (daily ban)
Solutions:
Method 1: wechat environment hidden alipay entrance
Method 2: In the wechat environment, click alipay to pay and guide the user to open the page using other browsers
JSAPI
If we can induce users to use the Alipay client to scan to open the cashier page on our touch screen, we can also use the JSAPI provided by Alipay to awaken the cashier
This is also the principle of B station wechat, Alipay, QQ can pay with the same TWO-DIMENSIONAL code, these three clients have provided their ownJSAPI
, users with different clients scan code, will enter the same page (b station implementation), this transfer page according to the container environment, call differentJSAPI
Payment function of
Alipay H5 open document
For more information about JsBridge, check out my previous article jsBridge Primer
A simple example of JSAPI
function ready(callback) {
// If jsBridge has already been injected, it is called directly
if (window.AlipayJSBridge) {
callback && callback();
} else {
// Listen for injected events if there is no injection
document.addEventListener('AlipayJSBridgeReady', callback, false);
}
}
ready(function () {
// Displays a prompt box
AlipayJSBridge.call('toast', {
content: 'hello'
});
});
Copy the code
Arouse the cashier need to use Alipay JSSDK
<script src="https://gw.alipayobjects.com/as/g/h5-lib/alipayjsapi/3.1.1/alipayjsapi.inc.min.js"></script>
<button id="J_btn" class="btn btn-default">pay</button>
<script>
var btn = document.querySelector('#J_btn');
btn.addEventListener('click'.function(){
ap.tradePay({
tradeNO: '201802282100100427058809844'
}, function(res){
ap.alert(res.resultCode);
});
});
</script>
Copy the code
The app end
At present, most apps are Hybrid apps. If your cashier page is not native to the app, you can directly use WebView to load the touch-screen online cashier
Mobile website payment products are not recommended to be used on the APP end
This is recommended by the official website of Alipay. Therefore, if you want to get the best payment experience, you are advised to access the SDK of Alipay for the development of the client. Of course, this part is beyond the scope of the front-end
However, generally in the APP side, we still use WebView to load the front-end page of the touch screen side, but in the APP, our front-end code, through JsBridge, can call the payment method of the client side
const payNum = '123abc';
// Pay the callback function
window.ali_pay_callback = function(res) {
if (res.status === 0) {
// The payment was successful
} else {
// Payment failed}}// APPSDK is a webView injected global object that can call native methods
APPSDK.invoke('ali_pay', {
payNum: payNum, / / order number
other: 'demo'.// Other parameters
}, 'ali_pay_callback');
Copy the code
Small program
The applet invokes the payment document
The payment process of mini program payment and APP payment is basically consistent with the experience, and the Alipay cashier can be aroused on the current page
const payNum = '123abc';
my.request({
url: 'https://demo.com/api/alipay'.// httpRequest domain whitelist must be added
method: 'POST'.data: { // The key and value in data are defined by the developer
from: Alipay.payNum: payNum, / / order number
other: 'demo'.// Other parameters
},
dataType: 'json'.success: function(res) {
// Call up the cashier
my.tradePay({
// Call the unified transaction creation interface (Alipay.trade.create) to get the return field Alipay transaction number trade_no
tradeNO: res.tradeNO,
success: (res) = > {
my.alert({
content: JSON.stringify(res),
});
},
fail: (res) = > {
my.alert({
content: JSON.stringify(res), }); }}); },fail: function(res) {
my.alert({content: 'fail'});
},
complete: function(res) {
my.hideLoading();
my.alert({content: 'complete'}); }});Copy the code
Summary of Alipay payment
We have learned the basic principle of Alipay payment from PC, touch screen and APP. It can be seen that the front-end implementation of payment is not complicated, but the real difficulty lies in the implementation of back-end payment system. As for the most difficult problem of Alipay arousal, in fact, alipay cashier itself has already realized the arousal function, so we do not need to achieve it
Wechat Pay development document
PC
Scan the payment document
Interaction mode:
Wechat does not provide an official cashier on the PC side like Alipay, so when we click wechat Pay, the TWO-DIMENSIONAL code popup will pop up directly, asking the user to scan the code for payment, and the user can directly evoke wechat Pay by scanning the code. When the QR code pops up, we need to poll and query the payment status immediately.
const payNum = '123abc';
ajax({
url: '/api/weixinpay'./ / API
type: 'POST'.data: {
payNum: payNum, / / order number
other: 'demo'.// Other parameters
}).then((res) = > {
const { qrUrl } = res;
//wxpay/bizpayurl? Pr =P1oi4x6, this schema can be scanned through wechat to evoke wechat payment
qrcode({
width: 175.height: 175.url: qrUrl
});
// Start polling for payment results
// Code omission, can refer to the previous Alipay PC implementation
}).catch((err) = > {
console.log('Commit failed')})Copy the code
The touch screen end
H5 Payment document
Interaction mode:
Click wechat Pay on the touch screen, and the page will jump directly to the middle page of wechat Pay, which will try to evoke wechat Pay
Different from the cashier desk of Alipay, the middle page of wechat Pay will automatically jump back to redirect_URL for more than 5 seconds after the cashier desk of wechat is set up. Therefore, it is impossible to guarantee that the payment process has finished when the page hops back. Therefore, the redirect_URL address set by merchants cannot automatically perform the order checking operation, and users should click the button to trigger the order checking operation
// Code omission, basically the same as alipay's touch screen
// wechat payment transfer page is usually a URL address in this format
// https://wx.tenpay.com/cgi-bin/mmpayweb-bin/checkmweb?prepay_id=wx111408048537349a5434e53d1930739300&package=1982317760&r edirect_url=https://m.imooc.com/myorder
Copy the code
Note: The wechat Payment transfer page generally cannot be accessed directly by the browser, because the transfer page needs to determine whether the referer is the authorized domain name submitted by the merchant when applying for H5. If you access it directly from your browser, the referer is empty, so the page will not load successfully. If you set up H5 payment in the APP, you need to manually set the referer in the WebView
Another trick is that we can call up the payment on the current page without using the Wechat transfer page
// The backend returns a schema directly
const schema = `weixin://wap/pay? appid%3Dwxd6841de60b02faef%26noncestr%3D095525b24fc94111a3663068c8dc8a90%26package%3DWAP%26prepayid%3Dwx091027118037832f 961440d31092022500%26sign%3D2CF5A14607C6AAEDE382758CA87B973F%26timestamp%3D1591669631`
// Mobile phone can evoke wechat payment
window.location.href = schema;
Copy the code
However, in this method, schema is easy to be intercepted by the webveiw of the third-party app, so that the payment fails to be invoked. For example, if you use this method to visit the cash register on Weibo, wechat will fail. Therefore, it is recommended to use the wechat transfer page, by the transfer page to evoke wechat more insurance. Of course, no matter what method is used in Alipay, wechat payment cannot be carried out (love and kill).
JSAPI
If our cashier page is opened in the wechat browser, then we can use the JSAPI provided by wechat to invoke payment
JSAPI payment is also called public account payment
JSAPI payment documentation
const payNum = '123abc';
function onBridgeReady(wxJsApiParam) {
window.WeixinJSBridge.invoke(
'getBrandWCPayRequest',
wxJsApiParam,/ / josn string
function (res) {
if (res.err_msg == "get_brand_wcpay_request:ok") {
// The payment was successful
location.href = `/success/${payNum}`;
} else if (res.err_msg == "get_brand_wcpay_request:fail") {
// Payment failed}}); }function weixinPay(wxJsApiParam) {
if (typeof WeixinJSBridge == "undefined") {
if (document.addEventListener) {
document.addEventListener('WeixinJSBridgeReady'.function () { onBridgeReady(wxJsApiParam) }, false);
} else if (document.attachEvent) {
document.attachEvent('WeixinJSBridgeReady'.function () { onBridgeReady(wxJsApiParam) });
document.attachEvent('onWeixinJSBridgeReady'.function () { onBridgeReady(wxJsApiParam) }); }}else {
onBridgeReady(wxJsApiParam);
}
}
ajax({
url: '/api/weixin_jsapi'./ / API
type: 'POST'.data: {
payNum: payNum, / / order number
other: 'demo'.// Other parameters
}).then((res) = > {
const { jsapiData } = res;
// jsapiData is a json string containing various data such as appId, paySign, etc. used to initiate wechat payment
weixinPay(JSON.parse(jsapiData));
}).catch((err) = > {
console.log('Commit failed')})Copy the code
To use JSAPI, we need to have a wechat public platform, because we need to set the parameter OpenID on the public platform to obtain the domain name of OpenID
In addition to using the built-in WeixinJSBridge object of wechat browser, we can also use JSSDK
<script src="http://res.wx.qq.com/open/js/jweixin-1.6.0.js"></script>
<script>
wx.chooseWXPay({
timestamp: 0.nonceStr: ' '.package: ' '.signType: ' '.paySign: ' '.success: function (res) {
// Callback function after successful payment}});</script>
Copy the code
2020.11.15 update
Because WeChat launched a so-called golden point plan “, so if your JSAPI back-end docking is not WeChat direct channel, but the third party payment channel (for example, yeepay payment), then pay after the success, not the callback function, but direct access to the official receipts WeChat page (depending on your service providers have plans to open some gold for you, If not, close the payment page directly)
For more details, please refer to “Wechat Gold Point Plan Merchants’ Receipt Docking Pit Record”.
The app end
APP Payment document
H5 Payment is not recommended to be used in the APP. If you need to use wechat Payment in the APP, please answer the APP Payment
Wechat official documents also do not recommend using touch screen payment method on the APP side, so it is better to access wechat SDK. The front end can also use JsBridge to call the wechat payment method of the client. You can refer to alipay’s app-side method above.
Small program
Applet payment document
In fact, small program payment is very similar to wechat JSAPI payment. Both need to obtain Openid first and call the same API
wx.requestPayment({
timeStamp: ' '.nonceStr: ' '.package: ' '.signType: 'MD5'.paySign: ' ',
success (res) { },
fail (res) { }
})
Copy the code
Wechat Pay summary
The process of JSAPI and mini program of wechat Payment is more complicated, because it involves obtaining a series of permissions such as access_token openID of public account. But in general, the complexity is mostly on the back end.
Other third-party payments
In addition to mainstream wechat Payment and Alipay payment, we may also need to connect with some other third-party payment platforms, such as QQ, PayPal, UnionPay, JINGdong Paitiao, major banks, etc. Of course, the principles are similar.
At the same time, we can also use third-party aggregative payment platforms, such as Duxiaoman Payment, which have integrated the payment functions of credit cards and memory cards of major banks. We can easily access SDK to save development costs.
conclusion
Web payment due to the high requirements of development conditions (at least to have a registered company), so most students do not have a lot of daily work contact. Of course, this article is just a review of the daily development, the front end of web payment in some common ways.
In the real project, we will still face many problems and difficulties, then we need to see the move.
reference
- Alipay payment and wechat payment in Web development
- Wechat Payment documents
- Alipay documents
expand
A reader mentioned the Payment Request API, a native Payment API provided by the W3C.
The Payment Request API is a system designed to eliminate checkout forms. It significantly improves user workflow during the shopping process, provides a more consistent experience for users, and enables e-commerce companies to easily leverage a wide range of completely different payment methods.
This API invokes the browser’s own checkout and payment page (native UI)
However, PaymentRequest only supports the following standard credit cards in Chrome: AMEX, Diners, Discover, JCB, Maestro, mastercard, UnionPay and Visa. So this API, at least domestically, is not really practical.
If you are interested, check out the detailed tutorial Payment Request API: Integration Guide.