Ai react-best-practices
install
source · Clone the upstream repo
git clone https://github.com/wpank/ai
Claude Code · Install into ~/.claude/skills/
T=$(mktemp -d) && git clone --depth=1 https://github.com/wpank/ai "$T" && mkdir -p ~/.claude/skills && cp -r "$T/skills/frontend/react-best-practices" ~/.claude/skills/wpank-ai-react-best-practices && rm -rf "$T"
manifest:
skills/frontend/react-best-practices/SKILL.mdsource content
React Best Practices
Comprehensive performance optimization guide for React and Next.js applications from Vercel Engineering. Contains 57 rules across 8 categories, prioritized by impact.
Installation
OpenClaw / Moltbot / Clawbot
npx clawhub@latest install react-best-practices
WHAT This Skill Does
Provides actionable rules for:
- Eliminating request waterfalls
- Optimizing bundle size
- Improving server-side performance
- Efficient client-side data fetching
- Minimizing re-renders
- Rendering performance optimizations
- JavaScript micro-optimizations
- Advanced patterns for edge cases
WHEN To Use
- Writing new React components or Next.js pages
- Implementing data fetching (client or server-side)
- Reviewing code for performance issues
- Refactoring React/Next.js applications
- Optimizing bundle size or load times
- Debugging slow renders or waterfalls
KEYWORDS
react performance, nextjs optimization, bundle size, waterfalls, suspense, server components, rsc, rerender, usememo, dynamic import, parallel fetching, cache, swr
Rule Categories by Priority
| Priority | Category | Impact | Rule Prefix |
|---|---|---|---|
| 1 | Eliminating Waterfalls | CRITICAL | |
| 2 | Bundle Size Optimization | CRITICAL | |
| 3 | Server-Side Performance | HIGH | |
| 4 | Client-Side Data Fetching | MEDIUM-HIGH | |
| 5 | Re-render Optimization | MEDIUM | |
| 6 | Rendering Performance | MEDIUM | |
| 7 | JavaScript Performance | LOW-MEDIUM | |
| 8 | Advanced Patterns | LOW | |
Quick Reference
1. Eliminating Waterfalls (CRITICAL)
| Rule | Description |
|---|---|
| Move await into branches where actually used |
| Use for independent operations |
| Use better-all for partial dependencies |
| Start promises early, await late in API routes |
| Use Suspense to stream content |
2. Bundle Size Optimization (CRITICAL)
| Rule | Description |
|---|---|
| Import directly, avoid barrel files |
| Use for heavy components |
| Load analytics/logging after hydration |
| Load modules only when feature is activated |
| Preload on hover/focus for perceived speed |
3. Server-Side Performance (HIGH)
| Rule | Description |
|---|---|
| Authenticate server actions like API routes |
| Use for per-request dedup |
| Use LRU cache for cross-request caching |
| Avoid duplicate serialization in RSC props |
| Minimize data passed to client components |
| Restructure components to parallelize fetches |
| Use for non-blocking operations |
4. Client-Side Data Fetching (MEDIUM-HIGH)
| Rule | Description |
|---|---|
| Use SWR for automatic request deduplication |
| Deduplicate global event listeners |
| Use passive listeners for scroll |
| Version and minimize localStorage data |
5. Re-render Optimization (MEDIUM)
| Rule | Description |
|---|---|
| Don't subscribe to state only used in callbacks |
| Extract expensive work into memoized components |
| Hoist default non-primitive props |
| Use primitive dependencies in effects |
| Subscribe to derived booleans, not raw values |
| Derive state during render, not effects |
| Use functional setState for stable callbacks |
| Pass function to useState for expensive values |
| Avoid memo for simple primitives |
| Put interaction logic in event handlers |
| Use startTransition for non-urgent updates |
| Use refs for transient frequent values |
6. Rendering Performance (MEDIUM)
| Rule | Description |
|---|---|
| Animate div wrapper, not SVG element |
| Use content-visibility for long lists |
| Extract static JSX outside components |
| Reduce SVG coordinate precision |
| Use inline script for client-only data |
| Suppress expected mismatches |
| Use Activity component for show/hide |
| Use ternary, not && for conditionals |
| Prefer useTransition for loading state |
7. JavaScript Performance (LOW-MEDIUM)
| Rule | Description |
|---|---|
| Group CSS changes via classes or cssText |
| Build Map for repeated lookups |
| Cache object properties in loops |
| Cache function results in module-level Map |
| Cache localStorage/sessionStorage reads |
| Combine multiple filter/map into one loop |
| Check array length before expensive ops |
| Return early from functions |
| Hoist RegExp creation outside loops |
| Use loop for min/max instead of sort |
| Use Set/Map for O(1) lookups |
| Use toSorted() for immutability |
8. Advanced Patterns (LOW)
| Rule | Description |
|---|---|
| Store event handlers in refs |
| Initialize app once per app load |
| useLatest for stable callback refs |
How to Use
Reading Individual Rules
Each rule file in
rules/ contains:
- Brief explanation of why it matters
- Incorrect code example with explanation
- Correct code example with explanation
- Additional context and references
rules/async-parallel.md rules/bundle-barrel-imports.md rules/rerender-memo.md
Full Compiled Document
For the complete guide with all rules expanded:
AGENTS.md
This 2900+ line document contains every rule with full code examples and detailed explanations, suitable for comprehensive reference.
Key Patterns
Parallel Data Fetching
// Bad: sequential const user = await fetchUser() const posts = await fetchPosts() // Good: parallel const [user, posts] = await Promise.all([ fetchUser(), fetchPosts() ])
Dynamic Imports
// Bad: bundles Monaco with main chunk import { MonacoEditor } from './monaco-editor' // Good: loads on demand const MonacoEditor = dynamic( () => import('./monaco-editor').then(m => m.MonacoEditor), { ssr: false } )
Functional setState
// Bad: stale closure risk const addItem = useCallback((item) => { setItems([...items, item]) }, [items]) // recreates on every items change // Good: always uses latest state const addItem = useCallback((item) => { setItems(curr => [...curr, item]) }, []) // stable reference
NEVER Do
- NEVER await operations sequentially when they can run in parallel
- NEVER import from barrel files (
) — import directlyimport { X } from 'lib' - NEVER skip authentication in Server Actions — treat them like API routes
- NEVER pass entire objects to client components when only one field is needed
- NEVER use
for conditional rendering with numbers — use ternary&& - NEVER subscribe to state only used in event handlers — read on demand
- NEVER mutate arrays with
— use.sort().toSorted() - NEVER put initialization in
— use module-level guarduseEffect([])