Files
klz-cables.com/app/[locale]/products/[...slug]/page.tsx
2026-01-17 01:50:54 +01:00

144 lines
5.5 KiB
TypeScript

import { notFound } from 'next/navigation';
import { MDXRemote } from 'next-mdx-remote/rsc';
import { getProductBySlug, getAllProducts } from '@/lib/mdx';
import ProductTechnicalData from '@/components/ProductTechnicalData';
import ProductTabs from '@/components/ProductTabs';
import RequestQuoteForm from '@/components/RequestQuoteForm';
import RelatedProducts from '@/components/RelatedProducts';
import Link from 'next/link';
interface ProductPageProps {
params: {
locale: string;
slug: string[];
};
}
const components = {
ProductTechnicalData,
ProductTabs,
p: (props: any) => <div {...props} className="mb-4" />,
table: (props: any) => (
<div className="overflow-x-auto my-8">
<table {...props} className="min-w-full divide-y divide-neutral-dark border border-neutral-dark" />
</div>
),
};
export default async function ProductPage({ params }: ProductPageProps) {
const { locale, slug } = params;
const productSlug = slug[slug.length - 1];
// Check if it's a category page
const categories = ['low-voltage-cables', 'medium-voltage-cables', 'high-voltage-cables', 'solar-cables'];
if (categories.includes(productSlug)) {
const allProducts = await getAllProducts(locale);
const categoryTitle = productSlug.split('-').map(word => word.charAt(0).toUpperCase() + word.slice(1)).join(' ');
// Filter products for this category
// Note: MDX categories are like "Low Voltage Cables"
const filteredProducts = allProducts.filter(p =>
p.frontmatter.categories.some(cat => cat.toLowerCase().replace(/\s+/g, '-') === productSlug)
);
return (
<div className="container mx-auto px-4 py-12">
<h1 className="text-4xl font-bold text-primary mb-8">{categoryTitle}</h1>
<div className="grid grid-cols-1 md:grid-cols-2 lg:grid-cols-3 gap-8">
{filteredProducts.map((product) => (
<Link
key={product.slug}
href={`/${locale}/products/${productSlug}/${product.slug}`}
className="group block bg-white rounded-lg overflow-hidden shadow-sm hover:shadow-md transition-all border border-neutral-dark"
>
<div className="aspect-[4/3] relative bg-neutral-light">
{product.frontmatter.images?.[0] && (
<img
src={product.frontmatter.images[0]}
alt={product.frontmatter.title}
className="w-full h-full object-contain p-4 group-hover:scale-105 transition-transform duration-300"
/>
)}
</div>
<div className="p-6">
<h2 className="text-xl font-bold text-text-primary group-hover:text-primary transition-colors">
{product.frontmatter.title}
</h2>
<p className="text-text-secondary mt-2 line-clamp-2 text-sm">
{product.frontmatter.description}
</p>
</div>
</Link>
))}
</div>
</div>
);
}
const product = await getProductBySlug(productSlug, locale);
if (!product) {
notFound();
}
return (
<div className="container mx-auto px-4 py-8">
<div className="mb-8">
<h1 className="text-4xl font-bold text-primary mb-4">{product.frontmatter.title}</h1>
<div className="flex flex-wrap gap-2 mb-4">
{product.frontmatter.categories.map((cat, idx) => (
<span key={idx} className="bg-neutral-dark text-text-secondary px-2 py-1 rounded text-sm">
{cat}
</span>
))}
</div>
</div>
<div className="grid grid-cols-1 lg:grid-cols-3 gap-8">
<div className="lg:col-span-2">
{/* Main Content Area */}
<div className="bg-white p-6 rounded-lg shadow-sm border border-neutral-dark">
<MDXRemote source={product.content} components={components} />
</div>
{/* Related Products */}
<RelatedProducts
currentSlug={productSlug}
categories={product.frontmatter.categories}
locale={locale}
/>
</div>
<div className="lg:col-span-1">
<div className="sticky top-4 space-y-6">
{/* Image Gallery */}
{product.frontmatter.images && product.frontmatter.images.length > 0 && (
<div className="bg-white p-4 rounded-lg shadow-sm border border-neutral-dark">
<div className="relative aspect-square mb-4 bg-neutral-light rounded overflow-hidden">
<img
src={product.frontmatter.images[0]}
alt={product.frontmatter.title}
className="w-full h-full object-contain"
/>
</div>
{product.frontmatter.images.length > 1 && (
<div className="grid grid-cols-4 gap-2">
{product.frontmatter.images.slice(1, 5).map((img, idx) => (
<div key={idx} className="relative aspect-square border border-neutral-dark rounded overflow-hidden bg-neutral-light">
<img src={img} alt="" className="w-full h-full object-cover" />
</div>
))}
</div>
)}
</div>
)}
{/* Request Quote Form */}
<RequestQuoteForm productName={product.frontmatter.title} />
</div>
</div>
</div>
</div>
);
}