Build product listing and detail pages
Build product listing and detail pages
Build a product list and detail page that show the same price and availability the cart will use. Keep the page’s presentation separate from the rules that determine whether a variant is sellable.
Before you begin
Use the Storefront quickstart to verify one prepared product. Resolve the store, price channel, currency, country, and locale through your application’s request context.
1. Load the product grid
Use the product ID as a stable rendering key and the slug for the product link.
Display price.discountedPrice?.value ?? price.value as the current price.
price.value is the original price; requesting only that field would miss a product discount.
Load another page only when hasNextPage is true, with the returned cursor and unchanged context.
Render an empty state without treating an empty list as a network failure.
2. Load the selected product
Handle a null product as an unavailable or missing page. If a product has more variants than this page contains, paginate before claiming to offer every option. For structured selectors, add the attribute assignments and selections your UI needs from the reference.
3. Select an actual variant
Keep the selected variant ID in state.
Change its image, price, SKU, and purchase control together.
Disable purchase when there is no usable price or availableForPurchase is false.
Never create a variant ID or SKU by concatenating option labels.
Verify
Test a missing product, missing image, missing price, unavailable variant, and a product with multiple choices.
Add the selected variant to a cart with matching context and confirm the returned item and amount.
The Next.js example places these operations under src/lib/thorcommerce/storefront/queries/products.graphql and the UI under src/features/products.