npx claudepluginhub parhumm/jaan-to --plugin jaan-toThis skill is limited to using the following tools:
> Convert designs and specs into production-ready React/Next.js component scaffolds with typed API hooks.
Creates isolated Git worktrees for feature branches with prioritized directory selection, gitignore safety checks, auto project setup for Node/Python/Rust/Go, and baseline verification.
Executes implementation plans in current session by dispatching fresh subagents per independent task, with two-stage reviews: spec compliance then code quality.
Dispatches parallel agents to independently tackle 2+ tasks like separate test failures or subsystems without shared state or dependencies.
Convert designs and specs into production-ready React/Next.js component scaffolds with typed API hooks.
$JAAN_CONTEXT_DIR/tech.md - Tech stack context (CRITICAL — determines framework, styling, versions)
#current-stack, #frameworks, #constraints$JAAN_CONTEXT_DIR/design.md - Design system guidelines (optional)$JAAN_CONTEXT_DIR/brand.md - Brand guidelines (optional)$JAAN_TEMPLATES_DIR/jaan-to-frontend-scaffold.template.md - Output template$JAAN_LEARN_DIR/jaan-to-frontend-scaffold.learn.md - Past lessons (loaded in Pre-Execution)${CLAUDE_PLUGIN_ROOT}/docs/extending/language-protocol.md - Language resolution protocol${CLAUDE_PLUGIN_ROOT}/docs/extending/frontend-ui-workflow-reference.md - Shared UI workflow reference (CSF3 format)Upstream Artifacts: $ARGUMENTS
Accepts 1-3 file paths or descriptions:
/jaan-to:frontend-design output)/jaan-to:frontend-task-breakdown output)/jaan-to:backend-api-contract output)/jaan-to:ux-microcopy-write outputMANDATORY — Read and execute ALL steps in: ${CLAUDE_PLUGIN_ROOT}/docs/extending/pre-execution-protocol.md
Skill name: frontend-scaffold
Execute: Step 0 (Init Guard) → A (Load Lessons) → B (Resolve Template) → C (Offer Template Seeding)
Also read context files if available:
$JAAN_CONTEXT_DIR/tech.md — Know the tech stack for framework-specific code generation$JAAN_CONTEXT_DIR/design.md — Know the design system patterns$JAAN_CONTEXT_DIR/brand.md — Know brand colors, fonts, toneRead and apply language protocol: ${CLAUDE_PLUGIN_ROOT}/docs/extending/language-protocol.md
Override field for this skill: language_frontend-scaffold
Language exception: Generated code output (variable names, code blocks, schemas, SQL, API specs) is NOT affected by this setting and remains in the project's programming language.
ultrathink
Use extended reasoning for:
For each provided path:
Present input summary:
INPUT SUMMARY
─────────────
Sources Found: {list}
Sources Missing: {list with fallback suggestions}
Components: {extracted component names with atomic level}
API Endpoints: {count from API contract}
TypeScript Types: {count derivable from schemas}
Read $JAAN_CONTEXT_DIR/tech.md:
#current-stack (default: React v19 + Next.js v15)Storybook detection (check alongside tech stack):
Glob: .storybook/main.* — Storybook installed?Grep: "storybook" package.json — Storybook in devDependencies?Glob: src/**/*.stories.tsx — Existing stories pattern?storybook_available = true (used in Steps 5, Phase 2 Output, Step 8)Read $JAAN_CONTEXT_DIR/design.md and $JAAN_CONTEXT_DIR/brand.md if available:
AskUserQuestion for items not in tech.md or design.md:
Present component tree with atomic design levels:
COMPONENT TREE
══════════════
STACK: {framework} + {styling} + {state_management}
COMPONENTS ({count} total)
──────────────────────────
Atoms: {list with estimates}
Molecules: {list with estimates}
Organisms: {list with estimates}
Templates: {list}
Pages: {list}
API HOOKS ({count})
───────────────────
{list of TanStack Query hooks with endpoints}
TYPES ({count})
───────────────
{list of TypeScript interfaces from API schemas}
STORIES ({count} — if Storybook detected)
──────────────────────────────────────────
{list of CSF3 story files to generate, one per component}
Use AskUserQuestion:
Do NOT proceed to Phase 2 without explicit approval.
All files in $JAAN_OUTPUTS_DIR/frontend/scaffold/{id}-{slug}/:
{id}-{slug}/
├── {id}-{slug}.md # Main doc (architecture + component map)
├── {id}-{slug}-components.tsx # React components
├── {id}-{slug}-hooks.ts # Typed API client hooks
├── {id}-{slug}-types.ts # TypeScript interfaces from API schemas
├── {id}-{slug}-pages.tsx # Page layouts / routes
├── {id}-{slug}-config.ts # Package.json + tsconfig + tailwind config
├── {id}-{slug}-stories.tsx # CSF3 Storybook stories (if Storybook detected)
├── {id}-{slug}-orval-config.ts # → project root: orval.config.ts
├── {id}-{slug}-msw-handlers.ts # → src/mocks/handlers.ts
├── {id}-{slug}-msw-browser.ts # → src/mocks/browser.ts
├── {id}-{slug}-msw-server.ts # → src/mocks/server.ts
└── {id}-{slug}-readme.md # Setup + run instructions
Include Source → Destination mapping table in {id}-{slug}-readme.md for dev-output-integrate to consume.
When an API contract (OpenAPI spec) is available from inputs:
Generate {id}-{slug}-orval-config.ts — Orval configuration:
input.target: relative path to the spec fileoutput.client: 'react-query' (TanStack Query v5)output.target: './src/lib/api/generated'output.schemas: './src/lib/api/schemas'output.mock: true (generates MSW handlers)output.mode: 'tags-split'Generate {id}-{slug}-msw-handlers.ts — MSW request handlers from spec:
import { http, HttpResponse } from 'msw'Generate {id}-{slug}-msw-browser.ts — MSW browser setup:
import { setupWorker } from 'msw/browser';
import { handlers } from './handlers';
export const worker = setupWorker(...handlers);
Generate {id}-{slug}-msw-server.ts — MSW Node.js server setup:
import { setupServer } from 'msw/node';
import { handlers } from './handlers';
export const server = setupServer(...handlers);
Update {id}-{slug}-config.ts: add to devDependencies: orval, msw, msw-storybook-addon. Add script: "generate:api": "orval --config ./orval.config.ts".
Reference: See
${CLAUDE_PLUGIN_ROOT}/docs/extending/openapi-integration-reference.mdfor Orval config patterns, MSW handler patterns, and flat output conventions.
Read $JAAN_TEMPLATES_DIR/jaan-to-frontend-scaffold.template.md and populate all sections based on Phase 1 analysis.
If tech stack needed, extract sections from tech.md:
#current-stack#frameworks#constraintsValidate generated output against checklist:
'use client' only where neededbabel-plugin-react-compiler when reactCompiler: true)storybook_available) — see ${CLAUDE_PLUGIN_ROOT}/docs/extending/frontend-ui-workflow-reference.md section "CSF3 Story Format Spec"If any check fails, fix before preview.
Present generated output summary. Use AskUserQuestion:
source "${CLAUDE_PLUGIN_ROOT}/scripts/lib/id-generator.sh"
SUBDOMAIN_DIR="$JAAN_OUTPUTS_DIR/frontend/scaffold"
mkdir -p "$SUBDOMAIN_DIR"
NEXT_ID=$(generate_next_id "$SUBDOMAIN_DIR")
slug="{project-name-slug}"
OUTPUT_FOLDER="${SUBDOMAIN_DIR}/${NEXT_ID}-${slug}"
Preview output configuration:
Output Configuration
- ID: {NEXT_ID}
- Folder:
$JAAN_OUTPUTS_DIR/frontend/scaffold/{NEXT_ID}-{slug}/- Main file:
{NEXT_ID}-{slug}.md
mkdir -p "$OUTPUT_FOLDER"$OUTPUT_FOLDERsource "${CLAUDE_PLUGIN_ROOT}/scripts/lib/index-updater.sh"
add_to_index \
"$SUBDOMAIN_DIR/README.md" \
"$NEXT_ID" \
"${NEXT_ID}-${slug}" \
"{Project Title}" \
"{Executive summary — 1-2 sentences}"
Scaffold written to:
$JAAN_OUTPUTS_DIR/frontend/scaffold/{NEXT_ID}-{slug}/Index updated:$JAAN_OUTPUTS_DIR/frontend/scaffold/README.md
Scaffold generated successfully!
Next Steps:
- Copy scaffold files to your project directory
- Run
npm installto install dependencies- Run
/jaan-to:frontend-story-generateto generate additional Storybook stories- Run
/jaan-to:frontend-visual-verifyto visually verify components (requires Playwright MCP)- Run
/jaan-to:dev-output-integrateto integrate scaffold into project- Run
/jaan-to:qa-test-casesto generate test cases
Use AskUserQuestion:
If "Learn from this": Run /jaan-to:learn-add frontend-scaffold "{feedback}"
React 19 Patterns (CRITICAL — differs from React 18):
'use client' when neededasync/await in Server Components, NOT useEffect + useStateuse(promise) with Suspense, NOT useEffect; never create promises during render (infinite loops)ref is a regular prop, NOT forwardRefuseMemo/useCallback/React.memo; enable in next.config.ts with { reactCompiler: true }; requires babel-plugin-react-compiler in devDependencies; up to 12% faster initial loadsuseActionState + useFormStatus (must be in child component of <form>) for formsdefaultProps)<Context.Provider> deprecated — use <Context> directlyref callbacks support cleanup functionsTailwindCSS v4 Patterns:
@import "tailwindcss" + @theme { } — NO tailwind.config.js@custom-variant dark (&:where(.dark, .dark *)) + next-themescn() helper (clsx + tailwind-merge), OKLCH colors!bg-red-500 → bg-red-500! (suffix), @layer utilities → @utility, bg-[--my-var] → bg-(--my-var); requires Safari 16.4+, Chrome 111+, Firefox 128+@tailwindcss/postcss as single plugin — autoprefixer is built-incontent array)Component Generation:
aria-* on all interactive elements<button>, <nav>, <main>) before ARIA; enforce with eslint-plugin-jsx-a11yAPI Integration:
useQuery/useMutation with auto-generated keys)openapi-typescript (~1.68M weekly downloads) generates only TypeScript types with zero runtime; companion openapi-fetch provides type-safe createClient<paths>() wrapper; requires manually writing TanStack Query hooks but offers more controlHydrationBoundary for RSC → client data handoff (prefetch with queryClient.prefetchQuery(), dehydrate cache, wrap in <HydrationBoundary state={dehydrate(queryClient)}>)queryOptions() factories for type-safe, reusable query definitions with hierarchical key factoriessrc/lib/api/generated/ — treated as dependency, never hand-edited"generate:api": "orval --config ./orval.config.ts" to package.jsonState Management:
useState/useReducernuqs v2.5+ (used by Sentry, Supabase, Vercel); type-safe parsers, server-side via createLoader()useActionState + useFormStatususeOptimistic (React 19); instant UI feedback, auto-reconcile or rollbackNext.js 15 Caching:
fetch() defaults to no-store (was force-cache in v14); opt into caching with cache: 'force-cache' or next: { revalidate: 3600 }unstable_cache deprecated — use 'use cache' directive with cacheTag() and cacheLife()route.ts) for external consumerseslint.config.mjs) replaces .eslintrc.jsonCSF3 Story Patterns (when storybook_available):
Reference: See
${CLAUDE_PLUGIN_ROOT}/docs/extending/frontend-ui-workflow-reference.mdfor CSF3 format spec, CVA variant detection, argTypes controls, and state coverage matrix.
{ComponentName}.stories.tsx per componentMeta<typeof Component> + StoryObj<typeof meta> patternargs objects only (no render functions)*.stories.tsx filesReact 19: useEffect for data fetching, forwardRef, manual memoization (useMemo/useCallback/React.memo), defaultProps, PropTypes, <Context.Provider>
Next.js 15: 'use client' everywhere, API routes for internal mutations, unstable_cache (deprecated — use 'use cache' directive with cacheTag()/cacheLife()), next lint (removed in Next.js 16 — use ESLint CLI with eslint.config.mjs flat config)
TailwindCSS v4: tailwind.config.js, dynamic class construction, @tailwind directives, v3 bang syntax (!bg-red-500), @layer utilities
Accessibility: <div onClick>, missing alt, color-only indicators, missing form labels
Production: react ^19, react-dom ^19, next ^15, @tanstack/react-query ^5.60, zustand ^5, nuqs ^2.5, next-themes ^0.4, clsx ^2.1, tailwind-merge ^2.6, zod ^3.23, axios ^1.7
Dev: typescript ^5.7, @types/react ^19, @types/node ^22, @tailwindcss/postcss ^4, tailwindcss ^4, eslint ^9, prettier ^3.4, orval ^7, vitest ^2, @testing-library/react ^16, eslint-plugin-jsx-a11y, babel-plugin-react-compiler (when reactCompiler: true)
tech.md detection$JAAN_OUTPUTS_DIR path'use client' only where needed