웹용 Google Pay API 101: 기본사항

1. 소개

빌드할 항목

이 Codelab을 완료하면 작동하는 Google Pay 통합이 포함된 최소한의 실행 가능한 웹사이트가 생성됩니다. 이 프로젝트는 결제 서비스 제공업체에 전송되어 처리될 수 있는 결제 토큰을 가져옵니다.

학습할 내용

  • Google Pay API를 로드하고 구성하는 방법
  • Google Pay 버튼을 표시하고 클릭을 처리하는 방법
  • Google Pay에서 결제 토큰을 요청하는 방법

필요한 항목

  • HTML 및 JavaScript 파일을 수정할 텍스트 편집기
  • Chrome 웹브라우저 또는 로컬 웹사이트를 테스트하는 다른 방법
  • 프로덕션의 경우 Google Pay merchantId가 필요합니다. Google Pay 및 월렛 콘솔에 등록하는 데 1분밖에 걸리지 않으므로 지금 등록하는 것이 좋습니다.

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. 빈 DIV가 ID가 gpay-container인 페이지에 추가됩니다. 이 DOM 요소는 Google Pay 버튼이 추가되는 상위 요소가 됩니다. 이 요소는 적절한 위치에 웹사이트 레이아웃에 배치할 수 있습니다.
  2. main.js 스크립트 태그는 DOM에서 gpay-container 요소 뒤에 배치됩니다. 이는 main.js에서 컨테이너 DIV를 쿼리하기 전에 DOM에 컨테이너 DIV가 있는지 확인하는 데 필요합니다. 또한 로드가 완료되기 전에 onGooglePayLoaded() 메서드가 있어야 하므로 pay.js가 로드되기 전에 로드되도록 스크립트는 동기식입니다. 동일한 효과를 얻는 다른 방법도 있지만 여기서는 다루지 않습니다.
  3. 마지막으로 pay.js가 비동기식으로 로드되고 onGooglePayLoaded()onload 핸들러로 구성합니다. 이 메서드는 main.js에서 정의됩니다.

3. Google Pay 구성

Google Pay 결제 요청에는 요청 객체가 필요합니다. 여기에서 baseGooglePayRequest로 정의된 객체에는 모든 요청에 대한 최소 공통 설정이 포함되어 있습니다. 요청에 따라 추가 설정이 추가되며 이 Codelab에서 검토할 예정입니다.

main.js 파일에 Google Pay 구성 상수를 추가합니다.

//=============================================================================
// 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. onGooglePayLoaded()는 HTML 파일에 정의된 대로 pay.js 스크립트의 로드가 완료되면 호출됩니다. isReadyToPay() 메서드는 Google Pay 버튼을 표시할지 여부를 결정하기 위해 호출됩니다. 소비자가 결제할 준비가 되면 (즉, Google 월렛에 결제 수단을 추가한 경우) Google Pay 버튼이 렌더링됩니다.
  2. onGooglePaymentButtonClicked()는 Google Pay 버튼을 클릭할 때 호출됩니다. 이 메서드는 결제 토큰을 검색하는 데 사용되는 loadPaymentData() 라이브러리 메서드를 호출합니다. 결제 토큰을 받으면 거래를 처리하기 위해 결제 게이트웨이로 전송합니다. transactionInfo는 이 버튼 클릭으로 처리해야 하는 트랜잭션을 설명합니다.

7. 결론

이 Codelab을 완료했습니다. Google Pay API를 웹사이트에 통합하는 방법을 알아봤습니다.

프로젝트 실행

Chrome으로 테스트

Google Chrome 웹브라우저를 사용하여 Chrome의 기본 메뉴에서 파일 > 파일 열기...를 사용하여 index.html를 엽니다. 이 방법으로 프로젝트를 열면 Chrome에서 main.js를 실행합니다. 다른 웹브라우저에서는 JavaScript 실행을 허용하지 않을 수 있습니다.

– 또는 –

로컬 웹 서버로 테스트

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에서 사이트를 방문합니다.

다음 단계

추가 리소스