diff --git a/CONTEXT.md b/CONTEXT.md index 657d475..72c9735 100644 --- a/CONTEXT.md +++ b/CONTEXT.md @@ -65,7 +65,7 @@ Homepage images: `GET /tenants/{domain}/website/static-images?pageKey=home`. Cat `GET /tenants/{domain}/website/business-info` -- `metaTags`: `[{ name, content }]` emitted once from root `generateMetadata` as `other`. Empty → omit. +- `metaTags`: `[{ html }]` — each full `` tag is placed in the root ``. Empty → omit. - `trustBadges`: `[{ kind: "enamad" | "samandehi", embedHtml }]` rendered in the footer with `dangerouslySetInnerHTML`. Empty → omit. Do not hardcode eNamad or Samandehi placeholders. ## Local fallbacks diff --git a/app/layout.tsx b/app/layout.tsx index 12d9227..32d06af 100644 --- a/app/layout.tsx +++ b/app/layout.tsx @@ -6,7 +6,7 @@ import { Header } from "@/components/layout/Header"; import { Footer } from "@/components/layout/Footer"; import { getNavCategories } from "@/lib/categories"; import { getLogoSrc } from "@/lib/media"; -import { getBusinessInfo, metaTagsToOther } from "@/lib/meshkee"; +import { getBusinessInfo, parseMetaTagHtml } from "@/lib/meshkee"; const vazir = Vazirmatn({ subsets: ["arabic", "latin"], @@ -15,17 +15,11 @@ const vazir = Vazirmatn({ weight: ["300", "400", "500", "600", "700", "800"], }); -export async function generateMetadata(): Promise { - const businessInfo = await getBusinessInfo(); - const other = metaTagsToOther(businessInfo?.metaTags); - - return { - title: "داروخانه دکتر ارجمند | صفحه اصلی", - description: - "خرید آنلاین دارو، مکمل، محصولات بهداشتی و آرایشی از داروخانه دکتر ارجمند در قم، سالاریه.", - ...(other ? { other } : {}), - }; -} +export const metadata: Metadata = { + title: "داروخانه دکتر ارجمند | صفحه اصلی", + description: + "خرید آنلاین دارو، مکمل، محصولات بهداشتی و آرایشی از داروخانه دکتر ارجمند در قم، سالاریه.", +}; export default async function RootLayout({ children }: { children: React.ReactNode }) { const [logoSrc, categories, businessInfo] = await Promise.all([ @@ -34,9 +28,16 @@ export default async function RootLayout({ children }: { children: React.ReactNo getBusinessInfo(), ]); + const cmsMetaTags = (businessInfo?.metaTags ?? []).flatMap((tag, index) => { + const attrs = parseMetaTagHtml(tag.html ?? ""); + if (!attrs) return []; + return []; + }); + return ( + {cmsMetaTags} ` HTML from business-info. */ export type BusinessMetaTag = { - name: string; - content: string; + html: string; }; +/** Parse a single `` tag into React attribute props for the document head. */ +export function parseMetaTagHtml(html: string): Record | null { + const match = html.trim().match(/^]*)\/?\s*>$/i); + if (!match) return null; + const attrs: Record = {}; + const attrRe = /([:\w.-]+)(?:\s*=\s*(?:"([^"]*)"|'([^']*)'|([^\s"'=<>`]+)))?/g; + let found: RegExpExecArray | null; + while ((found = attrRe.exec(match[1]))) { + const key = found[1].toLowerCase(); + if (key === "/") continue; + attrs[key] = found[2] ?? found[3] ?? found[4] ?? ""; + } + return Object.keys(attrs).length > 0 ? attrs : null; +} + export type BusinessTrustBadge = { kind: "enamad" | "samandehi"; embedHtml: string; @@ -45,13 +60,3 @@ export type BusinessInfo = { export async function getBusinessInfo() { return meshkeeGet(tenantPath("/website/business-info"), null); } - -export function metaTagsToOther(tags: BusinessMetaTag[] | undefined) { - const other: Record = {}; - for (const tag of tags ?? []) { - const name = tag.name?.trim(); - const content = tag.content?.trim(); - if (name && content) other[name] = content; - } - return Object.keys(other).length > 0 ? other : undefined; -}