Closed Bug 1688879 (importmaps) Opened 3 years ago Closed 2 years ago

Implement Import Maps

Categories

(Core :: JavaScript Engine, enhancement, P3)

enhancement

Tracking

()

RESOLVED FIXED
102 Branch
Tracking Status
firefox102 --- fixed

People

(Reporter: yulia, Assigned: allstars.chh)

References

(Depends on 1 open bug, Blocks 5 open bugs, )

Details

(Keywords: dev-doc-complete)

Attachments

(9 files, 2 obsolete files)

48 bytes, text/x-phabricator-request
Details | Review
48 bytes, text/x-phabricator-request
Details | Review
48 bytes, text/x-phabricator-request
Details | Review
48 bytes, text/x-phabricator-request
Details | Review
48 bytes, text/x-phabricator-request
Details | Review
48 bytes, text/x-phabricator-request
Details | Review
48 bytes, text/x-phabricator-request
Details | Review
48 bytes, text/x-phabricator-request
Details | Review
48 bytes, text/x-phabricator-request
Details | Review

Chrome is shipping in 89.

This is probably the most anticipated feature in JavaScript history. It will, finally, after 25 years, enable the bundler-free web development. Please prioritize it, thank you!

Any updates? Available in Chrome already. The last step to the native code re-use in the browser. Only took 25 years.

Import maps isn't standard yet, and looking at the repo they still have a few kinks to work out. For broader reference, WICG doesn't standardize HTML -- it incubates interesting proposals, which can then be merged into the HTML spec. That hasn't happened for import maps, and this feature is not yet standard. Chrome tends to ship proposals eagerly, to get early feedback. This is a great for people to experiment with it.

Since you mention bundler free web development: One of the proposed use cases is import maps + http push, and I know many people are excited about this. dhh spoke about this technique on twitter, and it brought a lot of attention to this bug. This technique will likely not be viable in the long run, as Chrome is dropping support for http push and they do not plan to support push from HTTP/3. You can refer here for more details: https://groups.google.com/a/chromium.org/g/blink-dev/c/K3rYLvmQUBY/m/0o4J1GEjAgAJ Something else, potentially equivalent, may take it's place, but it is hard to know right now. Import maps is independently useful. If you were excited about this -- then this solution may still take a bit of time as alternatives are explored.

Bundle "free" development is currently under active discussion. There is contention about whether or not bundling should be integrated into the browser, as the network requests may be too costly to ever move away from bundlers. There is disagreement on this point, and research is ongoing. IETF and WICG are looking into this, and presentations have been made to TC39 as well. Alternatives have also been discussed. You can take a look at the following repositories for more info:

https://github.com/WICG/webpackage
https://github.com/WICG/resource-bundles
https://github.com/littledan/proposal-module-fragments

From our side: at present, there isn't bandwidth to eagerly implement this proposal at the cost of other high priority work. Coupled with the experimental status, the shifting space of complex multi-resource applications, and the implementation complexity which may interfere with ongoing work, it doesn't make sense to implement immediately. It is on our radar however, and we will certainly get to it when we can. I am doing a pretty large push on modules this year, and it will likely be within the scope of that work. I have a few higher priority issues to get to first.

OK, phew, the last thing. I am not sure what you mean about "native code reuse". Perhaps you mean portability between server and frontend code?

In which case -- yes, import-maps would introduce native support for portability of code from node to the browser. This problem has existed since the introduction of nodejs and commonjs in 2009 and the unique approach to module specifiers. The module system didn't exist at the time and there was a lot to figure out. What works on node doesn't work on the web, as the web is a more constrained environment. Node introduced a more "user friendly" specifier, as they don't have the security requirement that the web has for non-spoofable resources. There is a good reason why we use URLs on the web, while node decided to do something else. Import maps, from a user perspecitve, would make things more ergonomic and make the portability between these two types of js hosts much better. I wouldn't say that this is as old as JavaScript itself, as the problem import maps is solving is complex, and arose out of relatively recent technologies. It is an interesting problem but a relatively recent one compared to the age of the language.

Thank you for the detailed comment! Glad to hear import maps are on radar. I believe they a way forward, and AFAIK there's no other compelling solutions for code reuse. Hope you can take look on them during your push on modules.

To my shame, I don't know what is "http push" so can't comment anything on that.

Under "native code re-use" I just mean a module system that supports/is integrated with packages repository. It great to have native modules in the language, finally, but wait, you still can't use all the code published in the repositories (w/o running special bundler web-server). Feels like language designers/implementors live in their own universe and every-day web engineers - in separate one. Why native ESM modules did not account for the de-facto standard of JavaScript package, created by npm (node_modules, bare package identifiers)? Because language designers plan to introduce their own format? In the same way - why Node.js guys back in the days, created synchronous modules spec, knowing it will never be accepted in browsers? This all is just madness, lack of communication and loving kindness to fellow developers. We can do better I believe.

@Y(In reply to Yulia Startsev from comment #4)

Thanks for presenting your position on the problem.
Let me quickly elaborate why I, as a JS developer, consider Import Maps absolutely essential to the future of the web.
We now live in the ecosystem where it's borderline impossible to start building a new application without using a build tool requiring a different runtime from what I'm building for (Node, Go, Rust, etc). Yes, sure, I can use native ES modules to break down my code into smaller maintainable pieces but the moment I need to reach out to any library I now have just two options:

  1. use a build tool and bundle it into my app; (It works now, but I'd like this to not be a hard requirement)
  2. include a "UMD" dist of the library into my page and refer to it via a global variable; (I don't think we need to go into detail why the second option is not scalable at all.)
  3. use an import from a URL;

The third option seems like a way to go but it's quickly crashes into a wall of the real live. In real apps it's quite often the case where a certain library (say React) has to exist in only 1 version in the app.
This scenario is almost impossible to handle when your dependencies are also using URLs to refer to their dependencies. It means that if my dependency "A" depends upon "react" that's being imported from a URL that is different from the version of "react" used by my other dependency "B" I'm gonna end up with a broken app I have no means of fixing.

Import Maps basically fix the JS code portability that we lost when we surrendered to the build tools. Without Import Maps there is almost no value in the native ESM support in the browsers - if I need to bundle anyways I can load and evaluate my bundled app code as an IIFE, why even bother with modules.

We already have a production-ready CDN that is willing to serve us prebundled dependencies in a portable format preserving bare module specifiers - https://jspm.org/docs/cdn. It also has some very compelling arguments regarding the loading performance benefits that approach brings. Import Maps is literally the last piece of the puzzle that browsers need to deliver to bring back the fun and simplicity of the early days of web development without sacrificing user experience and developer experience.

Just as a disclosure, the reason I'm so invested besides my personal passion about the web is that I'm currently working at Framer (framer.com) and the main goal of my team is to make it possible to use the components produced in the design tool (generated React code) outside of Framer, in the production apps. There is literally 0 viable options to achieve that in user and developer-friendly way without Import Maps.

I'd really appreciate it if you reconsider the priority and importance of this feature 🙏🏼

Hi Wizardly,

Thanks for your thoughts.

Import maps depends on work currently ongoing in the module loader, as otherwise the efforts would interfere and slow everything down. It will be worked on in the near future, but there is no way to say for certain when.

Good to see the importmap implementation being considered.
To add my pov, Importmaps are also answer to registry free package sharing. In my experience bundlers being necessary to optimise deployment vs being required to develop, distribute or deploy different painpoints.

If we only consider node then the situation is less positive but if we include Deno into the mix, then wonderful possibilities emerges. Since Deno supports URLs and importmaps, theoretically importmap may behave as registry. Apps can be built and distributed more granularly and freely.

The popular practice of rebuilding "whole app" is less optimal where URLs are primitive (not local filepath), because now the scale is enormous. Anything which can be represented as URL can be part of the build and that might be whole web :P.

If we are accepting that bundlers are de-facto and not going away, still the situation can be improved since right now, essentially we can only build through bundlers, which is made possible by nodejs, still no popular bundler supports URLs as module import URLs which is standardised long back and ships in browsers natively.

No support of URL in node js is major contributor of web apps not being deployed granularly. Situation is different for libraries.

Hi,

Also a huge fan of importmaps since they are an enormous quality of life improvement, especially when developing without bundlers/builders. Unfortunately, the lack of importmaps currently prevents me from developing and testing WebGPU apps in Firefox.

Depends on: 1311726

More benefits importmaps are bringing:

  1. hashes

In production i usually append hashes of the files to the urls (path/to/module.mjs?v=md5hash), so browsers are forced to re-download a file because its effectively a new resource.

While this works when importing a file from the browser, i can not really keep it in sync with the import statements inside javascript files. The hashes are usually generated in the server-runtime. Having the same hashes present in the javascript modules requires another stage in the build process.

By adding import-maps and using module specifiers rather than urls inside the modules, you can deal with that problem very easily!

  1. Dependencies

while older module-loading implementations (AMD, SystemJS) handle this pretty well, es6 modules have no support for avoiding cascades when loading modules.

This proposal (https://github.com/WICG/import-maps/issues/209) explains it.

For the moment the only possible (untested) solution that may exist is the prepending of <link rel="preload" /> tags before loading your module.

Please consider prioritizing this issue, i want to finally switch to modules and get rid of bundlers for good! Make coding fun again :)

Assignee: nobody → allstars.chh

I notice that the import-map tests in wpt are using internal APIs from v8.
See the 'window.internals' object from https://searchfox.org/mozilla-central/rev/bb14d901ac16633801b7f4adaa4fb104e6f072e4/testing/web-platform/tests/import-maps/data-driven/resources/test-helper-iframe.js#92

The method getParsedImportMap is defined in v8 internally
https://source.chromium.org/chromium/chromium/src/+/main:third_party/blink/renderer/core/testing/internals.h;drc=b8dc40b0a445983b75db39504cfdd66c304d7dca;l=346

So running the tests from m-c will get ReferenceError.
Filed an issue on wpt in https://github.com/web-platform-tests/wpt/issues/32697

So there might be some extra effort for running import-map's wpt test, either the test needs to be updated, or we need a similar window.internals stuff in our webidl with some testing pref.

The other issue is that the wpt test will pass the Error object to postMessage
https://searchfox.org/mozilla-central/rev/bb14d901ac16633801b7f4adaa4fb104e6f072e4/testing/web-platform/tests/import-maps/data-driven/resources/test-helper-iframe.js#7

Currently m-c won't support this as the Error object is not Sturcture-Clone ready. See bug 1556604.

Add a pref "dom.importMaps.enabled", with default false.

Removed "static" for ResolveModuleSpecifier, as we need to forward the resolving
algorithm to import map if it exists.

Also moved HandleResolveFailure code inside ResolveModuleSpecifier, so the
function will throw TypeError if the specifier cannot be resolved.
(Originally the throwing code is done by the callers.)

See https://wicg.github.io/import-maps/#resolving-updates

Attachment #9269416 - Attachment description: Bug 1688879 - Part 2: Add support for import maps in ScriptElement/ScriptLoader/ScriptKind → Bug 1688879 - Part 2: Add support for import maps in ScriptElement/ScriptLoader/ScriptKind.
Attachment #9269420 - Attachment description: Bug 1688879 - Part 6: Acquiring import maps → Bug 1688879 - Part 6: Acquiring import maps.
Attachment #9269422 - Attachment description: Bug 1688879 - Part 8: Assert import maps won't be processed in ScriptLoader::EvaluateScriptElement → Bug 1688879 - Part 8: Assert import maps won't be processed in ScriptLoader::EvaluateScriptElement.
Attachment #9269423 - Attachment description: Bug 1688879 - Part 9: mochitest and web-platform-test for import maps. → Bug 1688879 - Part 9: mochitest, xpcshell-test and web-platform-test for import maps.

Will ImportMaps be in any proper spec?

(In reply to Olli Pettay [:smaug] from comment #21)

Will ImportMaps be in any proper spec?
Yulia will discuss with the authors of Import Maps and try to push them to make it as a spec.

Will ImportMaps be in any proper spec?

:smaug that is a good question. It is intended for HTML. This has been an ongoing issue for us with this. The spec appeared to be in a largely finished state and there were a number of requests from developers to have this implemented both internally and externally. However, it has not been through a standards body, and we will not turn it on right now. Getting this implementation experience has given us some information that will hopefully resolve ongoing issues in the draft.

Yeah, sounds reasonable. I guess this is the second implementation of ImportMaps in a browser? That is the time when quite a bit of spec issues are usually found.

Attachment #9269419 - Attachment description: Bug 1688879 - Part 5: Refactor ResolveModuleSpecifier and forward to Import maps. → Bug 1688879 - Part 4: Refactor ResolveModuleSpecifier.
Attachment #9269418 - Attachment description: Bug 1688879 - Part 4: ResolveModuleSpecifier for import maps. → Bug 1688879 - Part 5: ResolveModuleSpecifier for import maps.
Pushed by allstars.chh@gmail.com:
https://hg.mozilla.org/integration/autoland/rev/5e695bf5dd0d
Part 1: Add Pref for import maps. r=jonco,yulia
https://hg.mozilla.org/integration/autoland/rev/d7b42d8312bb
Part 2: Add support for import maps in ScriptElement/ScriptLoader/ScriptKind. r=jonco,yulia,smaug
https://hg.mozilla.org/integration/autoland/rev/39ed48a5ecc2
Part 3: Parse and register an import map. r=jonco,yulia
https://hg.mozilla.org/integration/autoland/rev/03b772e02d07
Part 4: Refactor ResolveModuleSpecifier. r=jonco,yulia
https://hg.mozilla.org/integration/autoland/rev/f16b14d8f677
Part 5: ResolveModuleSpecifier for import maps. r=jonco,yulia,flod
https://hg.mozilla.org/integration/autoland/rev/6f0276c3ab0e
Part 6: Acquiring import maps. r=jonco,yulia
https://hg.mozilla.org/integration/autoland/rev/2cf08a51b184
Part 7: External import maps aren't supported. r=jonco,yulia
https://hg.mozilla.org/integration/autoland/rev/0503d2d2ae01
Part 8: Assert import maps won't be processed in ScriptLoader::EvaluateScriptElement. r=jonco,yulia
https://hg.mozilla.org/integration/autoland/rev/44e9abe72a5e
Part 9: mochitest, xpcshell-test and web-platform-test for import maps. r=jonco,yulia,robwu

Error message:

/builds/worker/checkouts/gecko/js/loader/ImportMap.cpp(262,30): error: passing object of class type 'typename raw_type<char16_t, int>::type' (aka 'char16ptr_t') through variadic function [-Werror,-Wclass-varargs]
[task 2022-05-05T00:33:57.282Z] 00:33:57 INFO - scopePrefix.get());
[task 2022-05-05T00:33:57.283Z] 00:33:57 INFO - ^
[task 2022-05-05T00:33:57.283Z] 00:33:57 INFO - 1 error generated.

prefs could be only specified in [DEFAULT] section in ini, so moving
those import maps tests to its own folder.

Attachment #9275220 - Attachment description: Bug 1688879 - Part 11: Move import maps tests to its own folder. → Bug 1688879 - Part 11: Move import maps mochitests to its own folder.
Pushed by allstars.chh@gmail.com:
https://hg.mozilla.org/integration/autoland/rev/877bb4c2ce66
Part 1: Add Pref for import maps. r=jonco,yulia
https://hg.mozilla.org/integration/autoland/rev/0e60834e17e5
Part 2: Add support for import maps in ScriptElement/ScriptLoader/ScriptKind. r=jonco,yulia,smaug
https://hg.mozilla.org/integration/autoland/rev/adeab05b7419
Part 3: Parse and register an import map. r=jonco,yulia
https://hg.mozilla.org/integration/autoland/rev/05e0a1bf32fc
Part 4: Refactor ResolveModuleSpecifier. r=jonco,yulia
https://hg.mozilla.org/integration/autoland/rev/f5862572ced8
Part 5: ResolveModuleSpecifier for import maps. r=jonco,yulia,flod
https://hg.mozilla.org/integration/autoland/rev/c2bce95a1aca
Part 6: Acquiring import maps. r=jonco,yulia
https://hg.mozilla.org/integration/autoland/rev/77ab231310ec
Part 7: External import maps aren't supported. r=jonco,yulia
https://hg.mozilla.org/integration/autoland/rev/d8edcfdb504b
Part 8: Assert import maps won't be processed in ScriptLoader::EvaluateScriptElement. r=jonco,yulia
https://hg.mozilla.org/integration/autoland/rev/6a5bb063965f
Part 9: mochitest, xpcshell-test and web-platform-test for import maps. r=jonco,yulia,robwu
Pushed by allstars.chh@gmail.com:
https://hg.mozilla.org/integration/autoland/rev/27984b95ed20
Part 10: Fix class-varargs warnings in Windows builds. r=jonco
https://hg.mozilla.org/integration/autoland/rev/350ddd17c7f5
Part 11: Move import maps mochitests to its own folder. r=jonco

It looks like the patches to fix the compilation error on windows (https://hg.mozilla.org/integration/autoland/rev/27984b95ed20) and mochitest failure (https://hg.mozilla.org/integration/autoland/rev/350ddd17c7f5) are not applied?
https://treeherder.mozilla.org/jobs?repo=autoland&resultStatus=testfailed%2Cbusted%2Cexception%2Cretry%2Cusercancel&revision=6a5bb063965f2110ced3fb456ddc47eaf6f4db20

I'll merge Part 10 into Part 3, and Part 11 into Part 9, that should fix the error.

Flags: needinfo?(allstars.chh)
Pushed by allstars.chh@gmail.com:
https://hg.mozilla.org/integration/autoland/rev/0bde7359a1c9
Part 1: Add Pref for import maps. r=jonco,yulia
https://hg.mozilla.org/integration/autoland/rev/10e132dcfa25
Part 2: Add support for import maps in ScriptElement/ScriptLoader/ScriptKind. r=jonco,yulia,smaug
https://hg.mozilla.org/integration/autoland/rev/c448d9606387
Part 3: Parse and register an import map. r=jonco,yulia
https://hg.mozilla.org/integration/autoland/rev/c2e589f3626f
Part 4: Refactor ResolveModuleSpecifier. r=jonco,yulia
https://hg.mozilla.org/integration/autoland/rev/e008ed2df049
Part 5: ResolveModuleSpecifier for import maps. r=jonco,yulia,flod
https://hg.mozilla.org/integration/autoland/rev/1b727ca4acde
Part 6: Acquiring import maps. r=jonco,yulia
https://hg.mozilla.org/integration/autoland/rev/8cf72f24bfdb
Part 7: External import maps aren't supported. r=jonco,yulia
https://hg.mozilla.org/integration/autoland/rev/ed15822a3a58
Part 8: Assert import maps won't be processed in ScriptLoader::EvaluateScriptElement. r=jonco,yulia
https://hg.mozilla.org/integration/autoland/rev/9aa8fd3fbed4
Part 9: mochitest, xpcshell-test and web-platform-test for import maps. r=jonco,yulia,robwu
Regressions: 1768059

Yulia, is that an important enough enhancement that it should also be mentioned in our general release notes in the web standards section? If it is , could you request an addition to the release notes? (https://wiki.mozilla.org/Release_Management/Release_Notes#Nomination_in_Bugzilla)
Thanks!

Flags: needinfo?(ystartsev)

This isn't a standard right now, and we won't be exposing it by default until that changes. This proposal unfortunately shipped extremely early in chrome without standards integration and has made a bit of a mess. They're aware of this though. I would propose that we nominate the shipping bug, unless you want to highlight that people can test it by turning on the pref?

Flags: needinfo?(ystartsev) → needinfo?(pascalc)

If it's unfinished and still behind a pref on nightly, let's not add it to release notes yet. I think that once it's activated in some of our pre-release channels like nightly, dev edition or early betas, we should add it to the pre-release notes so as to encourage our community to report any problem they may experience, thanks.

Flags: needinfo?(pascalc)
Blocks: 1793926

MDN docs work for this can be tracked in https://github.com/mdn/content/issues/16150

Blocks: 1801764
No longer blocks: 1801764
Depends on: 1833371
Depends on: 1865410
Attachment #9275219 - Attachment is obsolete: true
Attachment #9275220 - Attachment is obsolete: true
You need to log in before you can comment on or make changes to this bug.

Attachment

General

Created:
Updated:
Size: