remix-run / remix

Build Better Websites. Create modern, resilient user experiences with web fundamentals.
https://remix.run
MIT License
30.15k stars 2.55k forks source link

Cannot import "exports": { "module": ... } without type=module configured packages, instead we could get an error: Cannot use import statement outside a module #9070

Open LumaKernel opened 8 months ago

LumaKernel commented 8 months ago

Reproduction

Quick: Go to https://stackblitz.com/edit/remix-run-remix-cqepq2?file=app%2Froutes%2F_index.tsx Or see https://github.com/remix-run/remix/pull/9071

  1. Initialize remix plain project.
  2. Install use-immer@0.9.0 (Don't worry! It's tiny library, fully zero dependency, and I confirmed this is caused by some conditions with just rewriting its package.json)
  3. Add import statement for 'use-immer'

The package which causes this problem has these conditions:

The package.json in use-immer@0.9.0, you can see like this:

{
  "name": "use-immer",
  "version": "0.9.0",
  "description": "Use immer with React hooks",
  "main": "dist/use-immer.js",
  "umd:main": "dist/use-immer.umd.js",
  "module": "dist/use-immer.module.js",
  "jsnext:main": "dist/use-immer.module.js",
  "react-native": "dist/use-immer.module.js",
  "typings": "dist/index.d.ts",
  "source": "src/index.ts",
  "exports": {
    ".": {
      "require": "./dist/use-immer.js",
      "import": "./dist/use-immer.module.js",
      "types": "./dist/index.d.ts"
    }
  },
  "sideEffects": false,
  "scripts": { omitted.. },
  "repository": { omitted.. },
  "files": [ omitted.. ],
  "keywords": [ omitted.. ],
  "author": "Michel Weststrate",
  "license": "MIT",
  "bugs": {
    "url": "https://github.com/mweststrate/use-immer/issues"
  },
  "homepage": "https://github.com/mweststrate/use-immer#readme",
  "peerDependencies": { omitted.. },
  "devDependencies": { omitted.. }
}

And we can confirm this satisfies the condition. Actually, if I add "type=module" to this, and restart remix run, it succeeds to import.


Extra contexts

related:

This could be the bug of vite. I can create issue instead on vite, but I'm not sure for now. The most important part of this issue is I got small reproduction for these issues (currently discussions).

~I'm also making PR for Option 1 after submitting this issue.~ Done.

By the way, you may think, such packages should have type: module in their package.json. Actually, import from these packages from esm does not work, and multi-support is actually not possible by native level. Even if type=module is added, now, it cannot be require-able. Sadly, this is complicated situation. Node.js, TypeScript and Webpack treats exports as their own way. Webpack says as https://webpack.js.org/guides/package-exports/#support .

Thanks.

System Info

System:
    OS: Linux 5.19 Ubuntu 22.04.2 LTS 22.04.2 LTS (Jammy Jellyfish)
    CPU: (8) x64 11th Gen Intel(R) Core(TM) i5-1135G7 @ 2.40GHz
    Memory: 7.87 GB / 15.36 GB
    Container: Yes
    Shell: 5.1.16 - /bin/bash
  Binaries:
    Node: 20.11.0 - /usr/bin/node
    npm: 10.2.4 - /usr/bin/npm
    bun: 1.0.29 - ~/.bun/bin/bun
  Browsers:
    Chrome: 114.0.5735.133
    Chromium: 122.0.6261.128
  npmPackages:
    @remix-run/dev: ^2.8.1 => 2.8.1
    @remix-run/node: ^2.8.1 => 2.8.1
    @remix-run/react: ^2.8.1 => 2.8.1
    @remix-run/serve: ^2.8.1 => 2.8.1
    vite: ^5.1.0 => 5.1.6

Used Package Manager

npm

Expected Behavior

Not get error and just can import it as ESM module as usual.

Actual Behavior

Got an error:

Cannot use import statement outside a module
    at internalCompileFunction (https://remixrunremixcqepq2-01ee.w-credentialless-staticblitz.com/blitz.810981ba.js:180:1005)
    at wrapSafe (https://remixrunremixcqepq2-01ee.w-credentialless-staticblitz.com/blitz.810981ba.js:54:14101)
    at Module._compile (https://remixrunremixcqepq2-01ee.w-credentialless-staticblitz.com/blitz.810981ba.js:54:14512)
    at Module._extensions..js (https://remixrunremixcqepq2-01ee.w-credentialless-staticblitz.com/blitz.810981ba.js:54:15550)
    at Module.load (https://remixrunremixcqepq2-01ee.w-credentialless-staticblitz.com/blitz.810981ba.js:54:13457)
    at Module._load (https://remixrunremixcqepq2-01ee.w-credentialless-staticblitz.com/blitz.810981ba.js:54:10535
Click outside, press Esc key, or fix the code to dismiss.
You can also disable this overlay by setting server.hmr.overlay to false in vite.config.ts.
image

We have the workaround for this, just with importing by relative path:

- import { useImmer } from 'use-immer';
+ import { useImmer } from '../../node_modules/use-immer';
U-4-E-A commented 6 months ago

Is there any update on this issue? I am experiencing it with v2.9.2.

@remix-run/dev: 2.9.2
@remix-run/node: 2.9.2
@remix-run/react: 2.9.2
@remix-run/serve: 2.9.2
navdeep-soni commented 6 months ago

I am also experiencing the same issue

raRaRa commented 5 months ago

I've been running into the same issue with several packages such as react-content-loader and the workaround mentioned above seems to work for my case too.

IvanLi-CN commented 4 months ago

I encountered the same issue when using chartjs-react.

Following the suggestions from the original poster and this comment, I tried the following two solutions, both of which resolved the issue:

  1. Add { "type": "module" } to lib's package.json file
  2. Move the relevant code to a .client.tsx file