From dc9236eda173979f7ffe1c3c6bc4f626caa79b42 Mon Sep 17 00:00:00 2001 From: Arman Date: Fri, 18 Oct 2024 14:02:17 -0400 Subject: [PATCH] Add opengraph metadta for subcategories and products --- .../[subcategory]/[product]/page.tsx | 21 +++++++++++++ .../[category]/[subcategory]/page.tsx | 31 +++++++++++++++++++ 2 files changed, 52 insertions(+) diff --git a/src/app/(category-sidebar)/products/[category]/[subcategory]/[product]/page.tsx b/src/app/(category-sidebar)/products/[category]/[subcategory]/[product]/page.tsx index 357aa35..4d80ba6 100644 --- a/src/app/(category-sidebar)/products/[category]/[subcategory]/[product]/page.tsx +++ b/src/app/(category-sidebar)/products/[category]/[subcategory]/[product]/page.tsx @@ -4,6 +4,27 @@ import Image from "next/image"; import { notFound } from "next/navigation"; import { ne } from "drizzle-orm"; import { AddToCartForm } from "@/components/add-to-cart-form"; +import { Metadata } from "next"; + +export async function generateMetadata(props: { + params: Promise<{ product: string; category: string; subcategory: string }>; +}): Promise { + const { product: productParam } = await props.params; + const urlDecodedProduct = decodeURIComponent(productParam); + + const product = await db.query.products.findFirst({ + where: (products, { eq }) => eq(products.slug, urlDecodedProduct), + orderBy: (products, { asc }) => asc(products.name), + }); + + if (!product) { + return notFound(); + } + + return { + openGraph: { title: product.name, description: product.description }, + }; +} export default async function Page(props: { params: Promise<{ diff --git a/src/app/(category-sidebar)/products/[category]/[subcategory]/page.tsx b/src/app/(category-sidebar)/products/[category]/[subcategory]/page.tsx index dadfef9..bc009f9 100644 --- a/src/app/(category-sidebar)/products/[category]/[subcategory]/page.tsx +++ b/src/app/(category-sidebar)/products/[category]/[subcategory]/page.tsx @@ -3,6 +3,37 @@ import { ProductLink } from "@/components/ui/product-card"; import { db } from "@/db"; import { products } from "@/db/schema"; import { count, eq } from "drizzle-orm"; +import type { Metadata } from "next"; + +export async function generateMetadata(props: { + params: Promise<{ category: string; subcategory: string }>; +}): Promise { + const { subcategory: subcategoryParam } = await props.params; + const urlDecodedCategory = decodeURIComponent(subcategoryParam); + + const subcategory = await db.query.subcategories.findFirst({ + where: (subcategories, { eq }) => + eq(subcategories.slug, urlDecodedCategory), + orderBy: (categories, { asc }) => asc(categories.name), + }); + + const rows = await db + .select({ count: count() }) + .from(products) + .where(eq(products.subcategory_slug, urlDecodedCategory)); + + if (!subcategory) { + return notFound(); + } + + const description = rows[0]?.count + ? `Choose from over ${rows[0]?.count - 1} products in ${subcategory.name}. In stock and ready to ship.` + : undefined; + + return { + openGraph: { title: subcategory.name, description }, + }; +} export default async function Page(props: { params: Promise<{