l-add-product-page
Add new product detail pages to the Takazudo Modular website. Use when: (1) User wants to add a new product, (2) User says 'add product page' or 'new product'. Handles both single products and multi-v...
Add Product Detail Page
Guide the user through adding products to the Takazudo Modular website. Supports two patterns:
Product Patterns
Pattern A: Single Product
One product entry, one detail page. E.g., a single module or accessory.
Pattern B: Multi-Variant Product
Multiple product entries sharing one detail page. E.g., color/size variations like ZB60 (9 color×rail variants -> 1 page) or Iromihon-ACR (7 colors × 2 sizes = 14 entries -> 1 page).
Indicators of Pattern B:
- Multiple colors, sizes, or configurations
- User mentions “variations”, “colors”, “sets”
- Similar to existing ZB60 or Iromihon-ACR patterns
Information Gathering
Ask one question at a time:
- Product name/slug - URL-friendly identifier (kebab-case)
- Display name - Japanese product name
- Brand - From
src/data/brands.mjs(e.g.,takazudo,addac,oxi-instruments) - Description - Short Japanese description (1-2 sentences)
- Specs - Width (HP), materials, etc.
- Price - Including tax and shipping (integer, e.g., 7980)
- Is this a multi-variant product? - If yes, gather variant details (colors, sizes, etc.)
- Images - Check what images are available in
/static/images/p/
Step 1: Add to Master Data (src/data/product-master-data.mjs)
New products go at the TOP of the allProducts array.
Single Product Entry
{
slug: 'product-slug',
name: 'Product Name',
brand: 'takazudo',
brandBasedCategory: 'category-name',
imgSrc: '/images/p/image-slug',
description: 'Japanese description.',
detailHref: '/products/product-slug/',
price: 7980,
mercariProductId: '',
spec: { width: '40HP' },
tags: ['takazudo-modular', 'relevant-tag'],
}
Multi-Variant Entries
All variants share the same detailHref:
// All point to the same detail page
{
slug: 'product-color-s',
name: 'Product Color-S',
brandBasedCategory: 'product-series', // New category for this series
detailHref: '/products/product-intro/', // SHARED across all variants
// ... other fields unique per variant (imgSrc, description, price)
}
brandBasedCategory Rules
- For new product series: create a new category (e.g.,
iromihon-acr,zudo-block-60) - For adding to existing category: use existing value (e.g.,
simpleBlankPanel,modules) - Categories determine grouping on the brand page at
/brands/takazudo/
Step 2: Update Brand Page (Takazudo products only)
File: components/brand/variants/brand-page-takazudo.tsx
If a new brandBasedCategory was created, add a BrandProductSection:
<BrandProductSection
title="Product Series Name"
titleSub="日本語サブタイトル"
products={products['new-category'] || []}
/>
Place it in the appropriate position among existing sections.
Step 3: Create MercariNav Component (Multi-variant only)
For multi-variant products, create a dedicated MercariNav component:
File: components/mdx/{product-series}-mercari-nav.tsx
import * as React from 'react';
import { MercariNav } from './mercari-nav';
export const ProductSeriesMercariNav: React.FC = () => {
return (
<MercariNav
ids={['variant-slug-1', 'variant-slug-2', ...]}
/>
);
};
Then register in components/mdx/mdx-provider.tsx:
- Add import
- Add to
componentsobject
Step 4: Create MDX File
Location: src/mdx/products/{slug}-intro.mdx (NOT in src/mdx/notes/)
Frontmatter
---
title: "Takazudo Modular: Product Name"
description: >-
Takazudo Modular: Product Nameの紹介記事です。Short description here.
imgThumb: image-slug
avoidListing: false
product: primary-variant-slug
productNameBread: Series Name # For multi-variant: breadcrumb label
tags:
- takazudo-modular
- relevant-tag
categories:
- products-intro
contentType: products
createdAt: "YYYY-MM-DD"
updatedAt: null
---
product: References a slug from master data (use primary variant for multi-variant)productNameBread: Set when multiple variants share one page (overrides breadcrumb)imgThumb: Whennull, auto-usesimgSrcfrom master data
Content Structure
{Introduction paragraph}
{Purchase link - MercariNav or custom MercariNav component}
## TOC
## 商品写真
{Product photos using ImgsGrid/ExImg components}
## 概要
{Product overview}
## セット内容 / 仕様
{Specifications and contents}
## カラーバリエーション (if multi-variant)
{Color/variant list}
## 開発の背景
{Development background}
<Outro>
{Closing text with MercariNav}
</Outro>
Photo Display for Multi-Variant
Use ImgsGrid with captions to organize by variant:
<ImgsGrid
srcs={['variant-a-img', 'variant-b-img']}
alts={['Variant A', 'Variant B']}
captions={['Variant-A', 'Variant-B']}
extraWide />
Step 5: Build and Validate
- Run
pnpm build:metadata(picks up new images) - Run
pnpm check(typecheck + lint + format + MDX validation) - Run
pnpm test:unitfor confidence - Fix any issues with
pnpm check:fix
Notes
- File naming: Always kebab-case
- Prices: Integers including tax/shipping (e.g., 2980 for \2,980)
- mercariProductId: Leave empty (
'') if not yet listed on Mercari - Images: Must exist in
/static/images/p/{slug}/with processed variants. Runpnpm convimgsthenpnpm build:metadatafor new images - Product slugs: Must be unique, kebab-case, never change after creation
- Brand must exist in
src/data/brands.mjsbefore adding products
Related Skills
/l-add-mercari-item- Create Mercari listing after product page exists/l-add-brand- Add a new brand first if needed