Files
samen-clinic/CONTEXT.md
T
Alireza HassaniandCursor e7e5381b80 Update homepage static-image slots and customer login links.
Align slot catalog with slider / our-experts / two-service-banner and send guests to customer portal /login.

Co-authored-by: Cursor <cursoragent@cursor.com>
2026-10-01 21:23:22 +03:30

7.7 KiB
Raw Blame History

Clinic Samen — AI / Project Context

Source of truth

  • Live site being cloned: https://www.clinicsamen.com/
  • Prompt instructions: Ai-data/prompt.txt
  • Backend / Meshkee Website API: https://api.meshkee.com/docs/website
  • Static image slots prompt: Ai-data/prompt-images-slot.txt
  • Backend connect prompt: Ai-data/prompt-connect-backend.txt
  • SEO prompt: Ai-data/prompt-seo.txt
  • Domain: clinicsamen.com (NEXT_PUBLIC_WEBSITE_DOMAIN)
  • Tenant business id: 21 (from GET /tenants/clinicsamen.com)

Stack

  • Next.js 15 (App Router) + React 19 + TypeScript
  • Tailwind CSS v4 (utility import) + custom CSS in src/app/globals.css
  • Language: fa, direction: rtl
  • Fonts (downloaded from Meshkee CDN into public/fonts/):
    • iran-sans (default body / Persian UI)
    • montserrat (English labels)

Color palette (from live site CSS vars / accents)

  • Primary soft blue: #DFEAFE (--wb-primary-color)
  • Secondary / brand blue: #0141C5 (--wb-secondary-color)
  • Accent blue: #0946C7
  • Mint accent: #3ED2A7
  • Footer navy: #0B1F4D
  • Muted text: #707070

Pages

Route Purpose
/ Homepage
/about درباره ما
/contact تماس با ما
/ourdr درمانگران
/blog مقالات (Meshkee blogs API)
/blog/{id}/{titleSlug} جزئیات مقاله
/workshops کارگاه‌ها (Meshkee workshops API)
/workshops/{slug} جزئیات کارگاه

Meshkee API integration

Base: {NEXT_PUBLIC_MESHKEE_API_BASE}/tenants/{domain}/...
Helpers: src/lib/meshkee.ts → meshkeeGet, tenantPath, getTenant, getBusinessId

Blog

  • List: GET /blogs?page=&pageSize=
  • Detail: GET /blogs/by-id/{id} (canonical URL /blog/{id}/{titleSlug})
  • Legacy redirect: /blog/{slug} → canonical
  • Comments: GET /comments?entityType=blog&entityId={id}
  • Lib: src/lib/blog.ts

Workshops

  • List: GET /workshops?page=&pageSize=
  • Detail: GET /workshops/{slug} (URL /workshops/{slug})
  • Register (auth): POST /workshops/{workshopId}/register via src/app/api/workshops/[workshopId]/register/route.ts
  • Cancel registration (auth): DELETE /workshops/{workshopId}/register
  • Comments: included on workshop detail when API provides comments; otherwise empty
  • Lib: src/lib/workshops.ts
  • Note: Tenant currently has no published workshops in API; homepage/list fall back to static samples in src/data/site.ts.

Auth / customer portal

  • Login / user icon → https://customer.{domain}/login (customerPortalUrl in src/lib/config.ts → customer.clinicsamen.com)
  • Session: src/lib/session.tsx + shared cookies (src/lib/shared-auth-cookie.ts) — reads meshkee_customer_access_token from parent domain
  • Profile API proxy: GET /api/auth/me → Meshkee /auth/me
  • Admin handoff: POST /api/auth/handoff → Meshkee /auth/handoff → https://business.clinicsamen.com
  • Logged-in header: {firstName lastName} عزیز via userDisplayName
  • Dropdown (AccountMenu): پروفایل من → /profile; مدیریت وبسایت (admins/owners/team only, handoff ticket); خروج (clears shared cookies)
  • Component: src/components/AccountMenu.tsx (wired in Header topbar)

Static image slots

API: GET /tenants/{domain}/website/static-images?pageKey=home
Catalog for dashboard Refresh: GET /meshkee/static-image-slots → STATIC_IMAGE_SLOTS in src/lib/static-images.ts

key kind itemCount aspectRatio recommendedWidth homepage section
slider list (duplicatable) null 1920:740 1180 Hero slider
our-experts list (duplicatable) null 325:356 280 Home therapists / experts row
two-service-banner list 2 540:312 560 Dual promo banners under services

Field → UI mapping (match original homepage; empty API → local placeholders):

  • slider: url → slide image; linkUrl → wrap slide. titleFa / titleEn / subtext not rendered in hero (image-only).
  • our-experts: url → photo; linkUrl → card link (fallback /ourdr); titleFa → name (h3); subtext → role (p). titleEn not shown (original therapist cards have no English line).
  • two-service-banner: url → banner background; linkUrl → CTA href; titleFa → banner title (h3). titleEn / subtext not shown on banners.

Service icons on the homepage stay local (serviceCards in src/data/site.ts) — not a Meshkee static-image slot.

Rules:

  • Use slot.images (all if kind=list, first if kind=single)
  • url → <img src>; linkUrl → wrap in link
  • Empty / fail → keep local placeholders from src/data/site.ts / public/images/
  • Use slot.aspectRatio (via parseAspectRatio)
  • If a slot’s on-page size or aspect ratio changes in CSS, update STATIC_IMAGE_SLOTS in the same change (Meshkee reads the catalog as the static-image source of truth)

Helpers: src/lib/static-images.ts, src/components/SlotImage.tsx, src/components/SlotLink.tsx
Home wiring: src/app/page.tsx

Content & assets

  • Site copy, therapists bios, phones, address, socials live in src/data/site.ts
  • Static workshop/article fallbacks in src/data/site.ts (used when API empty)
  • Logos, banners, therapist photos, icons in public/images/
  • Favicon: /favicon.png
  • Bottom row matches Safeteb-style Meshkee credit
  • Component: src/components/Footer.tsx → .meshkee-credit
  • Styles: src/app/globals.css
  • Links to https://meshkee.com
  • Logo: public/images/footer/MeshkeeLogo-White.png

Important paths

  • Layout / shell: src/app/layout.tsx, src/components/Providers.tsx
  • Header + account: src/components/Header.tsx, src/components/AccountMenu.tsx
  • Footer: src/components/Footer.tsx
  • Home: src/app/page.tsx, src/components/HeroSlider.tsx, src/components/HomeSections.tsx
  • Blog: src/app/blog/, src/components/ArticlesCarousel.tsx
  • Workshops: src/app/workshops/, src/components/WorkshopGallery.tsx, src/components/WorkshopRegistration.tsx, src/components/EntityTabs.tsx
  • Config: src/lib/config.ts
  • Data: src/data/site.ts

Contact

  • Phones: 025-32706211, 025-32702623, 09936221511
  • Address: بنیاد - میدان جوان - بلوار آفرینش - خیابان ذوالفقار - نبش کوچه ۳
  • Socials: Instagram @Psy.samen, WhatsApp, Telegram, Eitaa
  • Map embed: OpenStreetMap iframe on contact page

Env

NEXT_PUBLIC_WEBSITE_DOMAIN=clinicsamen.com
NEXT_PUBLIC_MESHKEE_API_BASE=https://api.meshkee.com/api/v1
# Optional overrides:
# NEXT_PUBLIC_CUSTOMER_PORTAL_URL=https://customer.clinicsamen.com
# NEXT_PUBLIC_BUSINESS_ORIGIN=https://business.clinicsamen.com

Commands

npm install
npm run dev
npm run build

SEO canonical URLs

  • Blog: /blog/{id}/{titleSlug} → GET /blogs/by-id/{id}
  • Workshop: /workshops/{slug} → GET /workshops/{slug}
  • Slugify helper: src/lib/seo-slug.ts
  • Page metadata helper: src/lib/seo.ts → pageMetadata() (title, description, canonical, Open Graph)

Sitemap + robots

  • Do not add public/sitemap.xml or public/robots.txt (nginx proxies to Meshkee API)
  • Live sitemap index: /sitemap.xml → /sitemap-main.xml + CMS URLs
  • Static pages config: GET /meshkee/sitemap-config.json
  • Generated at build: scripts/generate-sitemap-config.mjs → src/lib/sitemap-config.generated.json
  • Run manually: npm run generate:sitemap-config
  • After deploy: business dashboard → Website → Settings → Sync sitemap config

On-page SEO rules

  • Unique <title> + meta description on every public page (via pageMetadata or generateMetadata)
  • Exactly one <h1> per page (homepage: header brand; inner pages: page hero)
  • Section headings use <h2> / <h3>
  • CMS images use meaningful alt (title when available)