Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Vite (using ESBuild) fails with 'require() of ES Module not supported' #2602

Closed
JorritSalverda opened this issue May 31, 2024 · 7 comments
Closed

Comments

@JorritSalverda
Copy link

Describe/explain the bug

When creating a Remix site with Vite and using the @nivo packages it fails to run with the Vite development server. It leads to the following error:

8:29:28 PM [vite] Internal server error: require() of ES Module /xyz/my-remix-app/node_modules/d3-interpolate/src/index.js from /xyz/my-remix-app/node_modules/@nivo/core/dist/nivo-core.cjs.js not supported.
Instead change the require of index.js in /xyz/my-remix-app/node_modules/@nivo/core/dist/nivo-core.cjs.js to a dynamic import() which is available in all CommonJS modules.
      at Object.<anonymous> (/xyz/my-remix-app/node_modules/@nivo/core/dist/nivo-core.cjs.js:1:164)

This probably has to do with Vite using ESBuild for development builds, which doesn't understand whether the packages are CommonJs or ESM and hence treating it incorrectly. It thinks nivo-core.cjs.js is an ESM file, while it's a CommonJS file in reality.

This can (partially) be fixed by adding type and exports to the packages as follows:

    "type": "module",
    "exports": {
        "require": "./dist/nivo-sunburst.cjs.js",
        "import": "./dist/nivo-sunburst.es.js"
    },

but then leads to a following error:

8:33:40 PM [vite] Internal server error: Cannot find module '/xyz/my-remix-app/node_modules/lodash/cloneDeep' imported from /xyz/my-remix-app/node_modules/@nivo/sunburst/dist/nivo-sunburst.es.js
Did you mean to import "lodash/cloneDeep.js"?
      at finalizeResolution (node:internal/modules/esm/resolve:265:11)
      at moduleResolve (node:internal/modules/esm/resolve:933:10)
      at defaultResolve (node:internal/modules/esm/resolve:1157:11)
      at ModuleLoader.defaultResolve (node:internal/modules/esm/loader:383:12)
      at ModuleLoader.resolve (node:internal/modules/esm/loader:352:25)
      at ModuleLoader.getModuleJob (node:internal/modules/esm/loader:227:38)
      at ModuleWrap.<anonymous> (node:internal/modules/esm/module_job:87:39)
      at link (node:internal/modules/esm/module_job:86:36)

To Reproduce
Steps to reproduce the behavior:

  1. npx create-remix@latest --template remix-run/remix/templates/cloudflare
  2. cd my-remix-app
  3. npm i @nivo/[email protected] @nivo/[email protected]
  4. replace contents of app/routes/_index.tsx with
import { ResponsiveSunburst } from "@nivo/sunburst";

export default function Index() {
  return (
    <div style={{ height: 400, width: 400 }}>
      <ResponsiveSunburst data={
        {
          "name": "nivo",
          "color": "hsl(185, 70%, 50%)",
          "children": [
            {
              "name": "viz",
              "color": "hsl(343, 70%, 50%)",
              "loc": 155750
            },
            {
              "name": "colors",
              "color": "hsl(142, 70%, 50%)",
              "loc": 83692
            }
          ]
        }
      }
        margin={{ top: 10, right: 10, bottom: 10, left: 10 }}
        id="name"
        value="loc"
        cornerRadius={2}
        borderColor={{ theme: 'background' }}
        colors={{ scheme: 'nivo' }}
      />
    </div>
  );
}
  1. run the development server with npm run dev and open the url to http://localhost:5173/ that shows in the output (port number can be different)

Expected behavior
Show the same as when running npm run build followed by npm run start and then opening the localhost site url shown in the logs. Vite uses tsc instead of esbuild for creating production artifact leading to a different outcome.

Desktop (please complete the following information):

  • OS: Zorin 17.1
  • Browser Chrome
  • Version Version 125.0.6422.112 (Official Build) (64-bit)

Additional context

https://publint.dev/@nivo/[email protected] show a number of issues with the packages that should be fixed.

@JorritSalverda
Copy link
Author

Perhaps a useful article on how to make the library work well for both ESM and CommonJS: https://www.maxpou.fr/blog/publish-npm-package-esm-and-cjs/

@JorritSalverda
Copy link
Author

You might also want to switch from lodash to lodash-es so you can use imports like import { cloneDeep } from 'lodash-es' while benefiting from ESM's tree shaking to minimize the end users bundle size.

@plouc
Copy link
Owner

plouc commented Jun 3, 2024

I think it's a duplicate of #2310.

@JorritSalverda
Copy link
Author

Could be but everyone wants to discontinue the commonjs version while the exports skips the need to do so, keeping only the lodash afterwards. I've managed to get it to work locally by patching nivo by both adding the exports section to all nivo package.json files and by adding the .js extension suffix to all lodash imports. I'll try to create a pull request for both.

@plouc
Copy link
Owner

plouc commented Jun 3, 2024

everyone wants to discontinue the commonjs version while the exports skips the need to do so

There are many tools out there, some with their own way of loading things, I think that's a bold assumption.

@plouc
Copy link
Owner

plouc commented Jun 3, 2024

I'm going to close this issue, as it's clearly related.

@JorritSalverda
Copy link
Author

The suggested Vite config addition from the other ticket actually worked wonders. Thx.

  ssr: {
    noExternal: [/^d3.*$/, /^@nivo.*$/],
  },

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Projects
None yet
Development

No branches or pull requests

2 participants