# Adaptive Pricing Let customers pay in their local currency with Adaptive Pricing. # Stripe-hosted page > This is a Stripe-hosted page for when payment-ui is stripe-hosted. View the full page at https://docs.stripe.com/payments/currencies/localize-prices/adaptive-pricing?payment-ui=stripe-hosted. Adaptive Pricing lets your customers pay in their local currency in more than [150 countries](https://docs.stripe.com/payments/currencies/localize-prices/adaptive-pricing.md#supported-currencies). With Adaptive Pricing, Stripe uses machine learning to determine the most relevant presentment currency, then automatically calculates the localized price and handles all currency conversion. Use Adaptive Pricing to: - Display pricing in local currencies based on location - Calculate prices in real time using an exchange rate guaranteed for 24 hours - Unlock payment methods that require local currency - Facilitate compliance when presenting supported currencies #### Integration effort Complexity: 1/5 #### Fees View information on [fees and our FAQ](https://support.stripe.com/questions/adaptive-pricing). ## Enable Adaptive Pricing in the Dashboard [Dashboard] Adaptive Pricing is always enabled for Payment Links. Manage Adaptive Pricing for Checkout in your [payment settings](https://dashboard.stripe.com/settings/adaptive-pricing) in the Dashboard. You can enable Adaptive Pricing in a sandbox and live mode. Disabling Adaptive Pricing doesn’t affect Checkout Sessions that have already been converted. ## Configure local payment methods [Dashboard] Adaptive Pricing can increase the usage of local payment methods by ensuring customers have the option to pay in their local currency and with payment methods most relevant to them. As an example, 70% of all e-commerce transactions in the Netherlands use iDEAL, but it only works with EUR. You can configure which payment methods you accept in your [payment methods settings](https://dashboard.stripe.com/settings/payment_methods) if you use dynamic payment methods. Adaptive Pricing provides access to the following payment methods that require presenting in local currency: - Amazon Pay - Bancontact - BLIK - EPS - iDEAL - Link - P24 - Pix - South Korean cards - Naver Pay - Kakao Pay - PAYCO - Revolut Pay - Samsung Pay - Wechat Pay ## Event destinations and reporting [Server-side] The Checkout Session and the underlying `PaymentIntent` objects reflect what your customer paid in your integration currency and amount, which is the currency you specified for your prices. If a customer pays in their local currency, the [checkout.session.completed](https://docs.stripe.com/api/events/types.md#event_types-checkout.session.completed) and [payment_intent.succeeded](https://docs.stripe.com/api/events/types.md#event_types-payment_intent.succeeded) event contains a `presentment_details` hash that includes the `presentment_amount` and `presentment_currency`. #### JSON ```json { "id": "{{EVENT_ID}}", "object": "event", "type": "checkout.session.completed", "data": { "object": { "id": "{{SESSION_ID}}", "object": "checkout.session", "currency": "usd", "amount_total": 1000, "amount_subtotal": 1000,"presentment_details": { "presentment_amount": 1370, "presentment_currency": "cad" } } } } ``` ## Testing To test local currency presentment for Checkout and Payment Links, pass in a location-formatted customer email that includes a suffix in a `+location_XX` format in the local part of the email. `XX` must be a valid [two-letter ISO country code](https://www.nationsonline.org/oneworld/country_code_list.htm). For example, to test currency presentment for a customer in France, pass in an email like `test+location_FR@example.com`. When you visit the URL for a Checkout Session or Payment Link created with a location-formatted email, you see the same currency as a customer does in the specified country. ### Testing Checkout When you create a Checkout Session, pass the location-formatted email as [customer_email](https://docs.stripe.com/api/checkout/sessions/object.md#checkout_session_object-customer_email) to simulate Checkout from a particular country. ```cli stripe checkout sessions create \ -d "line_items[0][price]"={{PRICE_ID}} \ -d "line_items[0][quantity]"=1 \ --mode=payment \ --success-url="https://example.com/success" \ --customer-email="test+location_FR@example.com" ``` ```ruby # Set your secret key. Remember to switch to your live secret key in production. # See your keys here: https://dashboard.stripe.com/apikeys client = Stripe::StripeClient.new("<>") session = client.v1.checkout.sessions.create({ line_items: [ { price: '{{PRICE_ID}}', quantity: 1, }, ], mode: 'payment', success_url: 'https://example.com/success', customer_email: 'test+location_FR@example.com', }) ``` ```python # Set your secret key. Remember to switch to your live secret key in production. # See your keys here: https://dashboard.stripe.com/apikeys client = StripeClient("<>") # For SDK versions 12.4.0 or lower, remove '.v1' from the following line. session = client.v1.checkout.sessions.create({ "line_items": [{"price": "{{PRICE_ID}}", "quantity": 1}], "mode": "payment", "success_url": "https://example.com/success", "customer_email": "test+location_FR@example.com", }) ``` ```php // Set your secret key. Remember to switch to your live secret key in production. // See your keys here: https://dashboard.stripe.com/apikeys $stripe = new \Stripe\StripeClient('<>'); $session = $stripe->checkout->sessions->create([ 'line_items' => [ [ 'price' => '{{PRICE_ID}}', 'quantity' => 1, ], ], 'mode' => 'payment', 'success_url' => 'https://example.com/success', 'customer_email' => 'test+location_FR@example.com', ]); ``` ```java // Set your secret key. Remember to switch to your live secret key in production. // See your keys here: https://dashboard.stripe.com/apikeys StripeClient client = new StripeClient("<>"); SessionCreateParams params = SessionCreateParams.builder() .addLineItem( SessionCreateParams.LineItem.builder() .setPrice("{{PRICE_ID}}") .setQuantity(1L) .build() ) .setMode(SessionCreateParams.Mode.PAYMENT) .setSuccessUrl("https://example.com/success") .setCustomerEmail("test+location_FR@example.com") .build(); // For SDK versions 29.4.0 or lower, remove '.v1()' from the following line. Session session = client.v1().checkout().sessions().create(params); ``` ```node // Set your secret key. Remember to switch to your live secret key in production. // See your keys here: https://dashboard.stripe.com/apikeys const stripe = require('stripe')('<>'); const session = await stripe.checkout.sessions.create({ line_items: [ { price: '{{PRICE_ID}}', quantity: 1, }, ], mode: 'payment', success_url: 'https://example.com/success', customer_email: 'test+location_FR@example.com', }); ``` ```go // Set your secret key. Remember to switch to your live secret key in production. // See your keys here: https://dashboard.stripe.com/apikeys sc := stripe.NewClient("<>") params := &stripe.CheckoutSessionCreateParams{ LineItems: []*stripe.CheckoutSessionCreateLineItemParams{ &stripe.CheckoutSessionCreateLineItemParams{ Price: stripe.String("{{PRICE_ID}}"), Quantity: stripe.Int64(1), }, }, Mode: stripe.String(stripe.CheckoutSessionModePayment), SuccessURL: stripe.String("https://example.com/success"), CustomerEmail: stripe.String("test+location_FR@example.com"), } result, err := sc.V1CheckoutSessions.Create(context.TODO(), params) ``` ```dotnet // Set your secret key. Remember to switch to your live secret key in production. // See your keys here: https://dashboard.stripe.com/apikeys var options = new Stripe.Checkout.SessionCreateOptions { LineItems = new List { new Stripe.Checkout.SessionLineItemOptions { Price = "{{PRICE_ID}}", Quantity = 1, }, }, Mode = "payment", SuccessUrl = "https://example.com/success", CustomerEmail = "test+location_FR@example.com", }; var client = new StripeClient("<>"); var service = client.V1.Checkout.Sessions; Stripe.Checkout.Session session = service.Create(options); ``` ```curl curl https://api.stripe.com/v1/checkout/sessions \ -u <>: \ -d "line_items[0][price]"="{{PRICE_ID}}" \ -d "line_items[0][quantity]"=1 \ -d mode=payment \ -d success_url="https://example.com/success" \ --data-urlencode customer_email="test+location_FR@example.com" ``` You can also create a [Customer](https://docs.stripe.com/api/customers/create.md) and specify their email that contains the `+location_XX` suffix. Stripe test cards work as usual. ### Testing Payment Links For Payment Links, pass the location-formatted email as the `prefilled_email` [URL parameter](https://docs.stripe.com/payment-links/customize.md#customize-checkout-with-url-parameters) to test currency presentment for customers in different countries. ## Restrictions Adaptive Pricing isn’t available for businesses using Elements with the Payment Intents API. Adaptive Pricing isn’t supported for Indian businesses. Additionally, Adaptive Pricing requires the [currency for your prices](https://docs.stripe.com/api/checkout/sessions/object.md#checkout_session_object-currency) to be one of your settlement currencies. Prices automatically convert during checkout. This applies to [prices](https://docs.stripe.com/products-prices/manage-prices.md#prices-create) you create and reference with a price ID and prices you create inline with [price_data](https://docs.stripe.com/api/checkout/sessions/create.md#create_checkout_session-line_items-price_data) when you create a Checkout Session. If you process payments through a platform, we require your platform’s integration currency to be the settlement currency of the merchant of record on the charge. Adaptive Pricing doesn’t apply for Checkout Sessions that: - Contain explicitly defined [manual currency prices](https://docs.stripe.com/payments/checkout/localize-prices/manual-currency-prices.md). - Are in `subscription` mode. - Use [capture_method](https://docs.stripe.com/api/checkout/sessions/create.md#create_checkout_session-payment_intent_data-capture_method) as `manual`. - Use [custom amounts](https://docs.stripe.com/payments/checkout/pay-what-you-want.md). Checkout Sessions that aren’t supported by Adaptive Pricing present prices in the original currency that you’ve set your prices in. ## Supported currencies Businesses in supported regions can automatically convert prices to the local currencies of their customers in the following markets: ### North America - AG - AW - BS - BB - BZ - BM - CA - KY - CR - DM - DO - GD - GT - HT - HN - MX - JM - PA - KN - LC - VC - TT - US ### South America - BR - BO - CO - CL - FK - GY - PY - PE - UY ### Europe - AL - AD - AT - BE - BA - HR - CY - CZ - DK - EE - FI - FR - DE - GI - GR - HU - IS - IE - IT - LV - LT - LU - MT - MC - MD - ME - NL - MK - NO - PL - PT - RO - SM - RS - SK - SI - ES - SE - CH - UA - GB - VA ### Asia - AF - AM - AZ - BD - BN - KH - CN - GE - HK - IN - ID - IL - JP - KZ - KG - MO - MY - MV - MN - NP - PK - PH - QA - SA - SG - KR - LK - TW - TJ - TH - TR - AE - UZ - VN - YE ### Oceania - AU - PF - NC - NZ - WF ### Africa - AO - DZ - BJ - BW - BF - BI - CM - CV - CF - TD - CI - DJ - GQ - GA - GM - GN - GW - KE - LR - MG - ML - MU - MA - MZ - NA - NE - CG - RW - SH - ST - SN - ZA - TZ - TG - UG - ZM ## Pricing - You pay 0% - Your customers pay 2–4% You don’t directly pay any additional Stripe fees for Adaptive Pricing, as all such fees are paid for by your customers. The Stripe-provided exchange rate you present to your customers includes a 2–4% conversion fee, increasing their purchase price by a corresponding amount. Stripe determines the fee, which varies for the purposes of increasing customer conversion. Your customer doesn’t pay this fee if they choose to pay in your integration currency, but their bank’s exchange rate and fees might apply. For detailed information about current Stripe fees, see our [pricing page](https://stripe.com/pricing). ## Exchange rate Stripe uses the mid-market exchange rate and applies a fee to guarantee the rate through settlement. Learn more about how Stripe handles [currency conversions](https://docs.stripe.com/currencies.md) and [Adaptive Pricing fees](https://support.stripe.com/questions/adaptive-pricing#:~:text=Adaptive%20Pricing%20is%20a%20Checkout,latest%20Stripe%2Dprovided%20exchange%20rates). ## Refunds You can issue a refund in your integration currency, and Stripe refunds your customer in the currency they used to make the payment. The refund uses the same exchange rate as the original transaction, so there are no extra costs for you, and your customer gets back the exact amount they paid. Learn more about how Stripe helps you manage [refunds](https://docs.stripe.com/refunds.md). # Embedded form > This is a Embedded form for when payment-ui is embedded-form. View the full page at https://docs.stripe.com/payments/currencies/localize-prices/adaptive-pricing?payment-ui=embedded-form. Adaptive Pricing lets your customers pay in their local currency in more than [150 countries](https://docs.stripe.com/payments/currencies/localize-prices/adaptive-pricing.md#supported-currencies). With Adaptive Pricing, Stripe uses machine learning to determine the most relevant presentment currency, then automatically calculates the localized price and handles all currency conversion. Use Adaptive Pricing to: - Display pricing in local currencies based on location - Calculate prices in real time using an exchange rate guaranteed for 24 hours - Unlock payment methods that require local currency - Facilitate compliance when presenting supported currencies #### Integration effort Complexity: 1/5 #### Fees View information on [fees and our FAQ](https://support.stripe.com/questions/adaptive-pricing). ## Enable Adaptive Pricing in the Dashboard [Dashboard] Manage Adaptive Pricing for Checkout in your [payment settings](https://dashboard.stripe.com/settings/adaptive-pricing) in the Dashboard. You can enable Adaptive Pricing in a sandbox and live mode. Disabling Adaptive Pricing doesn’t affect Checkout Sessions that have already been converted. ## Configure local payment methods [Dashboard] Adaptive Pricing can increase the usage of local payment methods by ensuring customers have the option to pay in their local currency and with payment methods most relevant to them. As an example, 70% of all e-commerce transactions in the Netherlands use iDEAL, but it only works with EUR. You can configure which payment methods you accept in your [payment methods settings](https://dashboard.stripe.com/settings/payment_methods) if you use dynamic payment methods. Adaptive Pricing provides access to the following payment methods that require presenting in local currency: - Amazon Pay - Bancontact - BLIK - EPS - iDEAL - Link - P24 - Pix - South Korean cards - Naver Pay - Kakao Pay - PAYCO - Revolut Pay - Samsung Pay - Wechat Pay ## Event destinations and reporting [Server-side] The Checkout Session and the underlying `PaymentIntent` objects reflect what your customer paid in your integration currency and amount, which is the currency you specified for your prices. If a customer pays in their local currency, the [checkout.session.completed](https://docs.stripe.com/api/events/types.md#event_types-checkout.session.completed) and [payment_intent.succeeded](https://docs.stripe.com/api/events/types.md#event_types-payment_intent.succeeded) event contains a `presentment_details` hash that includes the `presentment_amount` and `presentment_currency`. #### JSON ```json { "id": "{{EVENT_ID}}", "object": "event", "type": "checkout.session.completed", "data": { "object": { "id": "{{SESSION_ID}}", "object": "checkout.session", "currency": "usd", "amount_total": 1000, "amount_subtotal": 1000,"presentment_details": { "presentment_amount": 1370, "presentment_currency": "cad" } } } } ``` ## Testing To test local currency presentment, pass in a location-formatted customer email that includes a suffix in a `+location_XX` format in the local part of the email. `XX` must be a valid [two-letter ISO country code](https://www.nationsonline.org/oneworld/country_code_list.htm). For example, to test currency presentment for a customer in France, pass in an email like `test+location_FR@example.com`. A Checkout Session created with a location-formatted email displays the same currency as the specified country. ```cli stripe checkout sessions create \ -d "line_items[0][price]"={{PRICE_ID}} \ -d "line_items[0][quantity]"=1 \ --mode=payment \ --ui-mode=embedded \ --return-url="https://example.com/return" \ --customer-email="test+location_FR@example.com" ``` ```ruby # Set your secret key. Remember to switch to your live secret key in production. # See your keys here: https://dashboard.stripe.com/apikeys client = Stripe::StripeClient.new("<>") session = client.v1.checkout.sessions.create({ line_items: [ { price: '{{PRICE_ID}}', quantity: 1, }, ], mode: 'payment', ui_mode: 'embedded', return_url: 'https://example.com/return', customer_email: 'test+location_FR@example.com', }) ``` ```python # Set your secret key. Remember to switch to your live secret key in production. # See your keys here: https://dashboard.stripe.com/apikeys client = StripeClient("<>") # For SDK versions 12.4.0 or lower, remove '.v1' from the following line. session = client.v1.checkout.sessions.create({ "line_items": [{"price": "{{PRICE_ID}}", "quantity": 1}], "mode": "payment", "ui_mode": "embedded", "return_url": "https://example.com/return", "customer_email": "test+location_FR@example.com", }) ``` ```php // Set your secret key. Remember to switch to your live secret key in production. // See your keys here: https://dashboard.stripe.com/apikeys $stripe = new \Stripe\StripeClient('<>'); $session = $stripe->checkout->sessions->create([ 'line_items' => [ [ 'price' => '{{PRICE_ID}}', 'quantity' => 1, ], ], 'mode' => 'payment', 'ui_mode' => 'embedded', 'return_url' => 'https://example.com/return', 'customer_email' => 'test+location_FR@example.com', ]); ``` ```java // Set your secret key. Remember to switch to your live secret key in production. // See your keys here: https://dashboard.stripe.com/apikeys StripeClient client = new StripeClient("<>"); SessionCreateParams params = SessionCreateParams.builder() .addLineItem( SessionCreateParams.LineItem.builder() .setPrice("{{PRICE_ID}}") .setQuantity(1L) .build() ) .setMode(SessionCreateParams.Mode.PAYMENT) .setUiMode(SessionCreateParams.UiMode.EMBEDDED) .setReturnUrl("https://example.com/return") .setCustomerEmail("test+location_FR@example.com") .build(); // For SDK versions 29.4.0 or lower, remove '.v1()' from the following line. Session session = client.v1().checkout().sessions().create(params); ``` ```node // Set your secret key. Remember to switch to your live secret key in production. // See your keys here: https://dashboard.stripe.com/apikeys const stripe = require('stripe')('<>'); const session = await stripe.checkout.sessions.create({ line_items: [ { price: '{{PRICE_ID}}', quantity: 1, }, ], mode: 'payment', ui_mode: 'embedded', return_url: 'https://example.com/return', customer_email: 'test+location_FR@example.com', }); ``` ```go // Set your secret key. Remember to switch to your live secret key in production. // See your keys here: https://dashboard.stripe.com/apikeys sc := stripe.NewClient("<>") params := &stripe.CheckoutSessionCreateParams{ LineItems: []*stripe.CheckoutSessionCreateLineItemParams{ &stripe.CheckoutSessionCreateLineItemParams{ Price: stripe.String("{{PRICE_ID}}"), Quantity: stripe.Int64(1), }, }, Mode: stripe.String(stripe.CheckoutSessionModePayment), UIMode: stripe.String(stripe.CheckoutSessionUIModeEmbedded), ReturnURL: stripe.String("https://example.com/return"), CustomerEmail: stripe.String("test+location_FR@example.com"), } result, err := sc.V1CheckoutSessions.Create(context.TODO(), params) ``` ```dotnet // Set your secret key. Remember to switch to your live secret key in production. // See your keys here: https://dashboard.stripe.com/apikeys var options = new Stripe.Checkout.SessionCreateOptions { LineItems = new List { new Stripe.Checkout.SessionLineItemOptions { Price = "{{PRICE_ID}}", Quantity = 1, }, }, Mode = "payment", UiMode = "embedded", ReturnUrl = "https://example.com/return", CustomerEmail = "test+location_FR@example.com", }; var client = new StripeClient("<>"); var service = client.V1.Checkout.Sessions; Stripe.Checkout.Session session = service.Create(options); ``` ```curl curl https://api.stripe.com/v1/checkout/sessions \ -u <>: \ -d "line_items[0][price]"="{{PRICE_ID}}" \ -d "line_items[0][quantity]"=1 \ -d mode=payment \ -d ui_mode=embedded \ -d return_url="https://example.com/return" \ --data-urlencode customer_email="test+location_FR@example.com" ``` You can also create a [Customer](https://docs.stripe.com/api/customers/create.md) and specify an email for them that contains the `+location_XX` suffix. Stripe test cards work as usual. ## Restrictions Adaptive Pricing isn’t available for businesses using Elements with the Payment Intents API. Adaptive Pricing isn’t supported for Indian businesses. Additionally, Adaptive Pricing requires the [currency for your prices](https://docs.stripe.com/api/checkout/sessions/object.md#checkout_session_object-currency) to be one of your settlement currencies. Prices automatically convert during checkout. This applies to [prices](https://docs.stripe.com/products-prices/manage-prices.md#prices-create) you create and reference with a price ID and prices you create inline with [price_data](https://docs.stripe.com/api/checkout/sessions/create.md#create_checkout_session-line_items-price_data) when you create a Checkout Session. If you process payments through a platform, we require your platform’s integration currency to be the settlement currency of the merchant of record on the charge. Adaptive Pricing doesn’t apply for Checkout Sessions that: - Contain explicitly defined [manual currency prices](https://docs.stripe.com/payments/checkout/localize-prices/manual-currency-prices.md). - Are in `subscription` mode. - Use [capture_method](https://docs.stripe.com/api/checkout/sessions/create.md#create_checkout_session-payment_intent_data-capture_method) as `manual`. - Use [custom amounts](https://docs.stripe.com/payments/checkout/pay-what-you-want.md). Checkout Sessions that aren’t supported by Adaptive Pricing present prices in the original currency that you’ve set your prices in. ## Supported currencies Businesses in supported regions can automatically convert prices to the local currencies of their customers in the following markets: ### North America - AG - AW - BS - BB - BZ - BM - CA - KY - CR - DM - DO - GD - GT - HT - HN - MX - JM - PA - KN - LC - VC - TT - US ### South America - BR - BO - CO - CL - FK - GY - PY - PE - UY ### Europe - AL - AD - AT - BE - BA - HR - CY - CZ - DK - EE - FI - FR - DE - GI - GR - HU - IS - IE - IT - LV - LT - LU - MT - MC - MD - ME - NL - MK - NO - PL - PT - RO - SM - RS - SK - SI - ES - SE - CH - UA - GB - VA ### Asia - AF - AM - AZ - BD - BN - KH - CN - GE - HK - IN - ID - IL - JP - KZ - KG - MO - MY - MV - MN - NP - PK - PH - QA - SA - SG - KR - LK - TW - TJ - TH - TR - AE - UZ - VN - YE ### Oceania - AU - PF - NC - NZ - WF ### Africa - AO - DZ - BJ - BW - BF - BI - CM - CV - CF - TD - CI - DJ - GQ - GA - GM - GN - GW - KE - LR - MG - ML - MU - MA - MZ - NA - NE - CG - RW - SH - ST - SN - ZA - TZ - TG - UG - ZM ## Pricing - You pay 0% - Your customers pay 2–4% You don’t directly pay any additional Stripe fees for Adaptive Pricing, as all such fees are paid for by your customers. The Stripe-provided exchange rate you present to your customers includes a 2–4% conversion fee, increasing their purchase price by a corresponding amount. Stripe determines the fee, which varies for the purposes of increasing customer conversion. Your customer doesn’t pay this fee if they choose to pay in your integration currency, but their bank’s exchange rate and fees might apply. For detailed information about current Stripe fees, see our [pricing page](https://stripe.com/pricing). ## Exchange rate Stripe uses the mid-market exchange rate and applies a fee to guarantee the rate through settlement. Learn more about how Stripe handles [currency conversions](https://docs.stripe.com/currencies.md) and [Adaptive Pricing fees](https://support.stripe.com/questions/adaptive-pricing#:~:text=Adaptive%20Pricing%20is%20a%20Checkout,latest%20Stripe%2Dprovided%20exchange%20rates). ## Refunds You can issue a refund in your integration currency, and Stripe refunds your customer in the currency they used to make the payment. The refund uses the same exchange rate as the original transaction, so there are no extra costs for you, and your customer gets back the exact amount they paid. Learn more about how Stripe helps you manage [refunds](https://docs.stripe.com/refunds.md). # Embedded Components > This is a Embedded Components for when payment-ui is embedded-components. View the full page at https://docs.stripe.com/payments/currencies/localize-prices/adaptive-pricing?payment-ui=embedded-components. > Adaptive Pricing is only supported for Elements with the Checkout Sessions API. Adaptive Pricing isn’t supported on the Payment Intents API. Adaptive Pricing lets your customers pay in their local currency in more than [150 countries](https://docs.stripe.com/payments/currencies/localize-prices/adaptive-pricing.md#supported-currencies). With Adaptive Pricing, Stripe infers the presentment currency from the customer’s public IP address, then automatically calculates the localized price and handles all currency conversion. Use Adaptive Pricing to: - Display pricing in local currencies based on location using the [Currency Selector Element](https://docs.stripe.com/elements/currency-selector-element.md) - Calculate prices in real-time using an exchange rate guaranteed for 24 hours - Unlock payment methods that require local currency - Facilitate compliance when presenting supported currencies #### Integration effort Complexity: 2/5 #### Fees View information on [fees and our FAQ](https://support.stripe.com/questions/adaptive-pricing). #### UI customization Place the [Currency Selector Element](https://docs.stripe.com/elements/currency-selector-element.md) anywhere on your checkout page. ## Enable Adaptive Pricing in the Dashboard [Dashboard] Manage Adaptive Pricing for Checkout in your [Payments settings](https://dashboard.stripe.com/settings/adaptive-pricing) in the Dashboard. You can enable Adaptive Pricing in a sandbox and live mode. Disabling Adaptive Pricing doesn’t affect Checkout Sessions that have already been converted. ## Localize and format prices [Client-side] It’s important to display prices consistently according to the selected currency throughout your checkout page, including line items, shipping rates, discounts, tax, and totals. When using Embedded Components with Adaptive Pricing, the Embedded Components [Session object](https://docs.stripe.com/js/custom_checkout/session_object) can contain localized values if Adaptive Pricing is active. You should design your integration as though the session could contain amounts and currencies relevant to any country your buyers might be visiting your site from. This workflow relies on preformatted fields like [session.total.total.amount](https://docs.stripe.com/js/custom_checkout/session_object#custom_checkout_session_object-total-total-amount). The [Checkout Session](https://docs.stripe.com/api/checkout/sessions/object.md) object returned in the Stripe API remains in the same currency set in your Stripe integration with customer context available under [presentment_details](https://docs.stripe.com/api/checkout/sessions/object.md#checkout_session_object-presentment_details) and it won’t match exactly with the Embedded Components [Session object](https://docs.stripe.com/js/custom_checkout/session_object). #### HTML + JS The [Session object](https://docs.stripe.com/js/custom_checkout/session_object) provides formatted currency values that you can use directly in your UI. ```javascript const { actions } = await checkout.loadActions(); const { total } = actions.getSession(); // Display the formatted amounts in your UI document.getElementById('order-total').textContent = total.total.amount; ``` #### React The [useCheckout](https://docs.stripe.com/js/custom_checkout/react/use_checkout) hook provides formatted currency values that you can use directly in your UI. ```jsx import React from 'react'; import {useCheckout} from '@stripe/react-stripe-js/checkout'; const OrderSummary = () => { const checkoutState = useCheckout(); if (checkoutState.type === 'success') { // Display the formatted amounts in your UI return (
Total: {checkoutState.checkout.total.total.amount}
); } }; ``` ## Render the Currency Selector Element [Client-side] The [Currency Selector Element](https://docs.stripe.com/elements/currency-selector-element.md) is an embeddable UI component that facilitates Adaptive Pricing. Display it near the order total. > You are responsible for complying with laws that apply to price localization in your or your customers’ regions. You must render the Currency Selector Element in your use of Adaptive Pricing with Elements. Stripe recommends you consult your legal counsel for advice specific to your business. #### HTML + JS Create a container DOM element to mount the Currency Selector Element. Then create an instance of the Currency Selector Element using [checkout.createCurrencySelectorElement](https://docs.stripe.com/js/custom_checkout/create_currency_selector_element) and mount it by calling [element.mount](https://docs.stripe.com/js/element/mount), providing either a CSS selector or the container DOM element. You can decide to only create the Currency Selector Element when the [currencyOptions](https://docs.stripe.com/js/custom_checkout/session_object#custom_checkout_session_object-currencyOptions) are populated. If there are no `currencyOptions` and the Currency Selector Element is mounted, nothing displays. ```html
``` ```javascript const currencySelectorElement = checkout.createCurrencySelectorElement(); currencySelectorElement.mount('#currency-selector'); ``` #### React Mount the `CurrencySelectorElement` component within the `CheckoutProvider`. You can decide to only to mount the `CurrencySelectorElement` when the [currencyOptions](https://docs.stripe.com/js/custom_checkout/react/use_checkout#custom_checkout_react_use_checkout-currencyOptions) are populated. If there are no `currencyOptions` and the `CurrencySelectorElement` is mounted, nothing displays. ```jsx import React from 'react'; import {CurrencySelectorElement} from '@stripe/react-stripe-js/checkout'; const OrderSummary = () => { return ( ); }; ``` ### Design best practices We offer a configurable **Currency Selector Element** for your checkout page. Follow these best practices when choosing where to place your selector: - Add the **Currency Selector** near where payment details are entered, ideally directly above the **Payment Element**, since the selected currency might affect available payment methods. - If the **Payment Element** isn’t initially visible (due to multi-step flows or being lower on the page), position the **Currency Selector** near the total price display. - If you’re using the [Express Checkout Element](https://docs.stripe.com/elements/express-checkout-element.md), we recommend placing the Currency Selector Element above the Express Checkout Element to ensure your customers know what currency they will be charged in. - Apply these tips to your page layouts for all screen sizes. ![The Currency Selector Element placed above the Payment Element](https://b.stripecdn.com/docs-statics-srv/assets/adaptive-pricing-do-illustration.d74714dab5286f4a75521ba5b35b4a3c.png) > #### Do > > Place the Currency Selector above the Payment Element. If you’re only accepting cards, you can also place it directly below the Payment Element. ## Mark your integration as ready for Adaptive Pricing [Client-side] Once you have [localized and formatted your prices](https://docs.stripe.com/payments/currencies/localize-prices/adaptive-pricing.md#localize-prices) and [rendered the currency selector](https://docs.stripe.com/payments/currencies/localize-prices/adaptive-pricing.md#render-currency-selector-element), mark your integration as ready for Adaptive Pricing by setting the [adaptivePricing.allowed](https://docs.stripe.com/js/custom_checkout/init#custom_checkout_init-options-adaptivePricing-allowed) parameter when you initialize checkout. #### HTML + JS ```js const checkout = stripe.initCheckout({ clientSecret, // Mark your integration as ready for Adaptive PricingadaptivePricing: { allowed: true } }); // Use `checkout` to build your checkout page ``` #### React ```jsx >")} options={{ clientSecret, // Mark your integration as ready for Adaptive PricingadaptivePricing: {allowed: true} }} > {/* your components here */} ``` After your integration is marked as ready, you can manage Adaptive Pricing in your [Payments settings](https://dashboard.stripe.com/settings/adaptive-pricing) in the Dashboard, or per [Checkout Session](https://docs.stripe.com/api/checkout/sessions.md) using the [adaptive_pricing.enabled](https://docs.stripe.com/api/checkout/sessions/create.md#create_checkout_session-adaptive_pricing-enabled) parameter. ## Configure local payment methods [Dashboard] Adaptive Pricing can increase the usage of local payment methods by ensuring customers have the option to pay in their local currency and with payment methods most relevant to them. As an example, 70% of all e-commerce transactions in the Netherlands use iDEAL, but it only works with EUR. You can configure which payment methods you accept in your [payment methods settings](https://dashboard.stripe.com/settings/payment_methods) if you use dynamic payment methods. Adaptive Pricing provides access to the following payment methods that require presenting in local currency: - Amazon Pay - Bancontact - BLIK - EPS - iDEAL - Link - P24 - Pix - South Korean cards - Naver Pay - Kakao Pay - PAYCO - Revolut Pay - Samsung Pay - Wechat Pay ## Testing To test local currency presentment, pass in a location-formatted customer email that includes a suffix in a `+location_XX` format in the local part of the email. `XX` must be a valid [two-letter ISO country code](https://www.nationsonline.org/oneworld/country_code_list.htm). For example, to test currency presentment for a customer in France, pass in an email like `test+location_FR@example.com`. When you view your checkout page with the Currency Selector Element and Payment Element using a CheckoutSession created with a location-formatted email, you see the same currency as a customer does in the specified country. When you create a Checkout Session, pass the location-formatted email as [customer_email](https://docs.stripe.com/api/checkout/sessions/object.md#checkout_session_object-customer_email) to simulate Checkout from a particular country. ```curl curl https://api.stripe.com/v1/checkout/sessions \ -u "<>:" \ -d "line_items[0][price]"={{PRICE_ID}} \ -d "line_items[0][quantity]"=1 \ -d mode=payment \ -d ui_mode=custom \ -d "adaptive_pricing[enabled]"=true \ -d return_url={{RETURN_URL}} \ --data-urlencode customer_email="test+location_FR@example.com" ``` ```cli stripe checkout sessions create \ -d "line_items[0][price]"={{PRICE_ID}} \ -d "line_items[0][quantity]"=1 \ --mode=payment \ --ui-mode=custom \ -d "adaptive_pricing[enabled]"=true \ --return-url={{RETURN_URL}} \ --customer-email="test+location_FR@example.com" ``` ```ruby client = Stripe::StripeClient.new("<>") session = client.v1.checkout.sessions.create({ line_items: [ { price: '{{PRICE_ID}}', quantity: 1, }, ], mode: 'payment', ui_mode: 'custom', adaptive_pricing: {enabled: true}, return_url: '{{RETURN_URL}}', customer_email: 'test+location_FR@example.com', }) ``` ```python client = StripeClient("<>") # For SDK versions 12.4.0 or lower, remove '.v1' from the following line. session = client.v1.checkout.sessions.create({ "line_items": [{"price": "{{PRICE_ID}}", "quantity": 1}], "mode": "payment", "ui_mode": "custom", "adaptive_pricing": {"enabled": True}, "return_url": "{{RETURN_URL}}", "customer_email": "test+location_FR@example.com", }) ``` ```php $stripe = new \Stripe\StripeClient('<>'); $session = $stripe->checkout->sessions->create([ 'line_items' => [ [ 'price' => '{{PRICE_ID}}', 'quantity' => 1, ], ], 'mode' => 'payment', 'ui_mode' => 'custom', 'adaptive_pricing' => ['enabled' => true], 'return_url' => '{{RETURN_URL}}', 'customer_email' => 'test+location_FR@example.com', ]); ``` ```java StripeClient client = new StripeClient("<>"); SessionCreateParams params = SessionCreateParams.builder() .addLineItem( SessionCreateParams.LineItem.builder() .setPrice("{{PRICE_ID}}") .setQuantity(1L) .build() ) .setMode(SessionCreateParams.Mode.PAYMENT) .setUiMode(SessionCreateParams.UiMode.CUSTOM) .setAdaptivePricing( SessionCreateParams.AdaptivePricing.builder().setEnabled(true).build() ) .setReturnUrl("{{RETURN_URL}}") .setCustomerEmail("test+location_FR@example.com") .build(); // For SDK versions 29.4.0 or lower, remove '.v1()' from the following line. Session session = client.v1().checkout().sessions().create(params); ``` ```node const stripe = require('stripe')('<>'); const session = await stripe.checkout.sessions.create({ line_items: [ { price: '{{PRICE_ID}}', quantity: 1, }, ], mode: 'payment', ui_mode: 'custom', adaptive_pricing: { enabled: true, }, return_url: '{{RETURN_URL}}', customer_email: 'test+location_FR@example.com', }); ``` ```go sc := stripe.NewClient("<>") params := &stripe.CheckoutSessionCreateParams{ LineItems: []*stripe.CheckoutSessionCreateLineItemParams{ &stripe.CheckoutSessionCreateLineItemParams{ Price: stripe.String("{{PRICE_ID}}"), Quantity: stripe.Int64(1), }, }, Mode: stripe.String(stripe.CheckoutSessionModePayment), UIMode: stripe.String(stripe.CheckoutSessionUIModeCustom), AdaptivePricing: &stripe.CheckoutSessionCreateAdaptivePricingParams{ Enabled: stripe.Bool(true), }, ReturnURL: stripe.String("{{RETURN_URL}}"), CustomerEmail: stripe.String("test+location_FR@example.com"), } result, err := sc.V1CheckoutSessions.Create(context.TODO(), params) ``` ```dotnet var options = new Stripe.Checkout.SessionCreateOptions { LineItems = new List { new Stripe.Checkout.SessionLineItemOptions { Price = "{{PRICE_ID}}", Quantity = 1, }, }, Mode = "payment", UiMode = "custom", AdaptivePricing = new Stripe.Checkout.SessionAdaptivePricingOptions { Enabled = true, }, ReturnUrl = "{{RETURN_URL}}", CustomerEmail = "test+location_FR@example.com", }; var client = new StripeClient("<>"); var service = client.V1.Checkout.Sessions; Stripe.Checkout.Session session = service.Create(options); ``` You can also create a [Customer](https://docs.stripe.com/api/customers/create.md) and specify their email that contains the `+location_XX` suffix. Stripe test cards work as usual. ## Restrictions Adaptive Pricing isn’t available for businesses using Elements with the Payment Intents API. Adaptive Pricing isn’t supported for Indian businesses. Additionally, Adaptive Pricing requires the [currency for your prices](https://docs.stripe.com/api/checkout/sessions/object.md#checkout_session_object-currency) to be one of your settlement currencies. Prices automatically convert during checkout. This applies to [prices](https://docs.stripe.com/products-prices/manage-prices.md#prices-create) you create and reference with a price ID and prices you create inline with [price_data](https://docs.stripe.com/api/checkout/sessions/create.md#create_checkout_session-line_items-price_data) when you create a Checkout Session. If you process payments through a platform, we require your platform’s integration currency to be the settlement currency of the merchant of record on the charge. Adaptive Pricing doesn’t apply for Checkout Sessions that: - Contain explicitly defined [manual currency prices](https://docs.stripe.com/payments/checkout/localize-prices/manual-currency-prices.md). - Are in `subscription` mode. - Use [capture_method](https://docs.stripe.com/api/checkout/sessions/create.md#create_checkout_session-payment_intent_data-capture_method) as `manual`. - Use [custom amounts](https://docs.stripe.com/payments/checkout/pay-what-you-want.md). Checkout Sessions that aren’t supported by Adaptive Pricing present prices in the original currency that you’ve set your prices in. See our [support page](https://support.stripe.com/questions/adaptive-pricing) for more information. ## Supported currencies Businesses in supported regions can automatically convert prices to the local currencies of their customers in the following markets: ### North America - AG - AW - BS - BB - BZ - BM - CA - KY - CR - DM - DO - GD - GT - HT - HN - MX - JM - PA - KN - LC - VC - TT - US ### South America - BR - BO - CO - CL - FK - GY - PY - PE - UY ### Europe - AL - AD - AT - BE - BA - HR - CY - CZ - DK - EE - FI - FR - DE - GI - GR - HU - IS - IE - IT - LV - LT - LU - MT - MC - MD - ME - NL - MK - NO - PL - PT - RO - SM - RS - SK - SI - ES - SE - CH - UA - GB - VA ### Asia - AF - AM - AZ - BD - BN - KH - CN - GE - HK - IN - ID - IL - JP - KZ - KG - MO - MY - MV - MN - NP - PK - PH - QA - SA - SG - KR - LK - TW - TJ - TH - TR - AE - UZ - VN - YE ### Oceania - AU - PF - NC - NZ - WF ### Africa - AO - DZ - BJ - BW - BF - BI - CM - CV - CF - TD - CI - DJ - GQ - GA - GM - GN - GW - KE - LR - MG - ML - MU - MA - MZ - NA - NE - CG - RW - SH - ST - SN - ZA - TZ - TG - UG - ZM ## Pricing - You pay 0% - Your customers pay 2–4% You don’t directly pay any additional Stripe fees for Adaptive Pricing, as all such fees are paid for by your customers. The Stripe-provided exchange rate you present to your customers includes a 2–4% conversion fee, increasing their purchase price by a corresponding amount. Stripe determines the fee, which varies for the purposes of increasing customer conversion. Your customer doesn’t pay this fee if they choose to pay in your integration currency, but their bank’s exchange rate and fees might apply. For detailed information about current Stripe fees, see our [pricing page](https://stripe.com/pricing). ## Exchange rate Stripe uses the mid-market exchange rate and applies a fee to guarantee the rate through settlement. Learn more about how Stripe handles [currency conversions](https://docs.stripe.com/currencies.md) and [Adaptive Pricing fees](https://support.stripe.com/questions/adaptive-pricing#:~:text=Adaptive%20Pricing%20is%20a%20Checkout,latest%20Stripe%2Dprovided%20exchange%20rates). ## Refunds You can issue a refund in your integration currency, and Stripe refunds your customer in the currency they used to make the payment. The refund uses the same exchange rate as the original transaction, so there are no extra costs for you, and your customer gets back the exact amount they paid. Learn more about how Stripe helps you manage [refunds](https://docs.stripe.com/refunds.md). # Hosted Invoice Page > This is a Hosted Invoice Page for when payment-ui is invoices. View the full page at https://docs.stripe.com/payments/currencies/localize-prices/adaptive-pricing?payment-ui=invoices. Adaptive Pricing lets your customers pay in their local currency in more than [150 countries](https://docs.stripe.com/payments/currencies/localize-prices/adaptive-pricing.md#supported-currencies). With Adaptive Pricing, Stripe infers the presentment currency from the customer’s public IP address, then automatically calculates the localized price and handles all currency conversion. Use Adaptive Pricing to: - Display pricing in local currencies based on location - Calculate prices in real time using an exchange rate guaranteed for 24 hours - Facilitate compliance when presenting supported currencies #### Integration effort Complexity: 1/5 #### Fees Read our FAQ on [fees](https://support.stripe.com/questions/adaptive-pricing). ## Enable Adaptive Pricing in the Dashboard [Dashboard] Manage Adaptive Pricing for Hosted Invoice Pages in your [payment settings](https://dashboard.stripe.com/settings/adaptive-pricing) in the Dashboard. You can enable Adaptive Pricing in a sandbox and live mode. Disabling Adaptive Pricing affects Hosted Invoice Pages that have already been created. ## Configure local payment methods [Dashboard] Adaptive Pricing can increase the usage of local payment methods by ensuring customers have the option to pay in their local currency and with payment methods most relevant to them. You can configure which payment methods you accept for invoices in your [invoice settings](https://dashboard.stripe.com/settings/billing/invoice) or when creating an invoice. Adaptive Pricing only presents payment methods that support both the customer’s local currency and the currency that you issue the invoice in. ## Event destinations and reporting [Server-side] When you send an invoice, the [invoice.sent](https://docs.stripe.com/api/events/types.md#event_types-invoice.sent) event displays the amount and currency that you send the invoice in. After the invoice has been paid, use the invoice ID from the [invoice.payment_succeeded](https://docs.stripe.com/api/events/types.md#event_types-invoice.payment_succeeded) event to retrieve the associated payments for the invoice: #### JSON ```json { "object": {"id": "{{INVOICE_ID}}", "object": "invoice", "amount_paid": 1000 "currency": "usd" ... } } ``` Using the [v1/invoice_payments](https://docs.stripe.com/api/invoice-payment/list.md) API: #### curl ```bash curl --request GET \ --url https://api.stripe.com/v1/invoice_payments \ -u sk_test_123: \ --data 'expand[]=data.payment.payment_intent' \ --data limit=20 \ --data invoice='{{INVOICE_ID}}' ``` If a customer pays in their local currency, the `PaymentIntent` object contains a `presentment_details` hash that includes the `presentment_amount` and `presentment_currency`. When an invoice is paid, there are [payment_intent.succeeded](https://docs.stripe.com/api/events/types.md#event_types-payment_intent.succeeded) events for each PaymentIntent associated with the invoice. These objects contain the `presentment_details` hash. The presentment amount and currency reflect what your customer paid in the local currency. #### JSON ```json { "id": "{{PAYMENT_INTENT_ID}}", "object": "payment_intent", "currency": "usd", "amount": 1000,"presentment_details": { "presentment_amount": 1370, "presentment_currency": "cad" } } ``` ## Testing To test local currency presentment on Hosted Invoice Page, create a [Customer](https://docs.stripe.com/api/customers/create.md) with a location-formatted customer email that includes a suffix in a `+location_XX` format in the local part of the email. `XX` must be a valid [two-letter ISO country code](https://www.nationsonline.org/oneworld/country_code_list.htm). For example, to test currency presentment for a customer in France, create a customer and issue an invoice to an email like `test+location_FR@example.com`. When you visit the URL for the Hosted Invoice Page sent to a location-formatted email, you see the option to pay in the local currency of the specified country. ![Creating a customer with a location-formatted email during invoice creation](https://b.stripecdn.com/docs-statics-srv/assets/adaptive_pricing_hip_customer.eb3b947172844c48105619355fc3b986.png) ## Restrictions Adaptive Pricing isn’t supported for Indian businesses or for invoices that accept Canadian pre-authorized debit. You must issue invoices in one of your settlement currencies. If you process payments through a platform, we require the invoice to be issued in the settlement currency of the merchant of record on the charge. On the Hosted Invoice Page, prices automatically convert to the correct amount. Invoices that aren’t supported by Adaptive Pricing continue to present prices in the currency that you issue the invoice in. ## Supported currencies Businesses in supported regions can automatically convert prices to the local currencies of their customers in the following markets: ### North America - AG - AW - BS - BB - BZ - BM - CA - KY - CR - DM - DO - GD - GT - HT - HN - MX - JM - PA - KN - LC - VC - TT - US ### South America - BR - BO - CO - CL - FK - GY - PY - PE - UY ### Europe - AL - AD - AT - BE - BA - HR - CY - CZ - DK - EE - FI - FR - DE - GI - GR - HU - IS - IE - IT - LV - LT - LU - MT - MC - MD - ME - NL - MK - NO - PL - PT - RO - SM - RS - SK - SI - ES - SE - CH - UA - GB - VA ### Asia - AF - AM - AZ - BD - BN - KH - CN - GE - HK - IN - ID - IL - JP - KZ - KG - MO - MY - MV - MN - NP - PK - PH - QA - SA - SG - KR - LK - TW - TJ - TH - TR - AE - UZ - VN - YE ### Oceania - AU - PF - NC - NZ - WF ### Africa - AO - DZ - BJ - BW - BF - BI - CM - CV - CF - TD - CI - DJ - GQ - GA - GM - GN - GW - KE - LR - MG - ML - MU - MA - MZ - NA - NE - CG - RW - SH - ST - SN - ZA - TZ - TG - UG - ZM ## Pricing - You pay 0% - Your customers pay 2–4% You don’t directly pay any additional Stripe fees for Adaptive Pricing, as all such fees are paid for by your customers. The Stripe-provided exchange rate you present to your customers includes a 2–4% conversion fee, increasing their purchase price by a corresponding amount. Stripe determines the fee, which varies for the purposes of increasing customer conversion. Your customer doesn’t pay this fee if they choose to pay in the currency you issued your invoice in, but their bank’s exchange rate and fees might apply. For detailed information about current Stripe fees, see our [pricing page](https://stripe.com/pricing). ## Exchange rate Stripe uses the mid-market exchange rate and applies a fee to guarantee the rate through settlement. Learn more about how Stripe handles [currency conversions](https://docs.stripe.com/currencies.md) and [Adaptive Pricing fees](https://support.stripe.com/questions/adaptive-pricing#:~:text=Adaptive%20Pricing%20is%20a%20Checkout,latest%20Stripe%2Dprovided%20exchange%20rates). ## Refunds You can issue a refund in the currency you issued your invoice in, and Stripe refunds your customer in the currency they used to make the payment. The refund uses the same exchange rate as the original transaction, so there are no extra costs for you, and your customer gets back the exact amount they paid. Learn more about how Stripe helps you manage [refunds](https://docs.stripe.com/refunds.md). ## See also - [Adaptive Pricing FAQ](https://support.stripe.com/questions/adaptive-pricing)