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

Support stars in imports besides trailing slashes #284

Closed
daKmoR opened this issue Aug 1, 2022 · 1 comment
Closed

Support stars in imports besides trailing slashes #284

daKmoR opened this issue Aug 1, 2022 · 1 comment

Comments

@daKmoR
Copy link

daKmoR commented Aug 1, 2022

Currently, import maps have a trailing slash functionality that allows importing anything within a folder

{
  "imports": {
    "moment": "/node_modules/moment/src/moment.js",
    "moment/": "/node_modules/moment/src/"
  }
}

e.g. the above would allow imports like

import absCeil from 'moment/lib/utils/abs-ceil.js';
import indexOf from 'moment/lib/utils/index-of.js';

to work. see moment src to verify

Issue

  1. The trailing slash functionality feels "magical" in that unless you know it there is a low chance you would guess that behavior.
  2. It behaves differently than node entry point exports
  3. Trailing slash imports allow every file to be imported e.g. also potentially not intended imports like
    import privateJson from 'moment/lib/private.json' assert { type: 'json' };

Suggestion

Besides the trailing slash functionality also support * as a "simple string replace" functionality.
e.g. the above could then also be written as

{
  "imports": {
    "moment": "/node_modules/moment/src/moment.js",
    "moment/*": "/node_modules/moment/src/*"
  }
}

this fixes

  1. as it is more obvious that it supports * after "moment".

  2. as it can be 1:1 mapped to how node entry points work (which enables tools to very simply generate an import maps out of exports)

    "exports": {
      "./*": "./src/*",
    }

    Note: trailing slash exports have been deprecated with node 16 and have been removed since node 17 (iirc)

The import would remain exactly the same

import absCeil from 'moment/lib/utils/abs-ceil.js';
import indexOf from 'moment/lib/utils/index-of.js';

as the * will be replaced with lib/utils/abs-ceil.js in "/node_modules/moment/src/*".
Resulting in an actual import of /node_modules/moment/src/lib/utils/abs-ceil.js.

Note: potentially in a first iteration we could only support * at the end of a / (e.g. functional foo/* would be the same as foo/)

Support limitations and extensionless imports

In node the star * can not only be at the end of the import but also before a file extension.

e.g. the following exports

"exports": {
  "./*.js": "./src/*.js",
}

The import would change to extensionless but the actual file would remain the same

import absCeil from 'moment/lib/utils/abs-ceil';
import indexOf from 'moment/lib/utils/index-of';

as the * will be replaced with lib/utils/abs-ceil in "/node_modules/moment/src/*.js".
Resulting in an actual import of /node_modules/moment/src/lib/utils/abs-ceil.js.

This solves our last remaining issue (Nr. 3) by limiting what can be imported to only .js files.

To quote nodes docs about the implementation

* maps expose nested subpaths as it is a string replacement syntax only.

https://nodejs.org/dist/latest-v18.x/docs/api/packages.html#packages_subpath_patterns

What do you think? should * be supported in an import-map?

@domenic
Copy link
Collaborator

domenic commented Aug 2, 2022

Dupe of #7 and its various duplicates.

@domenic domenic closed this as completed Aug 2, 2022
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

No branches or pull requests

2 participants