Logo
Section 1 / 3

设置服务器

查看我们演示应用程序的服务器端实现细节。

导入

设置服务器

查看我们演示应用程序的服务器端实现细节。

在本章中,我们将实现一个名为 水果购买 的演示应用,该应用使用 React 编写。在此应用中,顾客可以挑选多种水果。当他们将水果加入购物车后,即可进行支付操作。我们将通过 Braintree 支付网关来提供支付功能。

对于一个完整应用,我们需要同时具备服务器端和客户端的代码。因此,在本节课中,我们将重点介绍应用的服务器端实现。

服务器端实现

以下是服务器端代码的实现示例。我们建议您先自行阅读代码并尝试理解其逻辑,然后再查看后续的详细说明。

Node

1const express = require('express'); 2const path = require('path'); 3const braintree = require('braintree'); 4 5const gateway = new braintree.BraintreeGateway({ 6 environment: braintree.Environment.Sandbox, 7 merchantId: '<商户ID>', 8 publicKey: '<公钥>', 9 privateKey: '<私钥>' 10}); 11 12const app = express(); 13const port = 3000; 14const DIST_DIR = path.join(__dirname, '../dist'); 15const HTML_FILE = path.join(DIST_DIR, 'index.html'); 16 17app.use(express.static(DIST_DIR)); 18app.use(express.urlencoded({ extended: true })); 19app.use(express.json()); 20 21app.use((req, res, next) => { 22 res.header('Access-Control-Allow-Origin', '*'); 23 res.header('Access-Control-Allow-Headers', 'Origin, X-Requested-With, Content-Type, Accept'); 24 next(); 25}); 26 27app.get('/requestToken', async (req, res) => { 28 try { 29 gateway.clientToken.generate({}, (err, response) => { 30 if (err) { 31 res.status(500).send(err); 32 } else { 33 res.send(response); 34 } 35 }); 36 } catch (err) { 37 res.status(500).send(err); 38 } 39}); 40 41app.post('/payment', async (req, res) => { 42 try { 43 const nonceFromTheClient = req.body.paymentMethodNonce; 44 const price = req.body.price; 45 const id = Math.floor(Math.random() * 1000) + 100; 46 var newTransaction = gateway.transaction.sale( 47 { 48 amount: price, 49 paymentMethodNonce: nonceFromTheClient, 50 orderId: id, 51 options: { 52 submitForSettlement: true, 53 storeInVaultOnSuccess: true 54 } 55 }, (error, result) => { 56 if (result) { 57 res.send(result); 58 } else { 59 res.status(500).send(error); 60 } 61 } 62 ); 63 } catch (err) { 64 console.log(err); 65 res.send(err); 66 } 67}); 68 69app.get('/ping', (req, res) => { 70 res.send('Braintree 后端服务正在运行'); 71}); 72 73app.get('/', (req, res) => { 74 res.sendFile(HTML_FILE); 75}); 76 77app.listen(port, () => { 78 console.log('应用正在监听端口:' + port); 79});

说明

正如我们已经了解的,服务器在完成交易过程中需要执行以下步骤:

  1. 接收来自客户端的客户端令牌请求
  2. 生成客户端令牌
  3. 将客户端令牌发送给客户端
  4. 接收来自客户端的支付方式凭证(nonce)
  5. 将支付方式凭证发送至 Braintree 以创建交易

下面我们结合上述代码片段,逐步解析这一工作流程。

创建 Braintree 网关

在 第5至10行,我们使用 braintree.BraintreeGateway() 方法创建了一个 Braintree 网关。该方法需要以下三个参数:

  1. 商户 ID(Merchant ID)
  2. 公钥(Public Key)
  3. 私钥(Private Key)

生成客户端令牌

在 第27至39行,我们定义了一个 GET 请求处理器,用于接收来自客户端的客户端令牌请求。当客户端发起请求时,服务器立即调用 clientToken.generate() 方法生成客户端令牌(第29至35行)。若生成成功,则将令牌返回给客户端(第33行);若发生错误导致无法生成令牌,则向客户端返回相应的错误信息(第31行)。

创建交易

我们在 第41至67行 定义了一个 POST 请求处理器,用于接收客户端传来的支付信息并创建交易。从客户端接收到以下两个关键数据(第43至44行):

  1. 支付方式凭证(paymentMethodNonce)
  2. 交易金额(price)

此外,创建交易还需要一个额外参数:订单 ID。我们在 第45行 生成了一个随机的订单 ID。收集齐所有必要参数后,我们在 第46至62行 使用 transaction.sale() 方法创建交易。如果交易创建成功,服务器将结果返回给客户端(第57行)。

使用 Braintree 进行交易

设置客户端