Fixing Next.js & MUI Warning: Prop className Did Not Match

Updated: January 1, 2024 By: Guest Contributor One comment

Working with Next.js and Material-UI (MUI) can sometimes lead to unexpected warning messages that could disrupt the development flow. One common issue is the ‘Warning: Prop className did not match’ warning. This issue generally arises from a mismatch between the server-rendered classes and the classes generated on the client side in a Next.js application that uses MUI.

Understanding the Prop className Mismatch Issue

Next.js using Server-Side Rendering (SSR) means your components’ styles are generated on the server. When the page reaches the browser, JavaScript takes over and regenerates these styles. If the server and the client use different configurations, it leads to a mismatch. Material-UI uses JSS (a CSS-in-JS solution) that generates unique class names during runtime. If those class names don’t match between server and client renders, you’ll get the className mismatch warning.

Solutons

Ensuring Consistent Rendering

To ensure the server and client render the same content, their configurations must match. There have been several strategies for aligning them, ranging from custom Document components to using Next.js’s built-in features designed to handle such inconsistencies.

Using Next.js 13 Server Components

Next.js 13 introduced server components which don’t involve client-side JavaScript at all. Instead, they render entirely on the server, sending the result to the client. This means there’s no client-side hydration mismatch. However, depending on this feature may not be suitable for all components, especially those that require rich interactions.

Adjusting Material-UI’s Styles Server-Side

The prevailing solution before the server components was to use a custom _document.js file to ensure that Material-UI styles are collected server-side and injected into the page markup. This needs to match with the client-side configuration. The implementation of this depends on the version of Material-UI you’re using and may involve using functions like ServerStyleSheets (in MUI v4) or StylesServerProvider in MUI v5.

Using createEmotionCache

In Next.js projects using the latest versions of MUI, you can use a custom instance of createEmotionCache to synchronize the server and client styles. The main idea is to insert a custom cache that reuses the same class names that were generated on the server. This cache should be used both on the custom _app.js and _document.js files for consistency.

A Working Example

Leveraging createEmotionCache in Next.js 13 or newer, here’s a complete code example that can run without encountering the className mismatch warning:

import createEmotionCache from '@emotion/cache';
import { CacheProvider } from '@emotion/react';
import { CssBaseline } from '@mui/material';
import { ThemeProvider } from '@mui/material/styles';

const clientSideEmotionCache = createEmotionCache();

function MyApp({ Component, pageProps }) {
return (
<CacheProvider value={clientSideEmotionCache}>
<ThemeProvider theme={theme}>
<CssBaseline />
<Component {...pageProps} />
</ThemeProvider>
</CacheProvider>
);
}

export default MyApp;

Make sure you replace theme with your own theme setting from MUI. This code snippet should be placed in your _app.js or _app.jsx file, which is responsible for setting up the page-level components in your Next.js application. This setup ensures that the server-rendered styles match the client-side styles, making the warning disappear. Remember, any MUI styling approach must be isomorphic, meaning it works the same on the server and the client for this fix to be effective.

1 Comment
Oldest
Newest Most Voted
Inline Feedbacks
View all comments