Support international pricing on storefronts

The prices displayed in a storefront can vary based on a customer's location.

This tutorial shows you how to use the Storefront API to query international prices for products and orders, and explicitly set the context of a cart and checkout.

The features described in this tutorial replace the deprecated presentment currencies functionality.

Requirements

To use the GraphQL queries and mutations, your app needs to request the following access scopes for a Shopify store:

  • unauthenticated_read_product_listings
  • unauthenticated_read_customers
  • unauthenticated_write_checkouts

Limitations and considerations

You need to manually enable each country’s currency in a Shopify store's payment settings before you can create a query with different country contexts.

Any queries for countries that aren't enabled will default to the store currency.

How international pricing works

Merchants can configure the prices of products on a per country basis in their Shopify admin. For example, a storefront might have default prices for products set in USD, and price adjustments configured for Canada (CAD), Australia (AUD), and France (EUR).

Diagram showing different prices of the same product based on customer location

Query available countries and currencies

To retrieve a list of available countries and corresponding currencies for a shop, you can query the localization field on QueryRoot. Specify a GraphQL directive called @inContext to get the current country's information.

@inContext directive

A directive provides a way for apps to describe additional options to the GraphQL executor. It lets GraphQL change the result of the query or mutation based on the additional information provided by the directive.

In the Storefront API, the @inContext directive takes an optional country code argument, and applies this directive to the query or mutation.

Example

The following example shows how to retrieve a list of available countries and their corresponding currencies for a shop that's located in France (@inContext(country: FR)).

POST /api/2021-07/graphql.json

View response

JSON response

Query product prices

To retrieve international prices for products, specify the @inContext(country: countryCode) directive in your query.

If you don't include the @inContext directive or provide a country argument that doesn't have custom prices configured, then the prices of products are returned in the default currency that's configured for the storefront.

Example

The following example shows how to query the price of the first product in a storefront within the context of Canada (@inContext(country: CA)). The response returns the price of the product in Canadian dollars.

POST /api/2021-07/graphql.json

View response

JSON response

Query price ranges for products

To query the price ranges for products, include the priceRange and compareAtPriceRange fields in your request.

Within the priceRange field, you can retrieve the lowest variant's price (minVariantPrice) and the highest variant's price (maxVariantPrice). You can also retrieve the compare at price of the product across all variants (compareAtPriceRange).

POST /api/2021-07/graphql.json

View response

JSON response

Query customer orders

Order information is returned in the context that it was created. For example, when an app requests the context of France (@inContext(country: FR)), any previous orders that were created in the United States are returned in USD totals:

POST /api/2021-07/graphql.json

View response

JSON response

Create a checkout

While queries use the @inContext directive to contextualize the response from the server, checkout uses an explicit buyerIdentity argument as an input to the mutation that will be persisted. Context within the checkout is progressive and can change as customers input their address or additional information.

To create a checkout in the context of a specific country, the checkoutCreate mutation takes an optional buyerIdentity.countryCode input argument which sets the checkout’s country field.

When an address is updated on the checkout to include a different country using the checkoutShippingAddressUpdateV2 mutation, the prices that are returned reflect the new country’s prices, or the store's default prices if the new country isn't enabled.

Example

In the following example, the @inContext(country: FR) directive is used so that line item variants are returned in EUR prices.

POST /api/2021-07/graphql.json

View response

JSON response

Create a cart

Similar to a checkout, cart uses an explicit buyerIdentity argument as an input to the mutation that will be persisted.

The @inContext directive contextualizes product variant prices. The country code that's passed into buyerIdentity contextualizes the estimated cost of the cart.

When a cart is created in a country context, the resulting response is in the specified country’s currency:

POST /api/unstable/graphql.json

View response

JSON response

Next steps