Can the Storefront API reuse an existing B2B customer session in a theme?

Short description of issue

Use existing Online Store B2B session with Storefront API in a theme?

Reproduction steps

  1. Log in to an Online Store as a B2B customer with company-specific pricing.
  2. Open a product page. Liquid and /products/{handle}.js return the correct B2B price.
  3. From the same theme and browser session, call the Storefront API using credentials: “same-origin”, without a separate customer access token.
  4. The Storefront API returns the public price instead of the contextual B2B price.

Additional info

We use Algolia for storefront search and want to progressively refresh product prices from Shopify so B2B customers and customers in different markets see the correct contextual prices.

This is a regular Online Store theme, not a headless storefront, so the customer is already logged in through Shopify. Liquid and /products/{handle}.js correctly return the customer’s B2B price. However, a same-origin Storefront API request returns the public price unless we provide a separate customer access token and company location through BuyerInput.

Is there a supported way for the Storefront API to reuse the existing Online Store customer session without requiring the customer to authenticate again? Ideally, we want to fetch prices for multiple products in one request.

What type of topic is this

General discussion

Hey @Robin_Sch - thanks for the detailed example.

I did some digging here, and the Storefront API can’t take its B2B buyer context directly from the existing Online Store session. A contextualized request still needs a Customer Account API access token and the applicable company location passed through BuyerInput. There isn’t a supported theme or Ajax API mechanism for reading that token from the Online Store session, and credentials: "same-origin" doesn’t replace the required buyer context.

That doesn’t mean the customer should need to enter their email or OTP again. When your storefront code redirects through the Customer Account authorization flow, an active customer session should let Shopify redirect straight back to your callback with an authorization code, which you then exchange for an access token. The top-level redirect round-trip is still required. The Customer Account API supports prompt=none, which returns login_required instead of showing a login screen when no active session exists: Customer Account API reference

Could you confirm what “authenticate again” looks like in your testing? Is the customer actually prompted to enter their email or OTP, or are they only seeing the redirect to the authorization endpoint and back? If they’re seeing a credentials or consent screen, it would also help to know the client type, whether you’re passing prompt=none or acr_values, and whether the callback returns login_required or interaction_required.

You can pass the Customer Account API access token directly as customerAccessToken. The older storefrontCustomerAccessTokenCreate exchange has been deprecated since API version 2025-01: Deprecation of storefrontCustomerAccessTokenCreate Mutation - Shopify developer changelog

For batching prices, nodes(ids:) accepts up to 250 IDs in one request, and @inContext(buyer: $buyer) applies the same B2B context across the whole operation. These responses contain buyer-specific pricing, so they shouldn’t be cached or shared between customers.

If avoiding the OAuth redirect is the main requirement, another option for a regular theme is to render the pricing through Liquid using the Section Rendering API, which uses the existing Online Store context. An app-backed option would be an authenticated app proxy querying Admin API contextualPricing with the customer’s company location.

Hope this helps!