react-19-compiler
npx machina-cli add skill JanSzewczyk/claude-plugins/react-19-compiler --openclawReact 19 & React Compiler Skill
React 19 patterns and React Compiler optimization guidance for Next.js applications.
Reference Files:
- compiler-guide.md - React Compiler capabilities and optimization
- when-to-memoize.md - When manual memoization is still needed
- hooks.md - useActionState, useFormStatus patterns
- server-components.md - Server vs Client Components
Project Configuration
This project has React Compiler enabled:
// next.config.ts
const nextConfig: NextConfig = {
experimental: {
reactCompiler: true,
},
};
With React Compiler enabled, you can safely remove most manual memoization (useMemo, useCallback, React.memo).
Quick Start
Let the Compiler Optimize
// ✅ Good - Let compiler handle optimization
function Component({ items, sortBy }) {
const sorted = [...items].sort((a, b) => a[sortBy] - b[sortBy]);
return <List items={sorted} />;
}
// ❌ Unnecessary with compiler
function Component({ items, sortBy }) {
const sorted = useMemo(() => {
return [...items].sort((a, b) => a[sortBy] - b[sortBy]);
}, [items, sortBy]);
return <List items={sorted} />;
}
Form Handling with useActionState
"use client";
import { useActionState } from "react";
import { submitForm } from "./actions";
function ContactForm() {
const [error, submitAction, isPending] = useActionState(
async (previousState, formData) => {
const result = await submitForm(formData);
if (!result.success) {
return result.error;
}
return null;
},
null
);
return (
<form action={submitAction}>
<input type="text" name="message" />
<SubmitButton />
{error && <p className="text-red-500">{error}</p>}
</form>
);
}
// ✅ useFormStatus must be in child component
function SubmitButton() {
const { pending } = useFormStatus();
return (
<button type="submit" disabled={pending}>
{pending ? "Sending..." : "Send"}
</button>
);
}
Key Concepts
React Compiler Benefits
The React Compiler:
- Automatically memoizes components and values at build time
- Eliminates need for manual
useMemo,useCallback,React.memo - Identifies bottlenecks and applies optimizations intelligently
- Reduces boilerplate and potential dependency-related bugs
When Manual Memoization IS Still Needed
See when-to-memoize.md for details. Key scenarios:
- External library callbacks - Non-React code expecting stable references
- Complex context values - When context updates trigger cascading re-renders
- Performance-critical loops - Thousands of items with expensive computations
New React 19 Hooks
| Hook | Purpose | Key Caveat |
|---|---|---|
useActionState | Form state management | Accepts async action, returns [state, action, isPending] |
useFormStatus | Form submission status | Must be called from child component inside <form> |
useOptimistic | Optimistic UI updates | For instant feedback before server confirmation |
File Locations
| Purpose | Location |
|---|---|
| Client components | features/*/components/*.tsx with "use client" |
| Server components | app/**/*.tsx, features/*/components/*.tsx (default) |
| Server actions | features/*/server/actions/*.ts |
React Compiler Configuration
The compiler is enabled in next.config.ts:
import type { NextConfig } from "next";
const nextConfig: NextConfig = {
experimental: {
reactCompiler: true,
},
};
export default nextConfig;
Migration Checklist
When working on this codebase:
- Remove unnecessary memoization - Let compiler handle it
- Keep memoization for external libs - Document why it's needed
- Use useActionState for forms - Replaces manual state + useTransition
- useFormStatus in child components - Not in same component as form
- Default to Server Components - Only add "use client" when needed
Running and Testing
# Type check
npm run type-check
# Dev server (compiler active)
npm run dev
# Production build (full optimization)
npm run build
Related Skills
server-actions- For implementing server actions with React 19 patternsstorybook-testing- For testing components with play functions
Source
git clone https://github.com/JanSzewczyk/claude-plugins/blob/main/plugins/nextjs-react/skills/react-19-compiler/SKILL.mdView on GitHub Overview
This skill covers React 19 patterns and React Compiler optimization guidance for Next.js apps. It explains when to rely on the compiler instead of manual memoization and how to use new hooks like useActionState and useFormStatus to manage form state and pending UI feedback.
How This Skill Works
With React Compiler enabled, the framework automatically memoizes components and values at build time, reducing the need for manual useMemo, useCallback, and React.memo. It identifies bottlenecks and applies optimizations intelligently, while you learn to use new hooks like useActionState for form actions and useFormStatus to reflect pending state in the UI.
When to Use It
- Relying on the React Compiler to optimize, removing most manual memoization
- External library callbacks require stable references for non-React code
- Complex or large context values that would otherwise trigger cascading re-renders
- Performance-critical loops with thousands of items and expensive computations
- Implementing forms with useActionState for async actions and useFormStatus for pending state in a child component
Quick Start
- Step 1: Enable React Compiler in next.config.ts (experimental: { reactCompiler: true })
- Step 2: Let the compiler optimize by removing most manual memoization (useMemo/useCallback/React.memo)
- Step 3: Implement form handling with useActionState and useFormStatus; place useFormStatus in a child component to reflect pending state
Best Practices
- Enable React Compiler in Next.js config and verify performance with real data
- Let the compiler handle most memoization; remove unnecessary useMemo, useCallback, and React.memo
- Retain manual memoization only for edge cases: external libraries, complex contexts, or heavy loops
- Use useActionState to manage form actions and move useFormStatus to a child to reflect pending state in the UI
- Cross-check guidance with the compiler docs (compiler-guide.md, when-to-memoize.md, hooks.md) and profile accordingly
Example Use Cases
- When should I use useMemo with React Compiler enabled
- How to use useActionState for form handling
- Implement form with useFormStatus for pending state
- Should I use React.memo with the compiler
- Understanding server vs client components with React Compiler