jsenv / importmap-node-module

Generate importmap for node_modules
35 stars 4 forks source link

Problems with creating importmap with from folders with `index.js` #74

Closed schlichtanders closed 7 months ago

schlichtanders commented 7 months ago

I am trying to get working importmap dependencies for preact in combination with @mui/material (where react is aliased to preact).

I failed to use jspm for multiple reasons and tried jsenv, but it also fails. I now setup a magicExtension of ["inherit", ".js", "/index.js"], but it still fails. Given the error logs it seems that the failure is related to importing folders with index.js in them.

I get thousands of errors like

Import resolution failed for "./Unstable_TrapFocus"
--- import trace ---
file:///home/myhome/MyPackage/node_modules/@mui/material/index.js:288:46
  287 | export { default as generateUtilityClasses } from './generateUtilityClasses';
> 288 | export { default as Unstable_TrapFocus } from './Unstable_TrapFocus';
      |                                              ^
--- reason ---
file not found on filesystem at /home/myhome/MyPackage/node_modules/@mui/material/Unstable_TrapFocus

where /home/myhome/MyPackage/node_modules/@mui/material/Unstable_TrapFocus actually points to a local folder with an index.js in them.

dmail commented 7 months ago

Hi welcome here,

The import fails to resolve because magicExtensions applies only to files. There is a dedicated if detecting import resolving to a directory:

https://github.com/jsenv/importmap-node-module/blob/1a558764abe33d05a6c324b5ce30b6875bdad537/src/util/resolve_file.js#L22-L42

There is a magicDirectoryIndexEnabled but it currently cannot be enabled from writeImportmaps. The option must be added to importResolutionDefault:

https://github.com/jsenv/importmap-node-module/blob/1a558764abe33d05a6c324b5ce30b6875bdad537/src/write_importmaps.js#L14-L29

And passed down to the resolveFile calls

I'll try to do this some day, PR welcome in the meantime.

schlichtanders commented 7 months ago

Thank you for the detailed investigation.

How could I write my little generate-importmap.mjs in order to specify this parameter?

dmail commented 7 months ago

Right now you can't. The fastest thing you could try would be to open resolve_file.js inside your node modules and modify it's content to force magicDirectoryIndexEnabled to true. Then execute generate-importmap.mjs and see if importmap is properly generated

schlichtanders commented 7 months ago

I fear that after fixing this, I am going to run into aliasing issues, that importmap-node-module does not respect the alias section of package.json. Do you know?

dmail commented 7 months ago

does not respect the alias section of package.json

Can you clarify what is the alias section? Is it a standard?

schlichtanders commented 7 months ago

My alias section in package.json looks like

"alias": {
    "react": "preact/compat",
    "react-dom/test-utils": "preact/test-utils",
    "react-dom": "preact/compat",
    "react/jsx-runtime": "preact/jsx-runtime"
  }

which is needed to replace react with preact. Don't know which kind of standard you are referring to, but this indeed works for parcel

dmail commented 7 months ago

I don't know how many tools support this "alias"` property in the package.json and I discover it today. Consequently my tool does not support it out of the box.

You can achieve this by passing manualImportMap param to writeImportmaps:

import { writeImportmaps } from "@jsenv/importmap-node-module";

await writeImportmaps({
  directoryUrl: new URL("./", import.meta.url),
  importmaps: {
    "./project.importmap": {
      manualImportmap: {
        scopes: {
          "./node_modules/react/": {
            "react": "./node_modules/preact/compat/dist/compat.module.js",
            "react-dom": "./node_modules/preact/compat/dist/compat.module.js",
          },
        },
      },
    },
  },
});
schlichtanders commented 7 months ago

I realized that the nodemodules I am using use require statements by default and hence are incompatible with the browser javascript runtime. (This took me ages to find out that this is one reason why nothing works :D)

Hence I am focussing more on importly or jspm.io which support other cdns where packages have been rewritten accordingly to esm style.

I am closing this issue then and thank you very much for your help.