Skip to content

esm: implement import.meta.resolve and make nodejs: scheme public

This PR implements import.meta.resolve as an async hook into the module resolver.

This fills the gap of enabling require.resolve workflows that aren't currently possible in ES modules, such as locating the exact path of a dependency or local resolution following all the correct resolver resolution rules.

This is a feature that will require alignment with browsers, so I'm opening this now to be able to start those discussions. Marking as blocked on consensus discussions.

Usage examples:

  • await import.meta.resolve('./dep.ext') -> file:///path/to/dep.ext, relative to current module.
  • await import.meta.resolve('./dep.ext', 'file:///different/path/parent') -> file:///different/path/dep.ext, relative to provided parent.
  • await import.meta.resolve('dependency') -> file:///path/to/node_modules/dependency/main.js, as resolved from current module.
  • await import.meta.resolve('dependency', 'file:///different/path/parent') -> file:///different/path/node_modules/dependency/main.js, as resolved from provided module.
  • await import.meta.resolve('./does-not-exist') -> Throws not found as the default Node.js resolver checks for existence.
  • await import.meta.resolve('fs') -> nodejs:fs

If the Node.js resolver has been hooked by a loader, the corresponding resolve function will be called in import.meta.resolve.

This API also makes the nodejs:fs internal builtin module scheme public, including the associated changes for this feature.

Checklist
  • make -j4 test (UNIX), or vcbuild test (Windows) passes
  • tests and/or benchmarks are included
  • documentation is changed or added
  • commit message follows commit guidelines

Merge request reports

Loading