Neither workshops nor portfolio is in this tenant's enabledModules
(["products","blog","finance"]) - same reasoning as before, page/nav entry
withheld until either is actually enabled.
Shopping cart (new):
- CartProvider (client context): live cart state, add/update/remove/refresh,
reads AUTH_TOKEN_COOKIE, calls the real /businesses/{id}/cart* endpoints
(bearer-only, no guest cart - by design, not a gap)
- CartButton: header/bottom-nav icon with a live count badge and a popup
preview; "ادامه" hands off to the customer portal's own cart/checkout,
since this storefront has no checkout UI (address/payment) to hand off to
internally - out of scope for this pass
- ProductBuyPanel: quantity stepper, wired to CartProvider.addItem() instead
of its own ad-hoc fetch+token logic, toast on success
- Cart/CartItem types are a best-effort guess at an undocumented response
shape (OpenAPI gives no field-level schema) - unverified against real data
since store-items are still empty; read every field defensively
Store-items pages (new): /store-items (flat listing of purchasable variants,
always priced unlike /products) and /store-items/{id} (detail - no slug,
resolves the variant's productId and reuses the product's own gallery/
description/technical-info/comments/related-products, just with that
variant preselected).
Contact form: now shows a toast + inline success text and resets while
staying on screen, instead of swapping to a separate "thank you" panel.
New shared providers: ToastProvider (useToast) and CartProvider, both
mounted once in layout.tsx.
Co-Authored-By: Claude Sonnet 5 <noreply@anthropic.com>
- Enlarge category carousel thumbnails (90px -> 104-140px responsive) and
confirm the slider/categories/banner static-image slots are all reading
correctly from the CMS (verified live, not a wiring bug)
- Fix installments page dropping "هندزفری و هدفون": it's a level-3 category,
not level-2, so level2.find() silently missed it - use findNode() over the
whole tree instead
- Extend gen-category-placeholders.mjs to generate a placeholder for every
category at every level (was level-2 only), needed for the fix above
- Add /about, /contact, /installments pages
- About: real copy transcribed from the live moalem.shop theme, real
product photos from the API, text-only brand strip (no scraped logos)
- Contact: ContactForm.tsx posts to the real POST /contact-submissions,
branch cards with key-less Google Maps embeds
- Installments: flat brand-colored hero (no photo/gradient), category
highlights reusing the same categories slot images as the homepage
- Replace the placeholder header/footer phone number with the real one, add
real branch addresses and Instagram/Telegram links (src/data/site.ts),
pulled from the live theme's footer
- Wire logo/favicon to GET /website/favicon (getFavicon() in api.ts) instead
of the static bundled files, so a dashboard upload now shows automatically;
layout.tsx metadata is now generateMetadata() to support this. The tenant's
uploaded logo/favicon currently belongs to a different business - the
wiring is correct and will self-correct once that's fixed in the dashboard
Co-Authored-By: Claude Sonnet 5 <noreply@anthropic.com>