--- allowed-tools: Read, Write, Edit argument-hint: [component-name] [--client] [--server] [--page] [--layout] description: Generate optimized React components for Next.js with TypeScript and best practices --- ## Next.js Component Generator **Component Name**: $ARGUMENTS ## Project Context Analysis ### Framework Detection - Next.js config: @next.config.js - TypeScript config: @tsconfig.json (if exists) - Tailwind config: @tailwind.config.js (if exists) - Package.json: @package.json ### Existing Component Patterns - Components directory: @components/ - App directory: @app/ (if App Router) - Pages directory: @pages/ (if Pages Router) - Styles directory: @styles/ ## Component Generation Requirements ### 1. Component Type Detection Based on arguments and context, determine component type: - **Client Component**: Interactive UI with state/events (`--client` or default for interactive components) - **Server Component**: Static rendering, data fetching (`--server` or default for Next.js 13+) - **Page Component**: Route-level component (`--page`) - **Layout Component**: Shared layout wrapper (`--layout`) ### 2. File Structure Creation Generate comprehensive component structure: ``` components/[ComponentName]/ ├── index.ts # Barrel export ├── [ComponentName].tsx # Main component ├── [ComponentName].module.css # Component styles ├── [ComponentName].test.tsx # Unit tests ├── [ComponentName].stories.tsx # Storybook story (if detected) └── types.ts # TypeScript types ``` ### 3. Component Templates #### Server Component Template ```typescript import { FC } from 'react'; import styles from './ComponentName.module.css'; interface ComponentNameProps { /** * Component description */ children?: React.ReactNode; /** * Additional CSS classes */ className?: string; } /** * ComponentName - Server Component * * @description Brief description of component purpose * @example * Content */ export const ComponentName: FC = ({ children, className = '', ...props }) => { return (
{children}
); }; export default ComponentName; ``` #### Client Component Template ```typescript 'use client'; import { FC, useState, useEffect } from 'react'; import styles from './ComponentName.module.css'; interface ComponentNameProps { /** * Component description */ children?: React.ReactNode; /** * Click event handler */ onClick?: () => void; /** * Additional CSS classes */ className?: string; } /** * ComponentName - Client Component * * @description Interactive component with client-side functionality * @example * console.log('clicked')}> * Content * */ export const ComponentName: FC = ({ children, onClick, className = '', ...props }) => { const [isActive, setIsActive] = useState(false); const handleClick = () => { setIsActive(!isActive); onClick?.(); }; return ( ); }; export default ComponentName; ``` #### Page Component Template ```typescript import { Metadata } from 'next'; import ComponentName from '@/components/ComponentName'; export const metadata: Metadata = { title: 'Page Title', description: 'Page description', }; interface PageProps { params: { id: string }; searchParams: { [key: string]: string | string[] | undefined }; } export default function Page({ params, searchParams }: PageProps) { return (

Page Title

); } ``` #### Layout Component Template ```typescript import { FC } from 'react'; import styles from './Layout.module.css'; interface LayoutProps { children: React.ReactNode; /** * Page title */ title?: string; } /** * Layout - Shared layout component * * @description Provides consistent layout structure across pages */ export const Layout: FC = ({ children, title, }) => { return (
{title &&

{title}

}
{children}

© 2024 Your App

); }; export default Layout; ``` ### 4. CSS Module Templates #### Basic Component Styles ```css /* ComponentName.module.css */ .container { display: flex; flex-direction: column; padding: 1rem; border-radius: 8px; border: 1px solid #e2e8f0; background-color: #ffffff; } .button { display: inline-flex; align-items: center; justify-content: center; padding: 0.5rem 1rem; border-radius: 6px; border: 1px solid transparent; background-color: #3b82f6; color: white; font-weight: 500; cursor: pointer; transition: all 0.2s; } .button:hover { background-color: #2563eb; } .button:focus { outline: 2px solid #3b82f6; outline-offset: 2px; } .button.active { background-color: #1d4ed8; } /* Responsive design */ @media (max-width: 768px) { .container { padding: 0.75rem; } .button { padding: 0.75rem 1rem; } } ``` #### Layout Styles ```css /* Layout.module.css */ .layout { min-height: 100vh; display: grid; grid-template-rows: auto 1fr auto; } .header { padding: 1rem 2rem; background-color: #f8fafc; border-bottom: 1px solid #e2e8f0; } .title { margin: 0; font-size: 1.5rem; font-weight: 600; color: #1e293b; } .main { padding: 2rem; max-width: 1200px; margin: 0 auto; width: 100%; } .footer { padding: 1rem 2rem; background-color: #f1f5f9; border-top: 1px solid #e2e8f0; text-align: center; color: #64748b; } ``` ### 5. TypeScript Types ```typescript // types.ts export interface BaseComponentProps { children?: React.ReactNode; className?: string; 'data-testid'?: string; } export interface ButtonProps extends BaseComponentProps { variant?: 'primary' | 'secondary' | 'outline'; size?: 'sm' | 'md' | 'lg'; disabled?: boolean; loading?: boolean; onClick?: () => void; } export interface LayoutProps extends BaseComponentProps { title?: string; sidebar?: React.ReactNode; breadcrumbs?: BreadcrumbItem[]; } export interface BreadcrumbItem { label: string; href?: string; current?: boolean; } ``` ### 6. Unit Tests ```typescript // ComponentName.test.tsx import { render, screen, fireEvent } from '@testing-library/react'; import ComponentName from './ComponentName'; describe('ComponentName', () => { it('renders children correctly', () => { render(Test Content); expect(screen.getByText('Test Content')).toBeInTheDocument(); }); it('applies custom className', () => { render(Test); const element = screen.getByText('Test'); expect(element).toHaveClass('custom-class'); }); it('handles click events', () => { const handleClick = jest.fn(); render(Click me); const button = screen.getByText('Click me'); fireEvent.click(button); expect(handleClick).toHaveBeenCalledTimes(1); }); it('toggles active state on click', () => { render(Toggle); const button = screen.getByText('Toggle'); expect(button).not.toHaveClass('active'); fireEvent.click(button); expect(button).toHaveClass('active'); fireEvent.click(button); expect(button).not.toHaveClass('active'); }); it('is accessible', () => { render(Accessible Button); const button = screen.getByRole('button'); expect(button).toBeInTheDocument(); expect(button).toHaveAccessibleName('Accessible Button'); }); }); ``` ### 7. Storybook Stories (if detected) ```typescript // ComponentName.stories.tsx import type { Meta, StoryObj } from '@storybook/react'; import ComponentName from './ComponentName'; const meta: Meta = { title: 'Components/ComponentName', component: ComponentName, parameters: { layout: 'centered', docs: { description: { component: 'A reusable component built for Next.js applications.', }, }, }, tags: ['autodocs'], argTypes: { onClick: { action: 'clicked' }, className: { control: 'text' }, }, }; export default meta; type Story = StoryObj; export const Default: Story = { args: { children: 'Default Component', }, }; export const WithCustomClass: Story = { args: { children: 'Custom Styled', className: 'custom-style', }, }; export const Interactive: Story = { args: { children: 'Click me', onClick: () => alert('Component clicked!'), }, }; ``` ### 8. Barrel Export ```typescript // index.ts export { default } from './ComponentName'; export type { ComponentNameProps } from './ComponentName'; ``` ## Framework-Specific Optimizations ### Tailwind CSS Integration (if detected) Replace CSS modules with Tailwind classes: ```typescript export const ComponentName: FC = ({ children, className = '', }) => { return (
{children}
); }; ``` ### Next.js App Router Optimizations - **Server Components**: Default for non-interactive components - **Client Components**: Explicit 'use client' directive - **Metadata**: Include metadata for page components - **Loading States**: Implement loading.tsx for async components ### Accessibility Features - **ARIA Labels**: Proper labeling for screen readers - **Keyboard Navigation**: Tab order and keyboard shortcuts - **Focus Management**: Visible focus indicators - **Semantic HTML**: Proper semantic elements ## Component Generation Process 1. **Analysis**: Analyze existing project structure and patterns 2. **Template Selection**: Choose appropriate template based on component type 3. **Customization**: Adapt template to project conventions 4. **File Creation**: Generate all component files 5. **Integration**: Update index files and exports 6. **Validation**: Verify component compiles and tests pass ## Quality Checklist - [ ] Component follows project naming conventions - [ ] TypeScript types are properly defined - [ ] CSS follows established patterns (modules or Tailwind) - [ ] Unit tests cover key functionality - [ ] Component is accessible (ARIA, keyboard navigation) - [ ] Documentation includes usage examples - [ ] Storybook story created (if Storybook detected) - [ ] Component compiles without errors - [ ] Tests pass successfully Provide the complete component implementation with all specified files and features.