Shipping module
Last updated: Jan 15th, 5:00pm
Overview
The PayPal shipping module presents shipping details to a buyer during the PayPal flow. The merchant has several options available for controlling how shipping addresses and shipping options are handled. The server-side shipping callbacks allow you to update the shipping and order amount information as buyers make changes on the PayPal review page.
Merchant and buyer interaction
Buyers can use the shipping module to specify the shipping address and shipping options on the PayPal review page. The system sends a callback to the merchant's URL with the updated shipping information.
When the buyer provides their shipping address, PayPal sends a callback to the merchant server with the buyer's address using the server-side shipping callbacks. In response, the merchant can send PayPal the shipping options and updated order cost amounts.
You can use server-side callbacks to:
- Verify that you support the shipping method.
- Update shipping costs.
- Change line items in the cart.
- Inform the buyer that you do not support their shipping method.
The following sample PayPal review page shows a buyer's shipping address and options:
How it works
The shipping address and options callback process involves the following steps:
- A buyer clicks on the PayPal button displayed on the merchant site.
- The merchant makes a Create Order API request to PayPal to set up the PayPal flow, including the parameters needed to enable the server-side callbacks.
- The buyer is taken to the PayPal flow where they are authenticated and shown the PayPal review page.
- PayPal makes a server-side callback to the merchant's server with the default shipping address from the buyer's PayPal wallet.
- The merchant processes the callback and responds with shipping options for the address and updated order amount.
- PayPal updates the review page to reflect the merchant's revised order amount and shipping options.
- If the buyer changes the shipping address or shipping options, a callback is made to the merchant. The merchant's response updates the PayPal review page.
- The buyer clicks the pay button on the PayPal review page to complete the transaction, which is returned to the merchant.
- The merchant may make a Show Order Details API call to get the final PayPal order information and verify it still matches the information in their system.
- The merchant captures the PayPal order to complete the transaction.
Create order
PayPal uses the PayPal Orders v2 API Create Order request to set up the PayPal flow used by the buyer to approve a PayPal transaction. There are several ways to determine how the shipping address and options are displayed on the PayPal review page and which events create callbacks when the buyer interacts with them.
Enabling server-side callbacks
The payment_source.paypal.experience_context.order_update_callback_config
object is used to enable and configure server-side callbacks during the PayPal flow. The callback_url
field specifies the endpoint on your
servers where PayPal sends the callback request. The callback_events
array specifies which callback events you support. The PayPal flow supports the following events:
SHIPPING_ADDRESS
: This event happens when the PayPal review page loads for the first time and when the buyer changes their shipping address. We recommend merchants to subscribe only toSHIPPING_ADDRESS
. This requires a merchant to respond with all the shipping options and amounts calculated on the initial callback. Since all options have been returned, the merchant callback does not have to be called when the selection option changes. This method reduces delays and the number of requests for PayPal.
SHIPPING_OPTION
: This event happens when the buyer selects new shipping options and when they change shipping options. We recommend merchants subscribe to this if they want to be notified or need to recalculate amounts with their callback URL when a selected shipping option changes for the current address. IfSHIPPING_OPTION
is not needed by the merchant, they should subscribe toSHIPPING_ADDRESS
.
Configuring shipping preferences
The shipping preference is a set using the payment_source.paypal.experience_context.shipping_preference
field. There are 3 possible values:
GET_FROM_FILE
: This default preference retrieves the customer-provided shipping address from PayPal.NO_SHIPPING
: This option removes the shipping address information from the PayPal review page and the API response. However, theshipping.phone_number
andshipping.email_address
fields are returned for digital goods delivery.SET_PROVIDED_ADDRESS
: The PayPal review page shows the shipping address provided by the merchant in the create order request. The buyer cannot change this address on the PayPal site. If the merchant does not pass an address, the buyer can choose the address on PayPal.
If you do not pass a shipping preference, the default behavior is GET_FROM_FILE
. The PayPal review page shows the default shipping address from the buyer's PayPal wallet. The buyer can select a different shipping address from
their wallet or add a new address.
Callbacks happen if the shipping preference is GET_FROM_FILE
.
Passing a shipping address
If you have a shipping address from the buyer, pass it to PayPal on the create order request. If you pass a shipping address with a shipping preference of GET_FROM_FILE
, it will display on the PayPal review page, where the buyer can change the shipping address. You can use the shipping preference SET_PROVIDED_ADDRESS
to prevent the buyer from changing the shipping address on the PayPal review page.
If your transaction does not involve shipping, you can pass the shipping preference SET_PROVIDED_ADDRESS
, and no shipping information will be displayed on the PayPal review page.
Here is a sample Create Order API request to a merchant with callback config:
1curl -v -X POST https://api-m.sandbox.paypal.com/v2/checkout/orders \2-H 'Content-Type: application/json' \3-H 'PayPal-Request-Id: 7b92603e-77ed-4896-8e78-5dea2050476a' \4-H 'Authorization: Bearer 6V7rbVwmlM1gFZKW_8QtzWXqpcwQ6T5vhEGYNJDAAdn3paCgRpdeMdVYmWzgbKSsECednupJ3Zx5Xd-g' \5-d '{6 "intent": "CAPTURE", "payment_source": {7 "paypal": {8 "experience_context": {9 "user_action": "PAY_NOW",10 "shipping_preference": "GET_FROM_FILE",11 "return_url": "https://example.com/returnUrl",12 "cancel_url": "https://example.com/cancelUrl",13 "order_update_callback_config": {14 "callback_events": ["SHIPPING_ADDRESS", "SHIPPING_OPTIONS"],15 "callback_url": "https://example.com/orders?cart_id=h98h98h&session_id=89h788fg8"16 }17 }18 }19 }, "purchase_units": [{20 "reference_id": "d9f80740-38f0-11e8-b467-0ed5f89f718b",21 "items": [{22 "name": "T-Shirt",23 "description": "Super Fresh Shirt",24 "unit_amount": {25 "currency_code": "USD",26 "value": "50.00"27 },28 "quantity": "1",29 "category": "PHYSICAL_GOODS",30 "sku": "sku01",31 "image_url": "https://example.com/static/images/items/1/tshirt_green.jpg",32 "url": "https://example.com/url-to-the-item-being-purchased-1",33 "upc": {34 "type": "UPC-A",35 "code": "123456789012"36 }37 }, {38 "name": "Shoes",39 "description": "Running, Size 10.5",40 "sku": "sku02",41 "unit_amount": {42 "currency_code": "USD",43 "value": "25.00"44 },45 "quantity": "2",46 "category": "PHYSICAL_GOODS",47 "image_url": "https://example.com/static/images/items/1/shoes_running.jpg",48 "url": "https://example.com/url-to-the-item-being-purchased-2",49 "upc": {50 "type": "UPC-A",51 "code": "987654321012"52 }53 }],54 "amount": {55 "currency_code": "USD",56 "value": "100.00",57 "breakdown": {58 "item_total": {59 "currency_code": "USD",60 "value": "100.00"61 }62 }63 }64 }]65 }
Server-side shipping callbacks
The Server-Side Callback API request to a merchant is consistent with GET orders and includes selected addresses and options outside of the order object.
- Sending order data is structurally similar to making a GET request.
- PayPal will send updated shipping addresses and options separately from the order to avoid confusion.
- If the address or option is incomplete, PayPal will not set it in order to prevent misunderstandings.
- PayPal will embed the cart identifier in the callback URL if merchants cannot associate their shopping cart with the order.
- Merchants with client-side shopping carts should include item details when they create the order for server-side shipping callbacks.
Callback request to merchant for shipping address event
The following sample is a PayPal server-side callback request to the merchant for a shipping event. The callback identifies the order, shipping_address
, shipping_option
, and purchase_units
.
1{2 "title": "Shipping Options Callback Request - Shipping Address and Shipping Options Event",3 "description": "The PayPal callback server sends request with a buyer's shipping address, the shipping option the buyer selected, and the purchase_units of the order, to the merchant listener URL. The merchant responds with a the appropriate tax calculation and breakdown for the given address and shipping option combination.",4 "runnable": true,5 "operationId": "server.callback",6 "request": {7 "method": "POST",8 "path": "v2/checkout/orders/order-update-callback",9 "headers": {10 "Content-Type": "application/json"11 },12 "body": {13 "id": "5O190127TN364715T",14 "shipping_address": {15 "country_code": "US",16 "admin_area_1": "TX",17 "admin_area_2": "Dallas",18 "postal_code": "75001"19 },20 "shipping_option": {21 "id": "2",22 "amount": {23 "currencyCode": "USD",24 "value": "20.00"25 },26 "type": "SHIPPING",27 "label": "Free Shipping"28 },29 "purchase_units": [{30 "reference_id": "d9f80740-38f0-11e8-b467-0ed5f89f718b",31 "amount": {32 "currency_code": "USD",33 "value": "100.00"34 }35 }]36 }37 },
Callback request fields
Field |
Description |
Data type |
---|---|---|
|
Unique identifier for the shipping order. For example, |
string |
|
Shipping address information. Includes |
object |
|
Identifies the shipping address country. For example, |
string |
|
Identifies the shipping address state or region. For example, |
string |
|
Identifies the shipping address, city, or municipality. For example, |
string |
|
Identifies the postal code. For example, |
number |
|
Shipping option information. Includes |
string |
|
Indicates the type of shipping option. For example, |
number |
|
Shipping option amount. Includes |
object |
|
Indicates the type of currency. For example, |
string |
|
String denoting the shipping option price, formatted as |
number |
|
An enum that indicates the type of shipping. For example, |
string |
|
Dropdown menu option selected by the buyer. Indicates whether the shipping is free or not. For example, |
string |
|
Defines the purchase unit. Includes |
object |
|
Identifier associated with the purchase units. For example, |
string |
|
Purchase amount. Includes |
object |
|
Indicates the type of currency. For example, |
string |
|
String denoting the purchase price, formatted as |
number |
Merchant response
The merchant response to a PayPal server-side callback request is similar to an order. A change to the customer’s shipping address or options can affect the following fields within the data structure:
purchase_units[].shipping.options
represent the shipping modules associated with the purchase units within the order. The purchase order field includes contact and delivery information, including phone number, PayPal account email address, order ID, and reference ID.purchase_units[].amount
represents the purchase unit amount in the order.
PayPal can handle these changes by taking one of the following approaches:
- Asking the merchant to return an updated order limited to the fields that can be changed.
- Asking the merchant to return a list of patch operations.
Merchant success response
When the order request is acceptable, the merchant responds with a success message that contains amount and shipping option changes.
Here is a sample HTTP 200 OK
callback response from a merchant with shipping options and amount updates.
1{2 "id": "8HFTASDATTV",3 "purchase_units": [{4 "reference_id": "d9f80740-38f0-11e8-b467-0ed5f89f718b",5 "amount": {6 "currency_code": "USD",7 "value": "105.00",8 "breakdown": {9 "item_total": {10 "currency_code": "USD",11 "value": "100.00"12 },13 "tax_total": {14 "currency_code": "USD",15 "value": "5.00"16 },17 "shipping": {18 "currency_code": "USD",19 "value": "0.00"20 }21 }22 },23 "shipping_options": [{24 "id": "1",25 "amount": {26 "currencyCode": "USD",27 "value": "0.00"28 },29 "type": "SHIPPING",30 "label": "Free Shipping",31 "selected": true32 }, {33 "id": "2",34 "amount": {35 "currencyCode": "USD",36 "value": "7.00"37 },38 "type": "SHIPPING",39 "label": "USPS Priority Shipping",40 "selected": false41 }, {42 "id": "3",43 "amount": {44 "currencyCode": "USD",45 "value": "10.00"46 },47 "type": "SHIPPING",48 "label": "1-Day Shipping",49 "selected": false50 }]51 }]52}
Merchant success response fields
A merchant response can include the fields identified in the following table.
Field |
Description |
Date type |
---|---|---|
|
Identifies the merchant. For example, |
string |
|
Purchase unit information. Includes |
object |
|
Uniquely identifies the purchase transaction. For example, |
string |
|
Purchase unit amount in the order. Includes |
object |
|
Code indicating the amount currency type. For example, |
string |
|
String denoting the purchase unit amount in the order, formatted as |
amount |
|
Amount breakdown. Includes |
object |
|
Amount item breakdown. Includes |
object |
|
Amount item total currency type. For example, |
string |
|
Amount item value. For example, |
number |
|
Amount tax breakdown. Includes |
object |
|
Currency type of the amount tax total. For example, |
string |
|
String denoting the |
number |
|
Amount shipping breakdown. Includes |
object |
|
Amount shipping currency type. For example, |
string |
|
String denoting the value. amount, formatted as In this example, there are no shipping costs associated with the purchase unit. |
number |
|
Shipping option details. Includes |
object |
|
Shipping option identifier. For example, |
number |
|
Amount for the selected shipping option. For example, |
object |
|
Type of currency required for the selected shipping option. For example, |
string |
|
String denoting the value. amount for the selected shipping option, formatted as |
number |
|
An enum that indicates the type of delivery for the selected option. For example, |
string |
|
Dropdown menu option selected by the buyer. Indicates the type of |
string |
|
Determines which option is selected by default. Possible values are |
boolean |
The order amount is automatically updated based on the options chosen by the buyers. You can use the onShippingOptionsChange()
callback to update your own database with the new cost amount.
Merchant decline response
A merchant can issue a 422
error to decline a callback event. This could occur when:
- The merchant rejects a shipping address.
- A server-side callback request to a merchant fails or times out.
- The merchant returns a poorly formatted response.
PayPal mechanisms handle these issues, minimizing disruptions throughout the process. Here are a few examples of merchant-declined callback events and associated descriptions:
Callback event type |
Error |
Description |
---|---|---|
Shipping address |
|
Your order can't be shipped to this address. |
Shipping address |
|
Your order can't be shipped to this country. |
Shipping address |
|
Your order can't be shipped to this state. |
Shipping address |
|
Your order can't be shipped to this zip. |
Shipping option |
|
The shipping method you selected is unavailable. To continue, choose another way to get your order. |
Shipping option |
|
Part of your order isn't available at this store. |
Here is a sample decline callback from the merchant. In this case, there is an HTTP 422 Unprocessable Entity
response, which is a country error.
1{2 "name": "UNPROCESSABLE_ENTITY",3 "details": [{4 "issue": "COUNTRY_ERROR"5 }]6}