Skip to content
Twilight React Playground
ثيم رائدaren

Which store, and its URLs

Advanced9 min

How the engine decides which store a request is for, which hosts may name one, and the store segment on localhost.

One theme serves many stores at once. The same build answers perfumes.example, furniture.example and every other merchant domain that installs it, so which store a page is for is decided on every request, never by your code or configuration.

The rules differ between a merchant's own domain and the hosts that serve many stores. Step through the decision.

Requesthost · path · cookieMay it name one?allowsRequestStoreIdWhat it namesquery › path › cookieRequest contextstoreId · storeBaseHost is the storemerchant domainOne resolverresolveStoreIdentifierRouter rewritestrip / add segmentVITE_STORE_DOMAINdevelopment, lastStore settingsor Store UnavailableOne address/<username>/…Browser agreesruntime-env script

1. A request arrives

A request carries three things that could say which store it is for: the host name (perfumes.example), the path (/cart) and its cookies. Which of them the engine believes depends on the host.

In engine terms

twilightMiddleware() reads the host with requestHostOf(request) (src/utils/request-host.ts): the request URL's host, else the Host header. Never X-Forwarded-Host, which a client can set.

The two kinds of host

HostMay the request name a store?The store is/cart means
A merchant domain (any host not below)NoThe host itselfThe cart page
preview.salla.designYes?storeId=, then the first path segment, then the cookieThe store whose username is cart
localhost, 127.0.0.1, [::1], *.localhostYesThe same, then VITE_STORE_DOMAINThe store whose username is cart

See what this page resolves

The store identifier every API call from this page sends, and the store the page actually rendered.Try this: type any value into explicit: it always wins, because the caller said so.
Storefront canvas · en · LTR
Runs in the browser…
Controls
Leave empty to see what the page resolves by itself.
What a theme writes
import { resolveStoreIdentifier } from '@salla.sa/twilight-theme-engine/api/store';

// '' means nothing resolved: every Salla API call would fail with 422.
const storeIdentifier = resolveStoreIdentifier();

Why a theme never pins a store

  • A store id in code (or a store-identifier you set on every request) makes every merchant's domain show that one shop. Let the request decide; pass an explicit identifier only when your code already knows which store it is asking about.
  • `VITE_STORE_DOMAIN` is not configuration. It is a build-time value for pnpm dev, and it is consulted last. On a deployed theme the host answers first.
  • `?storeId=` on a merchant domain does nothing, by design. Test store switching on localhost or the preview host.
  • A path built from the address bar gets the store segment twice on localhost and the preview host (/dev-x/dev-x/cart), because the router adds it again. Use the engine's Link, useNavigate and useLocation.
Check yourself

On a merchant's domain, someone opens https://their-shop.com/?storeId=123. Which store renders?