Comprehensive React Performance Optimization Guide

Vibrant JavaScript code on a screen showcasing front-end development with syntax highlighting.

Here’s a systematic approach to improving your React application’s performance:

1. Establish Performance Baselines
  • Install React DevTools Profiler extension
  • Record performance metrics using Chrome Lighthouse (run 3-5 times, take averages)
  • Measure key metrics: FCP, LCP, TTI, TBT, CLS
  • Use React.Profiler API to measure component render times
  • Set up Web Vitals monitoring: npm install web-vitals
2. Analyze Current Bundle
# Analyze bundle size
npm install --save-dev webpack-bundle-analyzer
# or for Create React App
npm install --save-dev source-map-explorer
npm run build
npx source-map-explorer 'build/static/js/*.js'
  • Identify largest dependencies
  • Look for duplicate packages
  • Find unused code
3. Component Rendering Analysis
  • Use React DevTools Profiler to identify components that re-render frequently
  • Check for unnecessary re-renders using “Highlight updates” in React DevTools
  • Look for components without proper memoization
  • Identify heavy computational logic in render methods
4. State Management Review
  • Audit global state structure (Redux, Context, Zustand, etc.)
  • Check if state is normalized and not duplicated
  • Identify over-using Context causing unnecessary re-renders
  • Review if state is at appropriate levels (lift state down where possible)
5. Dependencies Audit
npm install -g depcheck
depcheck
npm outdated
  • Remove unused dependencies
  • Update outdated packages
  • Replace heavy libraries with lighter alternatives
6. Memoization Strategy
  • React.memo: Wrap functional components that receive same props frequently
  • useMemo: Cache expensive calculations
  • useCallback: Memoize callback functions passed as props
  • Apply selectively – only where profiling shows benefit
// Example pattern
const ExpensiveComponent = React.memo(({ data, onAction }) => {
  const processedData = useMemo(() => 
    heavyCalculation(data), [data]
  );
  
  const handleAction = useCallback(() => {
    onAction(data.id);
  }, [data.id, onAction]);
  
  return <div>{processedData}</div>;
});
7. Code Splitting & Lazy Loading
// Route-based splitting
const Dashboard = lazy(() => import('./Dashboard'));
const Profile = lazy(() => import('./Profile'));

// Component-based splitting
const HeavyChart = lazy(() => import('./HeavyChart'));

// Usage with Suspense
<Suspense fallback={<Spinner />}>
  <HeavyChart data={data} />
</Suspense>
  • Split by routes first
  • Lazy load heavy components (charts, editors, modals)
  • Consider preloading critical routes on hover/interaction
8. List Optimization
  • Always use stable, unique key props (never index)
  • Implement virtualization for long lists:
npm install react-window
# or
npm install react-virtualized
  • Paginate or use infinite scroll for large datasets
  • Memoize list item components
9. Image & Asset Optimization
  • Use modern formats: WebP, AVIF with fallbacks
  • Implement lazy loading: loading="lazy" attribute
  • Use responsive images with srcset
  • Compress images (TinyPNG, ImageOptim)
  • Consider CDN for static assets
  • Implement blur-up/placeholder technique
10. Event Handler Optimization
  • Debounce/throttle expensive handlers (search, scroll, resize)
npm install lodash.debounce lodash.throttle
  • Use event delegation for lists
  • Remove event listeners in cleanup functions
11. State Management Optimization
  • Context API: Split contexts to prevent unnecessary re-renders
// Bad: Single context
const AppContext = { user, theme, settings };

// Good: Separate contexts
const UserContext, ThemeContext, SettingsContext;
  • Redux: Use reselect for memoized selectors, avoid connecting too many components
  • Consider state management alternatives: Zustand, Jotai for simpler needs
12. Network & Data Fetching
  • Implement request caching (React Query, SWR)
npm install @tanstack/react-query
# or
npm install swr
  • Use optimistic updates
  • Implement proper loading and error states
  • Prefetch data on hover/interaction
  • Use GraphQL with fragments to fetch only needed data
13. Production Build Optimization
// webpack.config.js optimizations
{
  optimization: {
    splitChunks: {
      chunks: 'all',
      cacheGroups: {
        vendor: {
          test: /[\\/]node_modules[\\/]/,
          name: 'vendors',
          priority: 10
        }
      }
    }
  }
}
  • Enable production mode
  • Minify and compress assets
  • Enable gzip/brotli compression on server
  • Use tree shaking (ensure sideEffects: false in package.json)
14. CSS Optimization
  • Remove unused CSS (PurgeCSS with Tailwind)
  • Use CSS-in-JS efficiently (emotion, styled-components with proper memoization)
  • Consider CSS modules for better tree-shaking
  • Avoid inline styles in render methods
15. Third-party Scripts
  • Load analytics/ads asynchronously
  • Defer non-critical scripts
  • Consider using Partytown for web workers
  • Audit and remove unnecessary third-party scripts
16. Set Up Performance Monitoring
npm install @sentry/react
# or use Google Analytics, LogRocket, etc.
  • Track Core Web Vitals in production
  • Set up error boundaries with monitoring
  • Monitor bundle size in CI/CD
17. Testing & Validation
  • Run Lighthouse audits after each optimization
  • Test on slow networks (Chrome DevTools throttling)
  • Test on low-end devices
  • Use React DevTools Profiler before/after comparisons
  • A/B test significant changes
18. Documentation & Code Quality
  • Document performance-critical sections
  • Set up ESLint rules for performance:
npm install eslint-plugin-react-hooks
  • Code review checklist for performance considerations
  • Create performance budget and enforce it
  • Remove console.logs from production
  • Implement React.StrictMode to catch issues
  • Use production build for deployment
  • Enable compression on server
  • Add proper cache headers
  • Lazy load routes
  • Optimize images
  • Remove unused dependencies
  • Add key props to lists
  • Implement error boundaries
  1. Profiling: React DevTools, Chrome DevTools, Lighthouse
  2. Bundle Analysis: webpack-bundle-analyzer, source-map-explorer
  3. Monitoring: Sentry, LogRocket, Web Vitals
  4. Optimization Libraries: react-window, React Query/SWR, lodash
  • First Contentful Paint: < 1.8s
  • Largest Contentful Paint: < 2.5s
  • Time to Interactive: < 3.8s
  • Total Bundle Size: < 200KB gzipped
  • Main thread work: < 2.5s

Remember: Always measure before and after optimizing. Premature optimization can lead to unnecessary complexity. Focus on the biggest bottlenecks first.

At 7Shades Digital, we specialised in creating strategies that help businesses excel in the digital world. If you’re ready to take your website to the next level, contact us today!

Scroll to Top