Covers React across supported versions (18 and 19): the component model, hooks system, virtual DOM and Fiber architecture, concurrent rendering features, Context API, error boundaries, rendering environments (client, server, static), React DevTools, React Compiler, Actions, and migration strategies. Use for \"React\", \"react\", \"JSX\", \"useState\", \"useEffect\", \"hooks\", \"React component\", \"virtual DOM\", \"React 18\", \"React 19\", \"React Compiler\" questions. Covers Server Compone...
Pro scans all 12 files and shows the line behind each finding
Scanned 9/24/2026
npx -y skills add chrishuffman5/domain-expert --skill react --agent claude-codeInstalls into .claude/skills of the current project.
Are you the author of React?
Add the live security badge to your README — it updates automatically with every re-scan.
[](https://www.skillsdirectory.com/skills/chrishuffman5-react)More formats (shields.io, HTML) on the badges page. Keep it an A: scan every change in CI with Pro.
---
name: react
description: "Covers React across supported versions (18 and 19): the component model, hooks system, virtual DOM and Fiber architecture, concurrent rendering features, Context API, error boundaries, rendering environments (client, server, static), React DevTools, React Compiler, Actions, and migration strategies. Use for \"React\", \"react\", \"JSX\", \"useState\", \"useEffect\", \"hooks\", \"React component\", \"virtual DOM\", \"React 18\", \"React 19\", \"React Compiler\" questions. Covers Server Components basics; for deep RSC patterns (boundary rules, serialization, composition, Server Actions) use the `react-server-components` skill instead."
license: MIT
---
# React
This skill covers React across all supported versions (18 and 19), including:
- Function components, JSX compilation, pure rendering model, and composition patterns
- Hooks system: rules, core hooks, custom hooks, dependency arrays, stale closures
- Virtual DOM, reconciliation (O(n) heuristic diffing), and keys
- Fiber architecture: fiber nodes, double buffering, interruptible rendering, priority lanes
- Concurrent features: `startTransition`, `useDeferredValue`, Suspense, automatic batching
- Context API: creating/consuming context, performance implications, selectors
- Error boundaries (class-only API) and React 19 improved error reporting
- Rendering environments: client (`createRoot`), server (streaming SSR), static (`prerender`), hydration
- React Compiler (React 19): automatic memoization, opt-in/out directives, ESLint plugin
- Actions (React 19): `useActionState`, `useOptimistic`, `useFormStatus`, form actions
- Server Components: RSC model, `"use client"` / `"use server"` directives, serialization, Server Actions
- Document metadata (React 19): `<title>`, `<meta>`, `<link>` hoisting, stylesheet precedence, resource preloading
- React DevTools: component tree, Profiler (flame/ranked charts), highlight updates
- State management ecosystem: Context+useReducer, Zustand, Jotai, Redux Toolkit, TanStack Query
When a question is version-specific, read the matching file under `references/versions/`. When the version is unknown, give general guidance and note where behavior differs across versions.
## How to Approach Tasks
When you receive a request:
1. **Classify** the request type:
- **Troubleshooting** -- Load `references/diagnostics.md`
- **Performance** -- Load `references/best-practices.md` (performance section)
- **Architecture / Design** -- Load `references/architecture.md`
- **Data Fetching** -- Load `references/patterns/data-fetching.md`
- **Forms** -- Load `references/patterns/forms.md`
- **State Management** -- Load `references/patterns/state-management.md`
- **Server Components** -- Use the `react-server-components` skill
- **Configuration** -- Reference `assets/tsconfig.json` or `assets/vite.config.ts`
2. **Identify version** -- Determine whether the user is on React 18 or 19. If unclear, ask. Version matters for available hooks, Compiler support, Server Component stability, and API shape.
3. **Load context** -- Read the relevant reference file for deep knowledge.
4. **Analyze** -- Apply React-specific reasoning, not generic JavaScript advice. Consider the rendering model, hook rules, component boundaries, and concurrent behavior.
5. **Recommend** -- Provide actionable guidance with code examples. Prefer idiomatic React patterns.
6. **Verify** -- Suggest validation steps (DevTools Profiler, console warnings, test assertions).
## Core Expertise
### Component Model
Function components are the standard. A function component accepts a `props` object and returns React elements (JSX). Props are read-only. State and side effects are managed through hooks.
```tsx
function Greeting({ name, children }: { name: string; children: React.ReactNode }) {
return (
<div>
<h1>Hello, {name}</h1>
{children}
</div>
);
}
```
Class components are supported but only recommended for error boundaries (the only class-only API). Custom hooks replace the mixin, HOC, and render prop patterns from older React.
JSX compiles to `jsx()` calls via the automatic runtime (React 17+). No `import React` needed in every file when using `"jsx": "react-jsx"` in tsconfig.
React assumes a pure rendering model: same props + state = same output. React Compiler (19) enforces purity automatically. StrictMode double-invokes render functions in development to surface violations.
Composition over inheritance: components compose by nesting, passing components as props, or using render props. Inheritance is not a React pattern.
### Virtual DOM and Fiber
React elements are lightweight JS objects describing the UI tree. The reconciler diffs old and new trees using two heuristics: same type = update in place, different type = unmount and remount. Keys stabilize list children across reorders.
Fiber (React 16+) replaced the synchronous recursive reconciler with an incremental, interruptible engine. Each component instance is a fiber node in a linked-list tree. React maintains two fiber trees (current and work-in-progress) for double buffering. Between units of work, React can pause and handle higher-priority updates.
Priority lanes (bit flags) classify updates: Sync (discrete input), Default (normal), Transition (`startTransition`), Deferred (`useDeferredValue`), Idle (offscreen Suspense).
### Hooks System
**Rules:** Call hooks only at the top level (never in loops/conditions/nested functions). Call hooks only from function components or custom hooks. ESLint plugin `eslint-plugin-react-hooks` enforces these rules.
**Core hooks:** `useState`, `useReducer`, `useEffect`, `useLayoutEffect`, `useContext`, `useRef`, `useMemo`, `useCallback`, `useImperativeHandle`, `useDebugValue`, `useSyncExternalStore`, `useId`, `useTransition`, `useDeferredValue`.
**React 19 hooks:** `useActionState`, `useOptimistic`, `useFormStatus`, `use()`.
**Dependency arrays:** `useEffect`, `useMemo`, `useCallback` re-run when deps change (shallow `Object.is`). Missing deps cause stale closures -- the most common React bug.
```tsx
// Stale closure bug
useEffect(() => {
const id = setInterval(() => setCount(count + 1), 1000); // count is stale
return () => clearInterval(id);
}, []); // missing count dependency
// Fix: functional updater
useEffect(() => {
const id = setInterval(() => setCount(c => c + 1), 1000);
return () => clearInterval(id);
}, []);
```
**Custom hooks** extract reusable stateful logic into `use*` functions. They can call other hooks and compose effects.
```tsx
function useLocalStorage<T>(key: string, initialValue: T) {
const [value, setValue] = useState<T>(() => {
try { return JSON.parse(localStorage.getItem(key) ?? '') ?? initialValue; }
catch { return initialValue; }
});
const setStoredValue = useCallback((v: T) => {
setValue(v);
localStorage.setItem(key, JSON.stringify(v));
}, [key]);
return [value, setStoredValue] as const;
}
```
### Concurrent Features (React 18+)
`createRoot` enables concurrent mode (required; `ReactDOM.render` is removed in 19).
```tsx
import { createRoot } from 'react-dom/client';
const root = createRoot(document.getElementById('root')!);
root.render(<App />);
```
`startTransition` marks updates as non-urgent (interruptible). `useTransition` adds an `isPending` flag.
```tsx
import { startTransition, useState } from 'react';
function SearchPage() {
const [query, setQuery] = useState('');
const [results, setResults] = useState([]);
function handleInput(e: React.ChangeEvent<HTMLInputElement>) {
setQuery(e.target.value); // urgent
startTransition(() => {
setResults(computeResults(e.target.value)); // non-urgent
});
}
return <input value={query} onChange={handleInput} />;
}
```
`useDeferredValue` defers re-rendering of expensive children. Suspense catches promises and shows fallback UI. Automatic batching applies to all state updates regardless of origin (setTimeout, fetch, native events). `flushSync` opts out of batching.
### Context API
```tsx
const ThemeContext = createContext('light');
// React 18
<ThemeContext.Provider value="dark"><Page /></ThemeContext.Provider>
// React 19 (simplified)
<ThemeContext value="dark"><Page /></ThemeContext>
```
When a Provider's value changes (new object reference), all consumers re-render. Mitigate with: split contexts, memoize values, context selectors (third-party), or external state managers.
Use context for low-frequency data (theme, locale, auth). Use external managers for frequently-updated shared state.
### Error Boundaries
Class-only API. `getDerivedStateFromError` + `componentDidCatch` catch render errors in the subtree.
```tsx
class ErrorBoundary extends React.Component {
state = { hasError: false };
static getDerivedStateFromError(error) { return { hasError: true }; }
componentDidCatch(error, info) { logErrorToService(error, info.componentStack); }
render() {
if (this.state.hasError) return this.props.fallback ?? <h2>Something went wrong.</h2>;
return this.props.children;
}
}
// Usage
<ErrorBoundary fallback={<ErrorPage />}>
<CriticalFeature />
</ErrorBoundary>
```
Does not catch event handler errors, async errors outside rendering, or errors in the boundary itself. Use `react-error-boundary` library for a hooks-friendly wrapper.
### Rendering Environments
| Mode | API | Notes |
|---|---|---|
| Client | `createRoot` / `hydrateRoot` | Concurrent mode enabled |
| Streaming SSR (Node) | `renderToPipeableStream` | Streams HTML with Suspense boundaries |
| Streaming SSR (Edge) | `renderToReadableStream` | Web Streams for Deno/CF Workers/Bun |
| Static (React 19) | `prerender` / `prerenderToNodeStream` | Waits for all data before emitting HTML |
Streaming SSR sends the HTML shell immediately. Suspense fallbacks appear first; resolved content streams in with inline `<script>` tags.
```tsx
import { renderToPipeableStream } from 'react-dom/server';
const { pipe } = renderToPipeableStream(<App />, {
bootstrapScripts: ['/bundle.js'],
onShellReady() { pipe(response); },
});
```
Selective hydration (React 18+): Suspense boundaries hydrate independently; user-interacted areas are prioritized.
### Server Components (React 19)
Server Components render on the server with direct access to databases and APIs, shipping zero JavaScript to the client. Client Components (marked `"use client"`) handle interactivity.
```tsx
// Server Component (default, no directive)
export default async function UsersPage() {
const users = await db.users.findMany();
return <UserList users={users} />; // Client Component
}
// Client Component
"use client";
export function UserList({ users }) {
const [search, setSearch] = useState('');
// ... interactive filtering
}
```
Key rules: Server Components cannot use hooks or browser APIs. Client Components cannot import Server Components (but can receive them as `children`). Props crossing the boundary must be serializable. See the `react-server-components` skill for full coverage.
### React DevTools
Component tree inspector with props/state/context. Profiler with flame chart (render duration) and ranked chart (sort by time). "Why did this render?" toggle. Highlight updates flashes borders on re-rendering components. Hooks inspector shows current values.
## Common Pitfalls
**1. Defining components inside other components**
Creates a new type reference every render, causing full remount of the child subtree. Always define components at module scope or use `useMemo` if dynamic generation is truly required.
**2. Missing cleanup in useEffect**
Effects that create subscriptions, timers, or event listeners must return a cleanup function. StrictMode double-invocation in development exposes this -- if you see double subscriptions, you have a cleanup bug.
**3. Stale closures in callbacks and effects**
Callbacks capture state/props at creation time. If dependency arrays are incomplete, the callback holds old values. Use the `react-hooks/exhaustive-deps` ESLint rule. Use functional updaters for state that changes frequently.
**4. Object/array literals in JSX props**
`<Comp style={{ color: 'red' }} />` creates a new object every render, defeating `React.memo`. Hoist stable values to module scope or `useMemo`. React Compiler (19) handles this automatically.
**5. Unstable keys on lists**
Using array index as key on reorderable lists causes incorrect reconciliation. Use stable, unique identifiers (database IDs, slugs).
**6. Context value not memoized**
Passing `{{ theme, setTheme }}` as context value creates a new object each render, re-rendering all consumers. Wrap with `useMemo`.
**7. useEffect for derived state**
Computing values in effects that should be computed during render. Use `useMemo` for derived values, not `useEffect` + `setState` (which causes an unnecessary extra render and risks infinite loops).
**8. Multiple React instances in the bundle**
Monorepos or duplicate dependencies cause "Invalid Hook Call" errors. Libraries should list React as `peerDependency`. Configure bundler aliasing to deduplicate.
**9. Ignoring hydration mismatches**
Server/client render differences (dates, random values, locale formatting) cause hydration warnings and potential UI bugs. Use `useEffect` for client-only content, `suppressHydrationWarning` for intentional mismatches.
**10. "use client" placed too high in the tree**
Making layout or provider files Client Components cascades to the entire subtree, losing Server Component benefits. Push the directive to the smallest interactive leaf.
## Version-Specific Guidance
| Version | Reference | What's version-specific |
|---|---|---|
| 18 | `references/versions/18.md` | Concurrent rendering, Suspense, streaming SSR, automatic batching, new hooks (`useId`, `useSyncExternalStore`, `useInsertionEffect`), Strict Mode changes, migration to React 19 |
| 19 | `references/versions/19.md` | Actions, React Compiler 1.0, new hooks (`useActionState`, `useOptimistic`, `useFormStatus`, `use`), ref-as-prop, document metadata, Context as Provider, custom elements, removed APIs |
## Sibling Skill
For deep RSC coverage, use the `react-server-components` skill: rendering model, client/server boundary, serialization constraints, streaming, Server Actions, composition patterns, framework integration, diagnostics.
## Reference Files
Load these when you need deep knowledge for a specific area:
- `references/architecture.md` -- Component model, virtual DOM, Fiber, hooks, concurrent features, Context, error boundaries, rendering environments. Read for "how does X work" questions.
- `references/best-practices.md` -- Component patterns, performance optimization, accessibility, testing. Read for design and quality questions.
- `references/diagnostics.md` -- Hydration errors, performance debugging, build/runtime issues. Read when troubleshooting errors.
## Configuration References
- `assets/tsconfig.json` -- Annotated TypeScript configuration for React 19 projects
- `assets/vite.config.ts` -- Annotated Vite configuration with React plugin and Compiler integration
## Pattern Guides
- `references/patterns/data-fetching.md` -- Suspense, `use()`, TanStack Query, SWR patterns
- `references/patterns/forms.md` -- Actions, `useActionState`, `useOptimistic`, `useFormStatus`
- `references/patterns/state-management.md` -- Context+useReducer, Zustand, Jotai, Redux Toolkit, TanStack Query comparison
## Diagnostic Scripts
Ready-made build/dependency audit (read-only) in `scripts/`.
- `scripts/01-bundle-and-deps-audit.sh` -- Production build size, largest chunks, dependency vulns
Is this your skill, or is something wrong with this listing? Request removal or report an issue. Author removals are honored within 72 hours.
No comments yet. Be the first to comment!