React Best Practices

React and Next.js performance optimization guidelines from Vercel Engineering. 57 rules across 8 categories for writing, reviewing, and refactoring React code.

MIT-0 · Free to use, modify, and redistribute. No attribution required.
3 · 2.4k · 33 current installs · 33 all-time installs
MIT-0
Security Scan
VirusTotalVirusTotal
Benign
View report →
OpenClawOpenClaw
Benign
high confidence
Purpose & Capability
Name/description match the provided content: a ruleset for React and Next.js performance. Files (README, SKILL.md, AGENTS.md and many rule markdowns) all align with the stated goal. There are no unrelated environment variables, binaries, or config paths requested.
Instruction Scope
SKILL.md + AGENTS.md are guidance documents for humans and for agents to use when writing/refactoring code. They do not request secrets or system files. Note: AGENTS.md explicitly targets automation/LLMs and is intended for agents to perform maintenance/refactors; that is coherent with the skill purpose but means an agent using this skill could modify your codebase if allowed—review any automated changes before applying.
Install Mechanism
No install spec in the registry (instruction-only). SKILL.md and README show example install commands (npx clawhub, copy into local skill dirs) but the skill package itself includes no install script or extracted binaries. Low install risk.
Credentials
The skill declares no required environment variables, credentials, or config paths. The guidance mentions common libraries (better-all, lru-cache, @vercel/analytics) but does not request tokens or secrets; the requested capabilities are proportionate to the stated purpose.
Persistence & Privilege
always:false and disable-model-invocation:false (normal). The skill does not request persistent presence, nor does it modify other skills or system-wide settings. Autonomous agent invocation is allowed by default but is not a unique privilege of this skill.
Assessment
This appears to be a coherent, instruction-only guide for improving React/Next.js performance and does not request credentials or install arbitrary code. Before you enable an agent to act autonomously with this skill, consider: (1) provenance — the registry metadata lists no homepage and source is unknown, so verify the origin if you require an official Vercel document; (2) automation risk — AGENTS.md is written for LLMs and enables automated refactors, so require human review or use a dry-run mode when letting an agent change your code; (3) dependency recommendations — some rules suggest libraries (better-all, lru-cache, @vercel/analytics); add third-party libs deliberately and review licenses; (4) validate any suggested code changes in CI and tests. If you only want read-only guidance, this skill is low-risk; if you plan to let an agent automatically modify code, apply normal code-review safeguards.

Like a lobster shell, security has layers — review code before you run it.

Current versionv1.0.0
Download zip
latestvk973nk8swb926qgh7r7m27nn5580wdmd

License

MIT-0
Free to use, modify, and redistribute. No attribution required.

SKILL.md

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

PriorityCategoryImpactRule Prefix
1Eliminating WaterfallsCRITICALasync-
2Bundle Size OptimizationCRITICALbundle-
3Server-Side PerformanceHIGHserver-
4Client-Side Data FetchingMEDIUM-HIGHclient-
5Re-render OptimizationMEDIUMrerender-
6Rendering PerformanceMEDIUMrendering-
7JavaScript PerformanceLOW-MEDIUMjs-
8Advanced PatternsLOWadvanced-

Quick Reference

1. Eliminating Waterfalls (CRITICAL)

RuleDescription
async-defer-awaitMove await into branches where actually used
async-parallelUse Promise.all() for independent operations
async-dependenciesUse better-all for partial dependencies
async-api-routesStart promises early, await late in API routes
async-suspense-boundariesUse Suspense to stream content

2. Bundle Size Optimization (CRITICAL)

RuleDescription
bundle-barrel-importsImport directly, avoid barrel files
bundle-dynamic-importsUse next/dynamic for heavy components
bundle-defer-third-partyLoad analytics/logging after hydration
bundle-conditionalLoad modules only when feature is activated
bundle-preloadPreload on hover/focus for perceived speed

3. Server-Side Performance (HIGH)

RuleDescription
server-auth-actionsAuthenticate server actions like API routes
server-cache-reactUse React.cache() for per-request dedup
server-cache-lruUse LRU cache for cross-request caching
server-dedup-propsAvoid duplicate serialization in RSC props
server-serializationMinimize data passed to client components
server-parallel-fetchingRestructure components to parallelize fetches
server-after-nonblockingUse after() for non-blocking operations

4. Client-Side Data Fetching (MEDIUM-HIGH)

RuleDescription
client-swr-dedupUse SWR for automatic request deduplication
client-event-listenersDeduplicate global event listeners
client-passive-event-listenersUse passive listeners for scroll
client-localstorage-schemaVersion and minimize localStorage data

5. Re-render Optimization (MEDIUM)

RuleDescription
rerender-defer-readsDon't subscribe to state only used in callbacks
rerender-memoExtract expensive work into memoized components
rerender-memo-with-default-valueHoist default non-primitive props
rerender-dependenciesUse primitive dependencies in effects
rerender-derived-stateSubscribe to derived booleans, not raw values
rerender-derived-state-no-effectDerive state during render, not effects
rerender-functional-setstateUse functional setState for stable callbacks
rerender-lazy-state-initPass function to useState for expensive values
rerender-simple-expression-in-memoAvoid memo for simple primitives
rerender-move-effect-to-eventPut interaction logic in event handlers
rerender-transitionsUse startTransition for non-urgent updates
rerender-use-ref-transient-valuesUse refs for transient frequent values

6. Rendering Performance (MEDIUM)

RuleDescription
rendering-animate-svg-wrapperAnimate div wrapper, not SVG element
rendering-content-visibilityUse content-visibility for long lists
rendering-hoist-jsxExtract static JSX outside components
rendering-svg-precisionReduce SVG coordinate precision
rendering-hydration-no-flickerUse inline script for client-only data
rendering-hydration-suppress-warningSuppress expected mismatches
rendering-activityUse Activity component for show/hide
rendering-conditional-renderUse ternary, not && for conditionals
rendering-usetransition-loadingPrefer useTransition for loading state

7. JavaScript Performance (LOW-MEDIUM)

RuleDescription
js-batch-dom-cssGroup CSS changes via classes or cssText
js-index-mapsBuild Map for repeated lookups
js-cache-property-accessCache object properties in loops
js-cache-function-resultsCache function results in module-level Map
js-cache-storageCache localStorage/sessionStorage reads
js-combine-iterationsCombine multiple filter/map into one loop
js-length-check-firstCheck array length before expensive ops
js-early-exitReturn early from functions
js-hoist-regexpHoist RegExp creation outside loops
js-min-max-loopUse loop for min/max instead of sort
js-set-map-lookupsUse Set/Map for O(1) lookups
js-tosorted-immutableUse toSorted() for immutability

8. Advanced Patterns (LOW)

RuleDescription
advanced-event-handler-refsStore event handlers in refs
advanced-init-onceInitialize app once per app load
advanced-use-latestuseLatest 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

  1. NEVER await operations sequentially when they can run in parallel
  2. NEVER import from barrel files (import { X } from 'lib') — import directly
  3. NEVER skip authentication in Server Actions — treat them like API routes
  4. NEVER pass entire objects to client components when only one field is needed
  5. NEVER use && for conditional rendering with numbers — use ternary
  6. NEVER subscribe to state only used in event handlers — read on demand
  7. NEVER mutate arrays with .sort() — use .toSorted()
  8. NEVER put initialization in useEffect([]) — use module-level guard

Files

60 total
Select a file
Select a file to preview.

Comments

Loading comments…