Google Pay API for Web 101:基础知识

1. 简介

构建内容

完成此 Codelab 后,您将拥有一个集成了 Google Pay 且可正常运行的最小化可行网站。此项目会检索付款令牌,该令牌可能会发送给付款服务提供商进行处理。

学习内容

  • 如何加载和配置 Google Pay API
  • 如何显示 Google Pay 按钮并处理点击
  • 如何向 Google Pay 请求付款令牌

所需条件

  • 您选择的文本编辑器,用于修改 HTML 和 JavaScript 文件。
  • Google Chrome 网络浏览器,或用于测试本地网站的其他方式。
  • 对于生产环境,您需要 Google Pay merchantId。在 Google Pay & Wallet Console 中注册只需一分钟的时间,不妨现在就完成注册。

使用 Project IDX 跟进

在 IDX 中打开此 Codelab

2. 创建 HTML 页面

创建项目文件

  1. 在计算机上创建一个名为 gpay-web-101 的文件夹,并在该文件夹中创建两个名为 index.htmlmain.js 的空文本文件。您的目录结构应如下所示:
    gpay-web-101/
      index.html
      main.js
    
  2. 在您选择的 IDE 中打开 index.html,然后添加以下代码:
    <!doctype html>
    <html lang="en">
    
    <head>
      <meta charset="UTF-8" />
      <meta name="viewport" content="width=device-width, initial-scale=1.0" />
      <title>Google Pay API for Web 101</title>
    </head>
    
    <body>
      <div id="gpay-container"></div>
      <p>Transaction info and errors will be logged to the console.</p>
      <script type="text/javascript" src="main.js"></script>
      <script
        async src="https://pay.google.com/gp/p/js/pay.js"
        onload="onGooglePayLoaded()">
      </script>
    </body>
    
    </html>
    

代码说明

  1. 系统会向页面添加一个 ID 为 gpay-container 的空 DIV。此 DOM 元素将是添加 Google Pay 按钮的父元素。您可以在网站布局中视需要放置此元素。
  2. main.js 脚本标记位于 DOM 中的 gpay-container 元素之后。这对于确保在 main.js 查询容器 DIV 之前,容器 DIV 已存在于 DOM 中至关重要。此外,该脚本是同步的,以确保在 pay.js 加载之前加载,因为 onGooglePayLoaded() 方法必须在加载完成之前存在。还有其他方法可以实现相同的效果,但我们在此不作讨论。
  3. 最后,系统会异步加载 pay.js,并将 onGooglePayLoaded() 配置为其 onload 处理脚本。此方法将在 main.js 中定义。

3. 配置 Google Pay

Google Pay 付款请求需要包含请求对象。此处定义为 baseGooglePayRequest 的对象包含适用于所有请求的最低常见设置。系统会根据所发出的要求添加其他设置,我们将在此 Codelab 中对此进行介绍。

将 Google Pay 配置常量添加到空的 main.js 文件中:

//=============================================================================
// Configuration
//=============================================================================

// The DOM element that the Google Pay button will be rendered into
const GPAY_BUTTON_CONTAINER_ID = 'gpay-container';

// Update the `merchantId` and `merchantName` properties with your own values.
// Your real info is required when the environment is `PRODUCTION`.
const merchantInfo = {
  merchantId: '12345678901234567890',
  merchantName: 'Example Merchant'
};

// This is the base configuration for all Google Pay payment data requests.
const baseGooglePayRequest = {
  apiVersion: 2,
  apiVersionMinor: 0,
  allowedPaymentMethods: [
    {
      type: 'CARD',
      parameters: {
        allowedAuthMethods: [
          "PAN_ONLY", "CRYPTOGRAM_3DS"
        ],
        allowedCardNetworks: [
          "AMEX", "DISCOVER", "INTERAC", "JCB", "MASTERCARD", "VISA"
        ]
      },
      tokenizationSpecification: {
        type: 'PAYMENT_GATEWAY',
        parameters: {
          gateway: 'example',
          gatewayMerchantId: 'exampleGatewayMerchantId'
        }
      }
    }
  ],
  merchantInfo
};

// Prevent accidental edits to the base configuration. Mutations will be
// handled by cloning the config using deepCopy() and modifying the copy.
Object.freeze(baseGooglePayRequest);

代码说明

  1. 将常量变量 GPAY_BUTTON_CONTAINER_ID 设置为 HTML 页面上用作 Google Pay 按钮的父级容器的 DOM 元素的 ID。
  2. 使用应用的相关设置创建配置对象 baseGooglePayRequest。如需查看每个属性和值,请参阅参考文档。此示例中显示的值可能与您的需求不完全匹配,因此请仔细查看。
  3. 使用您自己的值更新 merchantIdmerchantName 属性。当环境为 TEST 时,这些字段是可选字段。

资源

4. 添加付款客户端

付款客户端用于发出付款请求和注册回调。在此 Codelab 中,我们只会发出付款请求。此外,您还可以配置 PaymentDataCallbacks,以处理付款数据或授权发生变化的情况。不过,本 Codelab 不介绍这些高级主题。

将以下客户端代码附加到 main.js 的底部:

//=============================================================================
// Google Payments client singleton
//=============================================================================

let paymentsClient = null;

function getGooglePaymentsClient() {
  if (paymentsClient === null) {
    paymentsClient = new google.payments.api.PaymentsClient({
      environment: 'TEST',
      merchantInfo,
      // todo: paymentDataCallbacks (codelab pay-web-201)
    });
  }

  return paymentsClient;
}

代码说明

  1. paymentsClient 变量将在实例创建后将其保留给客户端。我们的代码不会直接访问该变量,而是始终通过 getGooglePaymentsClient() 方法访问该变量。
  2. getGooglePaymentsClient() 方法会检查客户端是否已实例化,并返回该实例。如果之前未实例化,则系统会创建、保存并返回一个。此方法可确保在此脚本的整个生命周期内仅创建并使用一个实例。
  3. 如需实例化客户端,请调用 PaymentsClient() 方法。在此示例中,我们告知客户我们位于 TEST 环境中。替代方案是 PRODUCTION。不过,TEST 是默认值,可以省略。

5. 添加帮助程序

以下辅助函数将在脚本的后面部分使用,添加它们的唯一目的是提高代码的可读性和可维护性。

将辅助函数附加到 main.js 的底部:

//=============================================================================
// Helpers
//=============================================================================

const deepCopy = (obj) => JSON.parse(JSON.stringify(obj));

function renderGooglePayButton() {
  const button = getGooglePaymentsClient().createButton({
    onClick: onGooglePaymentButtonClicked
  });

  document.getElementById(GPAY_BUTTON_CONTAINER_ID).appendChild(button);
}

代码说明

  1. deepCopy() 是一个实用程序,用于使用 JSON 序列化和反序列化来创建所提供对象的深层副本。这种方式可以轻松克隆对象,而无需担心共享引用。
  2. renderGooglePayButton() 是一个实用程序,用于调用 createButton() 库方法以显示 Google Pay 按钮。传递的参数是一组选项,用于定义按钮应如何运行,例如注册 onGooglePaymentButtonClicked() 函数来处理按钮点击。

6. 添加事件处理脚本

在此脚本中,我们将配置两个事件处理脚本。第一个方法会在 pay.js 库加载完毕时调用,另一个方法会在用户点击 Google Pay 按钮时调用。

将事件处理脚本附加到 main.js 的底部:

//=============================================================================
// Event Handlers
//=============================================================================

function onGooglePayLoaded() {
  const req = deepCopy(baseGooglePayRequest);

  getGooglePaymentsClient()
    .isReadyToPay(req)
    .then(function(res) {
      if (res.result) {
        renderGooglePayButton();
      } else {
        console.log("Google Pay is not ready for this user.");
      }
    })
    .catch(console.error);
}

function onGooglePaymentButtonClicked() {
  // Create a new request data object for this request
  const req = {
    ...deepCopy(baseGooglePayRequest),
    transactionInfo: {
      countryCode: 'US',
      currencyCode: 'USD',
      totalPriceStatus: 'FINAL',
      totalPrice: (Math.random() * 999 + 1).toFixed(2),
    },
    // todo: callbackIntents (codelab gpay-web-201)
  };

  // Write request object to console for debugging
  console.log(req);

  getGooglePaymentsClient()
    .loadPaymentData(req)
    .then(function (res) {
      // Write response object to console for debugging
      console.log(res);
      // @todo pass payment token to your gateway to process payment
      // @note DO NOT save the payment credentials for future transactions
      paymentToken = res.paymentMethodData.tokenizationData.token;
    })
    .catch(console.error);
}

代码说明

  1. pay.js 脚本根据 HTML 文件中的定义完成加载时,系统会调用 onGooglePayLoaded()。系统会调用 isReadyToPay() 方法来确定是否显示 Google Pay 按钮。如果消费者已准备好付款(即已向 Google 钱包添加付款方式),系统就会呈现 Google Pay 按钮。
  2. 点击 Google Pay 按钮时,系统会调用 onGooglePaymentButtonClicked()。此方法会调用 loadPaymentData() 库方法,该方法用于检索付款令牌。获取付款令牌后,您需要将其发送到付款网关以处理交易。transactionInfo 用于描述应在用户点击此按钮时处理的交易。

7. 总结

恭喜您完成此 Codelab!您已学习如何将 Google Pay API 集成到网站中。

运行项目

使用 Google Chrome 进行测试

使用 Google Chrome 网络浏览器,依次选择 Chrome 主菜单中的 File(文件)> Open File...(打开文件...),打开 index.html。以这种方式打开项目时,Chrome 会执行 main.js。其他网络浏览器可能不允许执行 JavaScript。

– 或 –

使用本地 Web 服务器进行测试

如果您已安装 Python,请在根 pay-web-101 文件夹中的终端提示中运行 python3 -m http.server

$ cd /your/path/to/pay-web-101
$ python3 -m http.server
Serving HTTP on :: port 8000 (http://[::]:8000/) ...

然后,访问 http://localhost:8000 网站。

后续步骤

其他资源