Skip to main content

How to Reesolve "Module not found: Can't resolve 'crypto'" Error in JavaScript

The Module not found: Error: Can't resolve 'crypto' is a common error in modern JavaScript projects, especially those using Webpack 5+. It occurs when a piece of your client-side code, which is intended to run in the browser, tries to import the crypto module. This module is a built-in part of the Node.js environment and is not available in browsers.

This guide will explain the fundamental reason this error happens and show you the correct way to solve it by either providing a browser-compatible "polyfill" or by telling Webpack to ignore it.

The Core Problem: Node.js Modules Don't Exist in the Browser

Modules like crypto, fs, path, and http are core Node.js APIs. They provide access to the server's cryptographic functions, file system, and other low-level operating system features. For security reasons, browsers are sandboxed and do not have access to these modules.

The Can't resolve 'crypto' error is Webpack telling you: "You're trying to bundle a library that has a line like const crypto = require('crypto');, but I can't find a browser-compatible version of that module."

This error became widespread with the release of Webpack 5, which removed the automatic polyfills for Node.js core modules. A "polyfill" is a piece of code that provides a browser-friendly substitute for a native Node.js module. Before Webpack 5, a substitute was often provided automatically; now, you must configure it explicitly.

The Solution: Configuring Webpack's resolve.fallback

The correct way to handle this is to explicitly tell Webpack what to do when it encounters an import for the crypto module. You do this in the resolve.fallback section of your Webpack configuration.

You have two main choices:

  • Option A (Most Common): If the functionality is not needed on the client side, tell Webpack to substitute it with an empty module (false).
  • Option B: If the functionality is needed, provide a browser-compatible polyfill library.

How to Apply the Solution

Option A (Most Common): The Library Doesn't Need crypto in the Browser

Often, a library you are using has code paths for both Node.js and the browser. The require('crypto') might be in a part of the code that will never run in a browser environment. In this case, you can safely tell Webpack to ignore it.

Solution: Set the fallback for crypto to false.

Option B: The Library Does Need crypto in the Browser

If a library relies on cryptographic functions to work in the browser, you need to provide a polyfill. The community-standard polyfill for the crypto module is crypto-browserify.

Solution:

  1. Install the polyfill:
    npm install crypto-browserify
  2. Configure the fallback in Webpack: Set the fallback to point to the installed polyfill.
    resolve: {
    fallback: {
    "crypto": require.resolve("crypto-browserify")
    }
    }
    Note: The crypto-browserify library often has dependencies on other polyfills, like stream. You may see a Can't resolve 'stream' error next. The solution is the same: install the polyfill (npm install stream-browserify) and add it to your fallback configuration.

Applying the Configuration in Different Frameworks

Here’s how to add the resolve.fallback configuration in popular frameworks.

In a Custom webpack.config.js

// webpack.config.js
module.exports = {
// ... other configurations
resolve: {
fallback: {
"crypto": false // Or: require.resolve("crypto-browserify")
}
},
// ... other configurations
};

In a Create React App Project

To modify the Webpack config without ejecting, use a tool like react-app-rewired.

  1. Install dependencies: npm install react-app-rewired customize-cra --save-dev.

  2. Update package.json scripts to use react-app-rewired.

  3. Create config-overrides.js:

    config-overrides.js:

    const { override } = require('customize-cra');

    module.exports = override(
    (config) => {
    config.resolve.fallback = {
    ...config.resolve.fallback,
    "crypto": false, // Or require.resolve("crypto-browserify")
    };
    return config;
    }
    );

In a Next.js Project

The crypto module can only be used in server-side code in Next.js (e.g., getServerSideProps). If it's being pulled into your client-side bundle, you can configure the fallback in next.config.js.

next.config.js:

/** @type {import('next').NextConfig} */
const nextConfig = {
webpack: (config) => {
config.resolve.fallback = {
...config.resolve.fallback,
crypto: false, // Or require.resolve("crypto-browserify")
};
return config;
},
};

module.exports = nextConfig;

Conclusion

The Module not found: Can't resolve 'crypto' error is a direct result of Webpack 5 no longer automatically providing polyfills for Node.js core modules.

  • The root cause is a library trying to use the Node.js crypto module in a browser environment.
  • The correct solution is to configure Webpack's resolve.fallback property.
  • If the functionality is not needed on the client, set the fallback to false. This is the most common and simplest fix.
  • If the functionality is needed, install the crypto-browserify polyfill and point to it in the fallback configuration.