Use when investigating any frontend issue before diagnosis or debugging — maps a Next.js route to its full component tree. Resolves "what components render on this page," "show me the component tree for /dashboard," or "trace imports for this route." Produces a ComponentMap artifact with server/client boundaries, props, hooks, data fetching, and styling metadata consumed by all downstream QA skills. Not for diagnosing bugs, fixing code, or generating tests — those are handled by specialist skills after mapping is complete.
Given a route, produce a depth-limited component tree with file paths, server/client boundaries, props, hooks, state management, data fetching patterns, and styling metadata. Output a ComponentMap artifact consumed by all downstream skills.
tsconfig.json, package.json, next.config.*.claude/qa-cache/component-maps/ for ComponentMap persistence/dashboard/settings)--depth N--fresh to bypass cache and rebuildapp/{route}/page.tsx or pages/{route}.tsx. Validate that the route contains only alphanumeric characters, hyphens, underscores, forward slashes, and brackets (for dynamic segments like [id]). Reject routes containing .., shell metacharacters, or null bytes.Copy this checklist and update as you complete each step:
Progress:
- [ ] Step 0: Check Cache
- [ ] Step 1: Resolve tsconfig Path Aliases
- [ ] Step 2: Identify Route Entry Points
- [ ] Step 3: Trace Imports (Depth-Limited)
- [ ] Step 4: Classify Completeness
- [ ] Step 5: Persist and Present
Note: If you've lost context of previous steps (e.g., after context compaction), check the progress checklist above. Resume from the last unchecked item. Re-read relevant reference files if needed.
.claude/qa-cache/component-maps/{route-slug}.json.references/caching-protocol.md.Using cached map ({age} old, {N} components, completeness: {level}) | --fresh to rebuild--fresh flag provided, skip cache entirely.tsconfig.json at the project root. If it has an extends field, read the parent config too.compilerOptions.paths and compilerOptions.baseUrl.{ "@/*": "./src/*", "~/lib/*": "./lib/*" }.tsconfig.json is missing, warn the user and proceed with relative-path-only resolution.App Router (default -- app/ directory exists):
app/{route}/page.tsx (or .ts, .jsx, .js).layout.tsx, loading.tsx, error.tsx, not-found.tsx in the same directory and parent directories up to app/layout.tsx.Pages Router (fallback -- pages/ directory, no app/):
pages/{route}.tsx (or pages/{route}/index.tsx).pages/_app.tsx and pages/_document.tsx.getServerSideProps or getStaticProps exports.Default depth: 3 levels from route entry. Override with --depth N.
For each file, starting from the entry points found in Step 2:
'use client' or 'use server' directives../Button): try .tsx, .ts, .jsx, .js, /index.tsx, /index.ts@/components/Button): resolve using the Step 1 lookup table, then try extensionsreact, next/link, @radix-ui/*): record as external, stop tracingnext/dynamic(() => import(...)), React.lazy): trace literal paths, flag isDynamic: trueimport { X } from './components'): follow re-export through index files, cap at 5 levelsreferences/import-tracing-protocol.md.displayName: the component function/const nameboundary: "server" (has 'use server' or in app/ without directive), "client" (has 'use client'), "shared" (no directive, outside app/)props: from TypeScript type annotation on the component parameterhooks: all useXxx( callsstateManagement: imports from zustand, jotai, recoil, @tanstack/react-query, or React context usagedataFetching: fetch() calls, server actions, tRPC calls, React Query hooks, SWR hooksstyling_approach: based on import type (.module.css -> css-modules, tailwind classes in JSX -> tailwind)has_conditional_classes: clsx(, cn(, classNames(, or ternary in classNamedesign_system_component: true if imported from a known UI libraryaccepts_className_prop: true if props type includes classNamelayout_role: infer from file location and component nameunresolved: true, unresolvedReason: "depth-limit"."full": unresolvedImports array is empty"shallow": all unresolved entries have reason "depth-limit""partial": any unresolved entry has a non-depth reason ("dynamic-computed", "barrel-depth-exceeded", "not-found")cachedFiles array..claude/qa-cache/component-maps/{route-slug}.json.Component Map: /dashboard/settings (depth 3, shallow)
Entry: app/dashboard/settings/page.tsx [server]
Layout: app/dashboard/layout.tsx [server]
23 components mapped | 4 unresolved (depth-limit) | 2 external (shadcn)
Server (8): SettingsPage, SettingsLayout, AccountSection, ...
Client (12): ThemeToggle, NotificationForm, ProfileEditor, ...
Shared (3): Button, Card, Input
Data flow: 2 server actions, 1 React Query hook, 3 prop chains
Hooks: useState(5), useEffect(3), useForm(2), useQuery(1)
The ComponentMap JSON follows the schema in the design document. Key fields:
{
"version": "1.0",
"route": "/dashboard/settings",
"depth": 3,
"completeness": "shallow",
"framework": { "name": "next", "routerType": "app", "version": "14.1.0" },
"entryComponent": {
"filePath": "/abs/path/app/dashboard/settings/page.tsx",
"displayName": "SettingsPage",
"boundary": "server",
"imports": [{ "targetPath": "...", "importType": "component" }]
},
"unresolvedImports": [{ "sourcePath": "...", "importSpecifier": "./DeepChild", "reason": "depth-limit" }],
"cachedFiles": ["..."]
}
Pass the ComponentMap artifact path to qa-coordinator. The map contains the full component tree with boundary, hooks, dataFetching, and styling_approach fields consumed by ui-bug-investigator and css-layout-debugger.
| Path | Load Condition | Content Summary |
|------|---------------|-----------------|
| references/caching-protocol.md | Step 0, when cache file exists | Cache validity rules, TTL, invalidation triggers |
| references/import-tracing-protocol.md | Step 3, always | Path alias resolution, barrel handling, dynamic imports, boundary rules |
Search for places (restaurants, cafes, etc.) via Google Places API proxy on localhost.
Interact with GitHub using the `gh` CLI. Use `gh issue`, `gh pr`, `gh run`, and `gh api` for issues, PRs, CI runs, and advanced queries.
Create or update AgentSkills. Use when designing, structuring, or packaging skills with scripts, references, and assets.
Start voice calls via the OpenClaw voice-call plugin.
Notion API for creating and managing pages, databases, and blocks.
Gemini CLI for one-shot Q&A, summaries, and generation.
Category:developer