PayPal Checkout

Capture an Authorization

Note: This guide assumes you have completed a basic Smart Payment Buttons integration.

On the server

  1. Set up your server to make calls to PayPal
  2. Get the authorization ID from your database
  3. Call PayPal to capture the authorization
  4. Save the capture ID to your database
  5. Handle any errors from the call

Note: To install the PayPal JavaScript SDK on your server, see the Set up the Server SDK guide. If you are calling the API directly, you do not need to install the SDK.

// Note: This code is intended as a *pseudocode* example. Each server platform and programming language has a different way of handling requests, making HTTP API calls, and serving responses to the browser.

// 1. Set up your server to make calls to PayPal

// 1a. Add your client ID and secret
PAYPAL_CLIENT = 'PAYPAL_SANDBOX_CLIENT';
PAYPAL_SECRET = 'PAYPAL_SANDBOX_SECRET';

// 1b. Point your server to the PayPal API
PAYPAL_OAUTH_API         = 'https://api.sandbox.paypal.com/v1/oauth2/token/';
PAYPAL_AUTHORIZATION_API = 'https://api.sandbox.paypal.com/v2/payments/authorizations/';

// 1c. Get an access token from the PayPal API
basicAuth = base64encode(`${ PAYPAL_CLIENT }:${ PAYPAL_SECRET }`);
auth = http.post(PAYPAL_OAUTH_API {
  headers: {
    Accept:        `application/json`,
    Authorization: `Basic ${ basicAuth }`
  },
  data: `grant_type=client_credentials`
});

// 2. Get the authorization ID from your database
authorizationID = database.lookupAuthorizationID();

// 3. Call PayPal to capture the authorization
capture = http.post(PAYPAL_AUTHORIZATION_API + authorizationID + '/capture', {
  headers: {
    Accept:        `application/json`,
    Authorization: `Bearer ${ auth.access_token }`
  }
});

// 4. Save the capture ID to your database
if (!capture.error) {
  captureID = capture.purchase_units[0]
    .payments.captures[0].id;
  database.saveCaptureID(captureID);
}

// 5. Handle any errors from the call
if (capture.error) {
  return console.error(capture.error);
}
// 1. Set up your server to make calls to PayPal

// 1a. Import the SDK package
const checkoutNodeJssdk = require('@paypal/checkout-server-sdk');

// 1b. Import the PayPal SDK client that was created in `Set up the Server SDK`.
/**
 *
 * PayPal HTTP client dependency
 */
const payPalClient = require('../Common/payPalClient');

module.exports = async function captureAuthorization() {

  // 2. Get the authorization ID from your database
  const authorizationID = database.lookupAuthorizationID();

  // 3. Call PayPal to capture the authorization
  const request = new checkoutNodeJssdk.payments.AuthorizationsCaptureRequest(authorizationID);
  request.requestBody({});
  try {
    const capture = await payPalClient.client().execute(request);

    // 4. Save the capture ID to your database for future reference.
    const captureID = capture.result.purchase_units[0]
        .payments.captures[0].id;
    //await database.saveCaptureID(captureID);

  } catch (err) {

    // 5. Handle any errors from the call
    console.error(err);
  }
}
<?php
namespace Sample\AuthorizeIntentExamples;

require __DIR__ . '/vendor/autoload.php';
//1. Import the PayPal SDK client that was created in `Set up the Server SDK`.
use Sample\PayPalClient;
use PayPalCheckoutSdk\Payments\AuthorizationsCaptureRequest;

class CaptureAuthorization
{

  // 2. Set up your server to receive a call from the client
  /**
   *Use the following function to capture Authorization.
   *Pass a valid authorization ID as an argument.
   */
  public static function captureAuth($authorizationId, $debug=false)
  {
    $request = new AuthorizationsCaptureRequest($authorizationId);
    $request->body = self::buildRequestBody();
    // 3. Call PayPal to capture an authorization.
    $client = PayPalClient::client();
    $response = $client->execute($request);
    // 4. Save the capture ID to your database for future reference.
    if ($debug)
    {
      print "Status Code: {$response->statusCode}\n";
      print "Status: {$response->result->status}\n";
      print "Capture ID: {$response->result->id}\n";
      print "Links:\n";
      foreach($response->result->links as $link)
      {
        print "\t{$link->rel}: {$link->href}\tCall Type: {$link->method}\n";
      }
      // To toggle printing the whole response body comment/uncomment
      // the follwowing line
      echo json_encode($response->result, JSON_PRETTY_PRINT), "\n";
    }
    return $response;
  }

   /**
   *You can use the following method to build the capture request body.
   *Refer to the Payments API reference for more information.
   */
  public static function buildRequestBody()
  {
    return "{}";
  }
}

/**
 *Driver function for invoking the capture flow.
 */
if (!count(debug_backtrace()))
{
  CaptureAuthorization::captureAuth('REPLACE-WITH-VALID-APPROVED-AUTH-ID', true);
}
?>
# 1. Import the PayPal SDK client that was created in `Set up the Server SDK`.
from sample import PayPalClient
from paypalcheckoutsdk.payments import AuthorizationsCaptureRequest
import json

class CaptureAuthorization(PayPalClient):

  #2. Set up your server to receive a call from the client
  """Use this function to capture an approved authorization.
     Pass a valid authorization ID as an argument to this function."""
  def capture_auth(self, authorization_id, debug=False):
    """Method to capture order using authorization_id"""
    request = AuthorizationsCaptureRequest(authorization_id)
    request.request_body(self.build_request_body())
    # 3. Call PayPal to capture an authorization.
    response = self.client.execute(request)
    # 4. Save the capture ID to your database for future reference.
    if debug:
      print 'Status Code: ', response.status_code
      print 'Status: ', response.result.status
      print 'Capture ID: ', response.result.id
      print 'Links: '
      for link in response.result.links:
        print('\t{}: {}\tCall Type: {}'.format(link.rel, link.href, link.method))
      json_data = self.object_to_json(response.result)
      print "json_data: ", json.dumps(json_data,indent=4)
    return response

  """Sample request body to Capture Authorization."""
  @staticmethod
  def build_request_body():
    return {}


"""This driver function invokes the capture order function with
   a valid authorization ID to capture. Replace the auth_id value with
   a valid authorization ID"""
if __name__ == "__main__":
  auth_id = 'REPLACE-WITH-VALID-APPROVED-AUTH-ID'
  CaptureAuthorization().capture_auth(auth_id, debug=True)
# 1. Import the PayPal SDK client that was created in `Set up the Server SDK`.
require_relative '../paypal_client'
include PayPalCheckoutSdk::Payments
module Samples
  module AuthorizeIntentExamples
    class CaptureAuthorization

      #2. Set up your server to receive a call from the client
      # Use this function to capture on an authorization.
      # Pass a valid authorization ID as an argument.
      def capture_auth (authorization_id, debug=false)
        request = AuthorizationsCaptureRequest::new(authorization_id)
        request.prefer("return=representation")
        # You can update the fields in the following request body
        # as needed. Refer to the Payments API reference for more information.
        request.request_body({})
        begin
          # 3. Call PayPal to capture an authorization.
          response = PayPalClient::client::execute(request)
          # 4. Save the capture ID to your database for future reference.
          if debug
            puts "Status Code: #"
            puts "Status: #"
            puts "Order ID: #"
            puts "Intent: #"
            puts "Links:"
            for link in response.result.links
              # This could also be called link.rel or link.href, but
              # method is a reserved keyword for Ruby. Avoid calling link.method
              puts "\t#{link["rel"]}: #{link["href"]}\tCall Type: #{link["method"]}"
            end
            puts PayPalClient::openstruct_to_hash(response.result).to_json
          end
          return response
        rescue BraintreeHttp::HttpError => ioe
          # Exception occured while processing the refund.
          puts " Status Code: #"
          puts " Debug Id: #"
          puts " Response: #"
        end
      end
    end
  end
end

# This driver function invokes the capture_order function with
# a valid authorization ID. Replace the authorization ID with a valid
# authorization ID.
if __FILE__ == $0
  Samples::AuthorizeIntentExamples::CaptureAuthorization::new::capture_auth('REPLACE-WITH-VALID-APPROVED-AUTH-ID',true)
end
package com.paypal.AuthorizeIntentExamples;

import java.io.IOException;

import org.json.JSONObject;

import com.braintreepayments.http.HttpResponse;
import com.braintreepayments.http.serializer.Json;
import com.paypal.PayPalClient;
import com.paypal.orders.OrderRequest;
import com.paypal.payments.AuthorizationsCaptureRequest;
import com.paypal.payments.Capture;
import com.paypal.payments.LinkDescription;

/*
*
*1. Import the PayPal SDK client that was created in `Set up the Server SDK`.
*This step extends the SDK client. It's not mandatory to extend the client, you can also inject it.
*/
public class CaptureAuthorization extends PayPalClient {

  //2. Set up your server to receive a call from the client
  /**
   *Method to capture order after authorization
   *
   *@param authId Authorization ID from authorizeOrder response
   *@param debug  true = print response data
   *@return HttpResponseCapture response received from API
   *@throws IOException Exceptions from API if any
   */
  public HttpResponseCapture captureAuth(String authId, boolean debug) throws IOException {
    AuthorizationsCaptureRequest request = new AuthorizationsCaptureRequest(authId);
    request.requestBody(buildRequestBody());
    //3. Call PayPal to capture an authorization.
    HttpResponseCapture response = client().execute(request);
    //4. Save the capture ID to your database for future reference.
    if (debug) {
      System.out.println("Status Code: " + response.statusCode());
      System.out.println("Status: " + response.result().status());
      System.out.println("Capture ID: " + response.result().id());
      System.out.println("Links: ");
      for (LinkDescription link : response.result().links()) {
        System.out.println("\t" + link.rel() + ": " + link.href() + "\tCall Type: " + link.method());
      }
      System.out.println("Full response body:");
      System.out.println(new JSONObject(new Json()
              .serialize(response.result())).toString(4));
    }
    return response;
  }

  /**
   *Create an empty body for capture request
   *
   *@return OrderRequest request with empty body
   */
  public OrderRequest buildRequestBody() {
    return new OrderRequest();
  }

  /**
   *This function uses the captureOrder function to
   *capture on authorization. Replace the authorization ID with
   *the valid authorization ID.
   *
   *@param args
   */
  public static void main(String[] args) {
    try {
      new CaptureAuthorization().captureAuth("REPLACE-WITH-VALID-APPROVED-AUTH-ID", true);
    } catch (Exception e) {
      e.printStackTrace();
    }
  }

}
using System;
using System.Collections.Generic;
using System.Threading.Tasks;
//1. Import the PayPal SDK client that was created in `Set up the Server SDK`.
using Samples;
using PayPalCheckoutSdk.Payments;
using BraintreeHttp;

namespace Samples.AuthorizeIntentExamples
{
  public class CaptureAuthorizationSample
  {
    //2. Set up your server to receive a call from the client
    // Use this method to capture the payment on the approved authorization.
    public async static TaskHttpResponse CaptureAuth(string AuthorizationId, bool debug = false)
    {
      var request = new AuthorizationsCaptureRequest(AuthorizationId);
      request.Prefer("return=representation");
      request.RequestBody(new CaptureRequest());
      //3. Call PayPal to capture an authorization.
      var response = await PayPalClient.client().Execute(request);
      //4. Save the capture ID to your database for future reference.
      if (debug)
      {
        var result = response.ResultCapture();
        Console.WriteLine("Status: {0}", result.Status);
        Console.WriteLine("Order Id: {0}", result.Id);
        Console.WriteLine("Links:");
        foreach (LinkDescription link in result.Links)
        {
          Console.WriteLine("\t{0}: {1}\tCall Type: {2}", link.Rel,
                                  link.Href,
                                  link.Method);
        }
        Console.WriteLine("Response JSON: \n {0}",
                    PayPalClient.ObjectToJSONString(result));
      }

      return response;
    }

    static void Main(string[] args)
    {
      string AuthId = "REPLACE-WITH-VALID-APPROVED-AUTH-ID";
      CaptureAuth(AuthId, true).Wait();
    }
  }
}

Read about capturing authorized payments, including sample responses, in the Payments API reference.

The capture request generates a capture response with capture ID that you can use for refunding transactions:

{
  "id": "1HW32023TU4585620"
}

Note: Remember to swap the credentials and API URL from sandbox to production when going live with your integration.

On the client

Next, change the onApprove function on your client. This function should call your server with an authorization ID to capture the funds.

onApprove: function(data, actions.) {
  return actions.order.authorize().then(function(authorization) {
    var authorizationID = authorization.purchase_units[0]
      .payments.authorizations[0].id

    return fetch('/my-server/capture-paypal-transaction', {
      body: JSON.stringify({
        authorizationID: authorizationID
      })
    }).then(function(res) {
      return res.json();
    }).then(function() {
      alert('Authorization captured!');
    });
  });
}

Now your client and server are set up to call the PayPal Orders API to capture an authorization.

Feedback