Code Cookbook

Save Cards on File

Save cards on file with Reader SDK to create a seamless purchase experience for returning customers and enable recurring payments.

Reader SDK
Customers API
Transactions API
Java (Android)
Android
iOS
Save

Before you start

  • You will need an access token. If you are using OAuth, you will need CUSTOMERS_WRITE permission to save a card on file and PAYMENTS_WRITE permission to process payments with the saved card. Cards on file are automatically updated on a monthly basis to confirm they are still valid and can be charged.
  • You need to have created a Customer object using the Customers API. You can follow The Customers API Setup Guide to create your first Customer object.
  • You need to have installed Reader SDK and configured your Android project.
  • You will need an access token. If you are using OAuth, you will need CUSTOMERS_WRITE permission to save a card on file and PAYMENTS_WRITE permission to process payments with the saved card. Cards on file are automatically updated on a monthly basis to confirm they are still valid and can be charged.
  • You need to have created a Customer object using the Customers API. You can follow The Customers API Setup Guide to create your first Customer object.
  • You need to have installed Reader SDK and configured your iOS project.
  • You will need an access token. If you are using OAuth, you will need CUSTOMERS_WRITE permission to save a card on file and PAYMENTS_WRITE permission to process payments with the saved card. Cards on file are automatically updated on a monthly basis to confirm they are still valid and can be charged.
  • You need to have created a Customer object using the Customers API. You can follow The Customers API Setup Guide to create your first Customer object.

Step 1: Collect the card information

Use the Reader SDK card on file workflow to create a customer card for an existing Customer object. The card on file workflow is a sequence of screens used by the customer to specify that they wish to save their card information for future purchases.

The card on file workflow begins with an asynchronous call to Square servers, which could be slow depending on network conditions.

We recommend displaying a spinner or loading indicator before starting the card on file workflow and clearing it when you receive the result (success or failure) so users know that work is being done in the background.

Use the Reader SDK card on file workflow to create a customer card for an existing Customer object. The card on file workflow is a sequence of screens used by the customer to specify that they wish to save their card information for future purchases.

The card on file workflow begins with an asynchronous call to Square servers, which could be slow depending on network conditions.

We recommend displaying a spinner or loading indicator before starting the card on file workflow and clearing it when you receive the result (success or failure) so users know that work is being done in the background.

Step 1.1: Create a customer card manager

The customer card manager lets you collect and store card information securely. Use the CustomerCardManager class to create a new information manager:

import com.squareup.sdk.reader.ReaderSdk;
import com.squareup.sdk.reader.crm.CustomerCardManager;

CustomerCardManager customerCardManager =
    ReaderSdk.customerCardManager();

Step 1.2: Write a callback to handle the result

Customer card information is stored on Square servers, not on the device running Reader SDK, so you need to implement a callback to handle the response from Square:

import com.squareup.sdk.reader.core.CallbackReference;

CallbackReference storeCardCallbackRef = customerCardManager.addStoreCardActivityCallback(result -> {
 hideLoadingIndicatorOnYourActivity();
 if (result.isSuccess()) {
   showStoreCardSuccessDialog(result.getSuccessValue());
 } else {
   showErrorDialog(result.getError());
 }
});

Implement the StoreCustomerCardControllerDelegate methods:

import SquareReaderSDK

extension <#YourViewController#>: SQRDStoreCustomerCardControllerDelegate {

    func storeCustomerCardController(_ storeCustomerCardController: SQRDStoreCustomerCardController, didFailWith error: Error) {
        hideLoadingView()

        // Show error message to user
    }

    func storeCustomerCardController(_ storeCustomerCardController: SQRDStoreCustomerCardController, didFinishWith card: SQRDCard) {
        hideLoadingView()

        // Indicate to user that card was linked
    }

    func storeCustomerCardControllerDidCancel(_ storeCustomerCardController: SQRDStoreCustomerCardController) {
        hideLoadingView()

        // Return to previous UI state
    }
}

Follow the steps in the Payment Form build guide or In-App Payments SDK to generate a valid card nonce.

Step 2: Save the customer card on file

Use the customer card manager to start the StoreCard activity and link the card to an existing customer ID:

showLoadingIndicatorOnYourActivity();
customerCardManager.startStoreCardActivity(activity, customerId));

Use the Customers API to send the card nonce and the customer ID to the CreateCustomerCard endpoint. It will return a customer card ID in the response field (customer_card_id).

$cardNonce = "{NONCE_FROM_STEP_1}";
$customerId = "{YOUR_CUSTOMER_ID}";  // Replace with an existing customer_id

// Create a CustomerCard request object
$body = new \SquareConnect\Model\CreateCustomerCardRequest();

// Set the card nonce value for your request object.
$body->setCardNonce($cardNonce);

// Send the request to the CreateCustomerCard endpoint

try {
  $result = $customersApi->createCustomerCard($customerId, $body);
  print_r($result);
} catch (Exception $e) {
  echo 'Error when calling createCustomerCard: ', $e->getMessage(), PHP_EOL;
}

Use the Customers API to send the card nonce and the customer ID to the CreateCustomerCard endpoint. It will return a customer card in the response field (customer_card).

access_token = '{A VALID SQUARE ACCESS TOKEN}'
card_nonce = '{NONCE_FROM_STEP_1}'
customer_id = '{YOUR_CUSTOMER_ID}'

# Create a CustomerCard request object
customer_card_api = SquareConnect::CustomerCardApi.new
customer_card_request = {
  card_nonce: card_nonce,
  billing_address: {
    address_line_1: '1455 Market St',
    address_line_2: 'Suite 600',
    locality: 'San Francisco',
    administrative_district_level_1: 'CA',
    postal_code: '94103',
    country: 'US'
  },
  cardholder_name: 'Amelia Earhart'
}

begin
  # Send the request to the CreateCustomerCard endpoint
  customer_card_response = customer_card_api.create_customer_card(
    access_token, customer_id, customer_card_request
  )
  puts 'CustomerCard ID to use with Charge:'
  puts customer_card_response.customer_card.id
rescue SquareConnect::ApiError => e
  raise "Error encountered while creating customer card: #{e.message}"
end

customer_card = customer_card_response.customer_card

Add code to start the store customer card flow:

import SquareReaderSDK

extension <#YourViewController#> {
    func storeCardOnFile() {
        showLoadingView()
        let cardOnFileController = SQRDStoreCustomerCardController(customerID: customerID, delegate: self)
        cardOnFileController.present(from: self)
    }
}

Contact Developer Support, join our Slack channel, or ask for help on Stack Overflow