How to Update Strict Mode in React

React Strict Mode is a valuable development tool that helps identify potential problems in an application by highlighting unsafe lifecycles, legacy API usage, and unexpected side effects. This article provides a straightforward guide on how to enable, update, and configure Strict Mode in your React projects, ensuring your codebase remains robust and ready for future React updates.

Enabling Strict Mode in Your App

To use or update Strict Mode, you must wrap your component tree with the <React.StrictMode> component. This is typically done in the entry point file of your application, such as index.js, index.tsx, or main.jsx.

Here is how to implement it:

import React from 'react';
import ReactDOM from 'react-dom/client';
import App from './App';

const root = ReactDOM.createRoot(document.getElementById('root'));
root.render(
  <React.StrictMode>
    <App />
  </React.StrictMode>
);

Applying Strict Mode Selectively

You do not have to run Strict Mode for your entire application all at once. If you are migrating a legacy codebase, you can activate it for specific parts of your component tree to update your code incrementally:

import React from 'react';

function MyComponent() {
  return (
    <div>
      <Header />
      <React.StrictMode>
        <ModernForm />
      </React.StrictMode>
      <Footer />
    </div>
  );
}

In this example, Strict Mode checks will only run for ModernForm and its children, leaving Header and Footer unaffected.

Adapting to React 18+ Strict Mode Behavior

In React 18 and newer versions, Strict Mode introduces a behavior where components mount, unmount, and remount again in development mode. This intentional double-rendering helps developers find bugs related to state loss and improper resource cleanup.

To update your code to work correctly under these Strict Mode conditions, follow these practices:

1. Always Write Cleanup Functions in useEffect

If your effect subscribes to an external data source, sets up a timer, or performs an asynchronous task, ensure you return a cleanup function to undo the action.

import { useEffect } from 'react';

function ChatRoom() {
  useEffect(() => {
    const connection = createConnection();
    connection.connect();

    // Cleanup function is critical for React 18+ Strict Mode
    return () => {
      connection.disconnect();
    };
  }, []);

  return <div>Welcome to the chat</div>;
}

2. Keep Render Functions Pure

Avoid performing side effects (like API calls or updating global variables) directly within the body of your component. Save those operations for event handlers or useEffect hooks.