how many async-modules can js-app practically load?
Can you elaborate on what loading state you need to keep track of? What is
the bottleneck that you run into? Also to be sure, when you say async-load,
do you mean import()
?
Can you elaborate on what loading state you need to keep track of? What is the bottleneck that you run into? Also to be sure, when you say async-load, do you mean `import()`? On Wed, May 22, 2019, 20:17 kai zhu <kaizhu256 at gmail.com> wrote: > i don't use es-modules. > but with amd/requirejs, I start having trouble with module-initializations > in nodejs/browser at ~5 async modules (that may or may not have > circular-references). 10 would be hard, and 20 would be near inhuman for > me. > > can we say its somewhat impractical for most applications to load more > than 50 async modules (with some of them having circular-references)? and > perhaps better design/spec module-loading mechanisms with this usability > concern in mind? > > p.s. its also impractical for me to async-load 5 or more modules without > using globalThis to keep track of each module's loading-state. > _______________________________________________ > es-discuss mailing list > es-discuss at mozilla.org > https://mail.mozilla.org/listinfo/es-discuss > -------------- next part -------------- An HTML attachment was scrubbed... URL: <http://mail.mozilla.org/pipermail/es-discuss/attachments/20190522/bde38a63/attachment.html>
actually, i admit i don't know what i'm talking about. just generally confused (through ignorance) on how large-scale es-module dependencies resolve when loaded/imported asynchronously.
actually, i admit i don't know what i'm talking about. just generally confused (through ignorance) on how large-scale es-module dependencies resolve when loaded/imported asynchronously. On Wed, May 22, 2019 at 10:42 PM Logan Smyth <loganfsmyth at gmail.com> wrote: > Can you elaborate on what loading state you need to keep track of? What is > the bottleneck that you run into? Also to be sure, when you say async-load, > do you mean `import()`? > > On Wed, May 22, 2019, 20:17 kai zhu <kaizhu256 at gmail.com> wrote: > >> i don't use es-modules. >> but with amd/requirejs, I start having trouble with >> module-initializations in nodejs/browser at ~5 async modules (that may or >> may not have circular-references). 10 would be hard, and 20 would be near >> inhuman for me. >> >> can we say its somewhat impractical for most applications to load more >> than 50 async modules (with some of them having circular-references)? and >> perhaps better design/spec module-loading mechanisms with this usability >> concern in mind? >> >> p.s. its also impractical for me to async-load 5 or more modules without >> using globalThis to keep track of each module's loading-state. >> _______________________________________________ >> es-discuss mailing list >> es-discuss at mozilla.org >> https://mail.mozilla.org/listinfo/es-discuss >> > -------------- next part -------------- An HTML attachment was scrubbed... URL: <http://mail.mozilla.org/pipermail/es-discuss/attachments/20190523/7b6e2a2e/attachment.html>
There's two main reasons why it scales:
- Modules are strongly encapsulated while minimizing global pollution.
- The resolution algorithm applies the same logic no matter how many modules are loaded.
It's much easier for it to scale when you write the code unaware of how many modules you might be loading and unaware of how deep their dependency graph is. Fewer assumptions here is key. It's an engineering problem, but a relatively simple one.
If you want a short example of how sync module resolution works, you can take a look at this little utility I wrote: isiahmeadows/simple-require-loader. That doesn't asynchronously resolve modules, but it should help explain the process from a synchronous standpoint. Asynchronous loading differs only in that it takes more code to express the same logic and you have to take into account concurrent requests (and you need to cache the request, not the result), but it's otherwise the same from 1km away.
Isiah Meadows contact at isiahmeadows.com, www.isiahmeadows.com
There's two main reasons why it scales: 1. Modules are strongly encapsulated while minimizing global pollution. 2. The resolution algorithm applies the same logic no matter how many modules are loaded. It's much easier for it to scale when you write the code unaware of how many modules you might be loading and unaware of how deep their dependency graph is. Fewer assumptions here is key. It's an engineering problem, but a relatively simple one. If you want a short example of how sync module resolution works, you can take a look at this little utility I wrote: https://github.com/isiahmeadows/simple-require-loader. That doesn't asynchronously resolve modules, but it should help explain the process from a synchronous standpoint. Asynchronous loading differs only in that it takes more code to express the same logic and you have to take into account concurrent requests (and you need to cache the request, not the result), but it's otherwise the same from 1km away. ----- Isiah Meadows contact at isiahmeadows.com www.isiahmeadows.com On Thu, May 23, 2019 at 10:49 AM kai zhu <kaizhu256 at gmail.com> wrote: > > actually, i admit i don't know what i'm talking about. just generally confused (through ignorance) on how large-scale es-module dependencies resolve when loaded/imported asynchronously. > > On Wed, May 22, 2019 at 10:42 PM Logan Smyth <loganfsmyth at gmail.com> wrote: >> >> Can you elaborate on what loading state you need to keep track of? What is the bottleneck that you run into? Also to be sure, when you say async-load, do you mean `import()`? >> >> On Wed, May 22, 2019, 20:17 kai zhu <kaizhu256 at gmail.com> wrote: >>> >>> i don't use es-modules. >>> but with amd/requirejs, I start having trouble with module-initializations in nodejs/browser at ~5 async modules (that may or may not have circular-references). 10 would be hard, and 20 would be near inhuman for me. >>> >>> can we say its somewhat impractical for most applications to load more than 50 async modules (with some of them having circular-references)? and perhaps better design/spec module-loading mechanisms with this usability concern in mind? >>> >>> p.s. its also impractical for me to async-load 5 or more modules without using globalThis to keep track of each module's loading-state. >>> _______________________________________________ >>> es-discuss mailing list >>> es-discuss at mozilla.org >>> https://mail.mozilla.org/listinfo/es-discuss > > _______________________________________________ > es-discuss mailing list > es-discuss at mozilla.org > https://mail.mozilla.org/listinfo/es-discuss
Asynchronous loading differs only in that it takes more code to express the same logic and you have to take into account concurrent requests (and you need to cache the request, not the result), but it's otherwise the same from 1km away.
so async-loading 50 <script type="module">
tags
has equivalent side-effect as sync-loading single webpack-rollup (of same 50 modules)?
i have nagging suspicion of doubts. has anyone tried native async-loading large numbers (>10) of
<script type="module">
tags, and verify it resolves identically to using a single webpack-rollup?
again, i'm not that knowledgeable on es-modules, so above question may be trivially true, and i'm just not aware.
> Asynchronous loading differs only in > that it takes more code to express the same logic and you have to take > into account concurrent requests (and you need to cache the request, > not the result), but it's otherwise the same from 1km away. so async-loading 50 ```<script type="module">``` tags has equivalent side-effect as sync-loading single webpack-rollup (of same 50 modules)? i have nagging suspicion of doubts. has anyone tried native async-loading large numbers (>10) of ```<script type="module">``` tags, and verify it resolves identically to using a single webpack-rollup? again, i'm not that knowledgeable on es-modules, so above question may be trivially true, and i'm just not aware. -kai > On 24 May 2019, at 23:41, Isiah Meadows <isiahmeadows at gmail.com> wrote: > > There's two main reasons why it scales: > > 1. Modules are strongly encapsulated while minimizing global pollution. > 2. The resolution algorithm applies the same logic no matter how many > modules are loaded. > > It's much easier for it to scale when you write the code unaware of > how many modules you might be loading and unaware of how deep their > dependency graph is. Fewer assumptions here is key. It's an > engineering problem, but a relatively simple one. > > If you want a short example of how sync module resolution works, you > can take a look at this little utility I wrote: > https://github.com/isiahmeadows/simple-require-loader. That doesn't > asynchronously resolve modules, but it should help explain the process > from a synchronous standpoint. Asynchronous loading differs only in > that it takes more code to express the same logic and you have to take > into account concurrent requests (and you need to cache the request, > not the result), but it's otherwise the same from 1km away. > > ----- > > Isiah Meadows > contact at isiahmeadows.com > www.isiahmeadows.com > > On Thu, May 23, 2019 at 10:49 AM kai zhu <kaizhu256 at gmail.com> wrote: >> >> actually, i admit i don't know what i'm talking about. just generally confused (through ignorance) on how large-scale es-module dependencies resolve when loaded/imported asynchronously. >> >> On Wed, May 22, 2019 at 10:42 PM Logan Smyth <loganfsmyth at gmail.com> wrote: >>> >>> Can you elaborate on what loading state you need to keep track of? What is the bottleneck that you run into? Also to be sure, when you say async-load, do you mean `import()`? >>> >>> On Wed, May 22, 2019, 20:17 kai zhu <kaizhu256 at gmail.com> wrote: >>>> >>>> i don't use es-modules. >>>> but with amd/requirejs, I start having trouble with module-initializations in nodejs/browser at ~5 async modules (that may or may not have circular-references). 10 would be hard, and 20 would be near inhuman for me. >>>> >>>> can we say its somewhat impractical for most applications to load more than 50 async modules (with some of them having circular-references)? and perhaps better design/spec module-loading mechanisms with this usability concern in mind? >>>> >>>> p.s. its also impractical for me to async-load 5 or more modules without using globalThis to keep track of each module's loading-state. >>>> _______________________________________________ >>>> es-discuss mailing list >>>> es-discuss at mozilla.org >>>> https://mail.mozilla.org/listinfo/es-discuss >> >> _______________________________________________ >> es-discuss mailing list >> es-discuss at mozilla.org >> https://mail.mozilla.org/listinfo/es-discuss -------------- next part -------------- An HTML attachment was scrubbed... URL: <http://mail.mozilla.org/pipermail/es-discuss/attachments/20190525/50726f96/attachment-0001.html>
so async-loading 50
<script type="module">
tags has equivalent side-effect as sync-loading single webpack-rollup (of same 50 modules)?
Why would 50 separate <script type="module">
tags be needed?
has anyone tried native async-loading large numbers (>10) of
<script type="module">
tags, and verify it resolves identically to using a single webpack-rollup?
Have you tried the two described approaches and compared the result?
How is "identically" determined?
> so async-loading 50 ```<script type="module">``` tags has equivalent side-effect as sync-loading single webpack-rollup (of same 50 modules)? Why would 50 separate ```<script type="module">``` tags be needed? > has anyone tried native async-loading large numbers (>10) of ```<script type="module">``` tags, and verify it resolves identically to using a single webpack-rollup? Have you tried the two described approaches and compared the result? How is "identically" determined? On Sat, May 25, 2019 at 6:12 AM kai zhu <kaizhu256 at gmail.com> wrote: > Asynchronous loading differs only in > that it takes more code to express the same logic and you have to take > into account concurrent requests (and you need to cache the request, > not the result), but it's otherwise the same from 1km away. > > > so async-loading 50 ```<script type="module">``` tags > has equivalent side-effect > as sync-loading single webpack-rollup (of same 50 modules)? > > i have nagging suspicion of doubts. has anyone tried native async-loading > large numbers (>10) of > ```<script type="module">``` tags, and verify it resolves identically to > using a single webpack-rollup? > > again, i'm not that knowledgeable on es-modules, so above question may be > trivially true, and i'm just not aware. > > -kai > > On 24 May 2019, at 23:41, Isiah Meadows <isiahmeadows at gmail.com> wrote: > > There's two main reasons why it scales: > > 1. Modules are strongly encapsulated while minimizing global pollution. > 2. The resolution algorithm applies the same logic no matter how many > modules are loaded. > > It's much easier for it to scale when you write the code unaware of > how many modules you might be loading and unaware of how deep their > dependency graph is. Fewer assumptions here is key. It's an > engineering problem, but a relatively simple one. > > If you want a short example of how sync module resolution works, you > can take a look at this little utility I wrote: > https://github.com/isiahmeadows/simple-require-loader. That doesn't > asynchronously resolve modules, but it should help explain the process > from a synchronous standpoint. Asynchronous loading differs only in > that it takes more code to express the same logic and you have to take > into account concurrent requests (and you need to cache the request, > not the result), but it's otherwise the same from 1km away. > > ----- > > Isiah Meadows > contact at isiahmeadows.com > www.isiahmeadows.com > > On Thu, May 23, 2019 at 10:49 AM kai zhu <kaizhu256 at gmail.com> wrote: > > > actually, i admit i don't know what i'm talking about. just generally > confused (through ignorance) on how large-scale es-module dependencies > resolve when loaded/imported asynchronously. > > On Wed, May 22, 2019 at 10:42 PM Logan Smyth <loganfsmyth at gmail.com> > wrote: > > > Can you elaborate on what loading state you need to keep track of? What is > the bottleneck that you run into? Also to be sure, when you say async-load, > do you mean `import()`? > > On Wed, May 22, 2019, 20:17 kai zhu <kaizhu256 at gmail.com> wrote: > > > i don't use es-modules. > but with amd/requirejs, I start having trouble with module-initializations > in nodejs/browser at ~5 async modules (that may or may not have > circular-references). 10 would be hard, and 20 would be near inhuman for > me. > > can we say its somewhat impractical for most applications to load more > than 50 async modules (with some of them having circular-references)? and > perhaps better design/spec module-loading mechanisms with this usability > concern in mind? > > p.s. its also impractical for me to async-load 5 or more modules without > using globalThis to keep track of each module's loading-state. > _______________________________________________ > es-discuss mailing list > es-discuss at mozilla.org > https://mail.mozilla.org/listinfo/es-discuss > > > _______________________________________________ > es-discuss mailing list > es-discuss at mozilla.org > https://mail.mozilla.org/listinfo/es-discuss > > > _______________________________________________ > es-discuss mailing list > es-discuss at mozilla.org > https://mail.mozilla.org/listinfo/es-discuss > -------------- next part -------------- An HTML attachment was scrubbed... URL: <http://mail.mozilla.org/pipermail/es-discuss/attachments/20190525/637cfa36/attachment.html>
Why would 50 separate
<script type="module">
tags be needed?
because a reason for es-module's existence in the first place is to bring "large-scale modular development" to the browser. i want to test that claim (hence this thread's subject-title).
Have you tried the two described approaches and compared the result? How is "identically" determined?
no i haven't, and i suspect nobody does in practice, because they all use babel/webpack. identicality would be determined by if the app functions the same regardless whether you used a webpack-rollup or individual <script type="module">
tags.
> Why would 50 separate ```<script type="module">``` tags be needed? because a reason for es-module's existence in the first place is to bring "large-scale modular development" to the browser. i want to test that claim (hence this thread's subject-title). > Have you tried the two described approaches and compared the result? How is "identically" determined? no i haven't, and i suspect nobody does in practice, because they all use babel/webpack. identicality would be determined by if the app functions the same regardless whether you used a webpack-rollup or individual ```<script type="module">``` tags. -kai > On 25 May 2019, at 01:20, guest271314 <guest271314 at gmail.com> wrote: > > > so async-loading 50 ```<script type="module">``` tags has equivalent side-effect > as sync-loading single webpack-rollup (of same 50 modules)? > > Why would 50 separate ```<script type="module">``` tags be needed? > > > has anyone tried native async-loading large numbers (>10) of ```<script type="module">``` tags, and verify it resolves identically to using a single webpack-rollup? > > Have you tried the two described approaches and compared the result? > > How is "identically" determined? > > On Sat, May 25, 2019 at 6:12 AM kai zhu <kaizhu256 at gmail.com <mailto:kaizhu256 at gmail.com>> wrote: >> Asynchronous loading differs only in >> that it takes more code to express the same logic and you have to take >> into account concurrent requests (and you need to cache the request, >> not the result), but it's otherwise the same from 1km away. > > so async-loading 50 ```<script type="module">``` tags > has equivalent side-effect > as sync-loading single webpack-rollup (of same 50 modules)? > > i have nagging suspicion of doubts. has anyone tried native async-loading large numbers (>10) of > ```<script type="module">``` tags, and verify it resolves identically to using a single webpack-rollup? > > again, i'm not that knowledgeable on es-modules, so above question may be trivially true, and i'm just not aware. > > -kai > >> On 24 May 2019, at 23:41, Isiah Meadows <isiahmeadows at gmail.com <mailto:isiahmeadows at gmail.com>> wrote: >> >> There's two main reasons why it scales: >> >> 1. Modules are strongly encapsulated while minimizing global pollution. >> 2. The resolution algorithm applies the same logic no matter how many >> modules are loaded. >> >> It's much easier for it to scale when you write the code unaware of >> how many modules you might be loading and unaware of how deep their >> dependency graph is. Fewer assumptions here is key. It's an >> engineering problem, but a relatively simple one. >> >> If you want a short example of how sync module resolution works, you >> can take a look at this little utility I wrote: >> https://github.com/isiahmeadows/simple-require-loader <https://github.com/isiahmeadows/simple-require-loader>. That doesn't >> asynchronously resolve modules, but it should help explain the process >> from a synchronous standpoint. Asynchronous loading differs only in >> that it takes more code to express the same logic and you have to take >> into account concurrent requests (and you need to cache the request, >> not the result), but it's otherwise the same from 1km away. >> >> ----- >> >> Isiah Meadows >> contact at isiahmeadows.com <mailto:contact at isiahmeadows.com> >> www.isiahmeadows.com <http://www.isiahmeadows.com/> >> >> On Thu, May 23, 2019 at 10:49 AM kai zhu <kaizhu256 at gmail.com <mailto:kaizhu256 at gmail.com>> wrote: >>> >>> actually, i admit i don't know what i'm talking about. just generally confused (through ignorance) on how large-scale es-module dependencies resolve when loaded/imported asynchronously. >>> >>> On Wed, May 22, 2019 at 10:42 PM Logan Smyth <loganfsmyth at gmail.com <mailto:loganfsmyth at gmail.com>> wrote: >>>> >>>> Can you elaborate on what loading state you need to keep track of? What is the bottleneck that you run into? Also to be sure, when you say async-load, do you mean `import()`? >>>> >>>> On Wed, May 22, 2019, 20:17 kai zhu <kaizhu256 at gmail.com <mailto:kaizhu256 at gmail.com>> wrote: >>>>> >>>>> i don't use es-modules. >>>>> but with amd/requirejs, I start having trouble with module-initializations in nodejs/browser at ~5 async modules (that may or may not have circular-references). 10 would be hard, and 20 would be near inhuman for me. >>>>> >>>>> can we say its somewhat impractical for most applications to load more than 50 async modules (with some of them having circular-references)? and perhaps better design/spec module-loading mechanisms with this usability concern in mind? >>>>> >>>>> p.s. its also impractical for me to async-load 5 or more modules without using globalThis to keep track of each module's loading-state. >>>>> _______________________________________________ >>>>> es-discuss mailing list >>>>> es-discuss at mozilla.org <mailto:es-discuss at mozilla.org> >>>>> https://mail.mozilla.org/listinfo/es-discuss <https://mail.mozilla.org/listinfo/es-discuss> >>> >>> _______________________________________________ >>> es-discuss mailing list >>> es-discuss at mozilla.org <mailto:es-discuss at mozilla.org> >>> https://mail.mozilla.org/listinfo/es-discuss <https://mail.mozilla.org/listinfo/es-discuss> > > _______________________________________________ > es-discuss mailing list > es-discuss at mozilla.org <mailto:es-discuss at mozilla.org> > https://mail.mozilla.org/listinfo/es-discuss <https://mail.mozilla.org/listinfo/es-discuss> -------------- next part -------------- An HTML attachment was scrubbed... URL: <http://mail.mozilla.org/pipermail/es-discuss/attachments/20190525/5a04ce42/attachment-0001.html>
Have not tried babel or webpack. You can write the test to answer your own inquiry and post the result at a gist.
Have not tried babel or webpack. You can write the test to answer your own inquiry and post the result at a gist. On Sat, May 25, 2019 at 6:34 AM kai zhu <kaizhu256 at gmail.com> wrote: > Why would 50 separate ```<script type="module">``` tags be needed? > > > because a reason for es-module's existence in the first place is to bring > "large-scale modular development" to the browser. i want to test that > claim (hence this thread's subject-title). > > Have you tried the two described approaches and compared the result? How > is "identically" determined? > > > no i haven't, and i suspect nobody does in practice, because they all use > babel/webpack. identicality would be determined by if the app functions > the same regardless whether you used a webpack-rollup or individual ```<script > type="module">``` tags. > > -kai > > > > On 25 May 2019, at 01:20, guest271314 <guest271314 at gmail.com> wrote: > > > so async-loading 50 ```<script type="module">``` tags has equivalent > side-effect > as sync-loading single webpack-rollup (of same 50 modules)? > > Why would 50 separate ```<script type="module">``` tags be needed? > > > has anyone tried native async-loading large numbers (>10) of ```<script > type="module">``` tags, and verify it resolves identically to using a > single webpack-rollup? > > Have you tried the two described approaches and compared the result? > > How is "identically" determined? > > On Sat, May 25, 2019 at 6:12 AM kai zhu <kaizhu256 at gmail.com> wrote: > >> Asynchronous loading differs only in >> that it takes more code to express the same logic and you have to take >> into account concurrent requests (and you need to cache the request, >> not the result), but it's otherwise the same from 1km away. >> >> >> so async-loading 50 ```<script type="module">``` tags >> has equivalent side-effect >> as sync-loading single webpack-rollup (of same 50 modules)? >> >> i have nagging suspicion of doubts. has anyone tried native >> async-loading large numbers (>10) of >> ```<script type="module">``` tags, and verify it resolves identically to >> using a single webpack-rollup? >> >> again, i'm not that knowledgeable on es-modules, so above question may be >> trivially true, and i'm just not aware. >> >> -kai >> >> On 24 May 2019, at 23:41, Isiah Meadows <isiahmeadows at gmail.com> wrote: >> >> There's two main reasons why it scales: >> >> 1. Modules are strongly encapsulated while minimizing global pollution. >> 2. The resolution algorithm applies the same logic no matter how many >> modules are loaded. >> >> It's much easier for it to scale when you write the code unaware of >> how many modules you might be loading and unaware of how deep their >> dependency graph is. Fewer assumptions here is key. It's an >> engineering problem, but a relatively simple one. >> >> If you want a short example of how sync module resolution works, you >> can take a look at this little utility I wrote: >> https://github.com/isiahmeadows/simple-require-loader. That doesn't >> asynchronously resolve modules, but it should help explain the process >> from a synchronous standpoint. Asynchronous loading differs only in >> that it takes more code to express the same logic and you have to take >> into account concurrent requests (and you need to cache the request, >> not the result), but it's otherwise the same from 1km away. >> >> ----- >> >> Isiah Meadows >> contact at isiahmeadows.com >> www.isiahmeadows.com >> >> On Thu, May 23, 2019 at 10:49 AM kai zhu <kaizhu256 at gmail.com> wrote: >> >> >> actually, i admit i don't know what i'm talking about. just generally >> confused (through ignorance) on how large-scale es-module dependencies >> resolve when loaded/imported asynchronously. >> >> On Wed, May 22, 2019 at 10:42 PM Logan Smyth <loganfsmyth at gmail.com> >> wrote: >> >> >> Can you elaborate on what loading state you need to keep track of? What >> is the bottleneck that you run into? Also to be sure, when you say >> async-load, do you mean `import()`? >> >> On Wed, May 22, 2019, 20:17 kai zhu <kaizhu256 at gmail.com> wrote: >> >> >> i don't use es-modules. >> but with amd/requirejs, I start having trouble with >> module-initializations in nodejs/browser at ~5 async modules (that may or >> may not have circular-references). 10 would be hard, and 20 would be near >> inhuman for me. >> >> can we say its somewhat impractical for most applications to load more >> than 50 async modules (with some of them having circular-references)? and >> perhaps better design/spec module-loading mechanisms with this usability >> concern in mind? >> >> p.s. its also impractical for me to async-load 5 or more modules without >> using globalThis to keep track of each module's loading-state. >> _______________________________________________ >> es-discuss mailing list >> es-discuss at mozilla.org >> https://mail.mozilla.org/listinfo/es-discuss >> >> >> _______________________________________________ >> es-discuss mailing list >> es-discuss at mozilla.org >> https://mail.mozilla.org/listinfo/es-discuss >> >> >> _______________________________________________ >> es-discuss mailing list >> es-discuss at mozilla.org >> https://mail.mozilla.org/listinfo/es-discuss >> > > -------------- next part -------------- An HTML attachment was scrubbed... URL: <http://mail.mozilla.org/pipermail/es-discuss/attachments/20190525/2031de73/attachment.html>
If you come up with a benchmark for this, would you mind sharing the code and not just the results? I'm curious how my stuff will fare.
I'm in an environment where it is still not practical to use ES modules, and have started work again on BravoJS, which implements the old CommonJS Modules/2.0 strawman. (Same primordial development soup as AMD, but with a different set of flaws; favouring correctness/compatibility instead of brevity)
How I've solved this problem historically is to have some smarts on the server side, that feeds (transitive) dependencies of a module at the same time as the module. It will be interesting to play with that type of loader -- if possible -- once ES module loaders become well-defined/implemented/available.
We also have to remember that loading via SCRIPT tags -- type=module or not -- is important to developers, so that we can load modules from CDNs and so on without cross-site security pain.
Thanks,
If you come up with a benchmark for this, would you mind sharing the code and not just the results? I'm curious how my stuff will fare. I'm in an environment where it is still not practical to use ES modules, and have started work again on BravoJS, which implements the old CommonJS Modules/2.0 strawman. (Same primordial development soup as AMD, but with a different set of flaws; favouring correctness/compatibility instead of brevity) How I've solved this problem historically is to have some smarts on the server side, that feeds (transitive) dependencies of a module at the same time as the module. It will be interesting to play with that type of loader -- if possible -- once ES module loaders become well-defined/implemented/available. We also have to remember that loading via SCRIPT tags -- type=module or not -- is important to developers, so that we can load modules from CDNs and so on without cross-site security pain. Thanks, Wes On Sat, 25 May 2019 at 02:41, guest271314 <guest271314 at gmail.com> wrote: > Have not tried babel or webpack. You can write the test to answer your own > inquiry and post the result at a gist. > > On Sat, May 25, 2019 at 6:34 AM kai zhu <kaizhu256 at gmail.com> wrote: > >> Why would 50 separate ```<script type="module">``` tags be needed? >> >> >> because a reason for es-module's existence in the first place is to bring >> "large-scale modular development" to the browser. i want to test that >> claim (hence this thread's subject-title). >> >> Have you tried the two described approaches and compared the result? How >> is "identically" determined? >> >> >> no i haven't, and i suspect nobody does in practice, because they all use >> babel/webpack. identicality would be determined by if the app functions >> the same regardless whether you used a webpack-rollup or individual ```<script >> type="module">``` tags. >> >> -kai >> >> >> >> On 25 May 2019, at 01:20, guest271314 <guest271314 at gmail.com> wrote: >> >> > so async-loading 50 ```<script type="module">``` tags has equivalent >> side-effect >> as sync-loading single webpack-rollup (of same 50 modules)? >> >> Why would 50 separate ```<script type="module">``` tags be needed? >> >> > has anyone tried native async-loading large numbers (>10) of ```<script >> type="module">``` tags, and verify it resolves identically to using a >> single webpack-rollup? >> >> Have you tried the two described approaches and compared the result? >> >> How is "identically" determined? >> >> On Sat, May 25, 2019 at 6:12 AM kai zhu <kaizhu256 at gmail.com> wrote: >> >>> Asynchronous loading differs only in >>> that it takes more code to express the same logic and you have to take >>> into account concurrent requests (and you need to cache the request, >>> not the result), but it's otherwise the same from 1km away. >>> >>> >>> so async-loading 50 ```<script type="module">``` tags >>> has equivalent side-effect >>> as sync-loading single webpack-rollup (of same 50 modules)? >>> >>> i have nagging suspicion of doubts. has anyone tried native >>> async-loading large numbers (>10) of >>> ```<script type="module">``` tags, and verify it resolves identically >>> to using a single webpack-rollup? >>> >>> again, i'm not that knowledgeable on es-modules, so above question may >>> be trivially true, and i'm just not aware. >>> >>> -kai >>> >>> On 24 May 2019, at 23:41, Isiah Meadows <isiahmeadows at gmail.com> wrote: >>> >>> There's two main reasons why it scales: >>> >>> 1. Modules are strongly encapsulated while minimizing global pollution. >>> 2. The resolution algorithm applies the same logic no matter how many >>> modules are loaded. >>> >>> It's much easier for it to scale when you write the code unaware of >>> how many modules you might be loading and unaware of how deep their >>> dependency graph is. Fewer assumptions here is key. It's an >>> engineering problem, but a relatively simple one. >>> >>> If you want a short example of how sync module resolution works, you >>> can take a look at this little utility I wrote: >>> https://github.com/isiahmeadows/simple-require-loader. That doesn't >>> asynchronously resolve modules, but it should help explain the process >>> from a synchronous standpoint. Asynchronous loading differs only in >>> that it takes more code to express the same logic and you have to take >>> into account concurrent requests (and you need to cache the request, >>> not the result), but it's otherwise the same from 1km away. >>> >>> ----- >>> >>> Isiah Meadows >>> contact at isiahmeadows.com >>> www.isiahmeadows.com >>> >>> On Thu, May 23, 2019 at 10:49 AM kai zhu <kaizhu256 at gmail.com> wrote: >>> >>> >>> actually, i admit i don't know what i'm talking about. just generally >>> confused (through ignorance) on how large-scale es-module dependencies >>> resolve when loaded/imported asynchronously. >>> >>> On Wed, May 22, 2019 at 10:42 PM Logan Smyth <loganfsmyth at gmail.com> >>> wrote: >>> >>> >>> Can you elaborate on what loading state you need to keep track of? What >>> is the bottleneck that you run into? Also to be sure, when you say >>> async-load, do you mean `import()`? >>> >>> On Wed, May 22, 2019, 20:17 kai zhu <kaizhu256 at gmail.com> wrote: >>> >>> >>> i don't use es-modules. >>> but with amd/requirejs, I start having trouble with >>> module-initializations in nodejs/browser at ~5 async modules (that may or >>> may not have circular-references). 10 would be hard, and 20 would be near >>> inhuman for me. >>> >>> can we say its somewhat impractical for most applications to load more >>> than 50 async modules (with some of them having circular-references)? and >>> perhaps better design/spec module-loading mechanisms with this usability >>> concern in mind? >>> >>> p.s. its also impractical for me to async-load 5 or more modules without >>> using globalThis to keep track of each module's loading-state. >>> _______________________________________________ >>> es-discuss mailing list >>> es-discuss at mozilla.org >>> https://mail.mozilla.org/listinfo/es-discuss >>> >>> >>> _______________________________________________ >>> es-discuss mailing list >>> es-discuss at mozilla.org >>> https://mail.mozilla.org/listinfo/es-discuss >>> >>> >>> _______________________________________________ >>> es-discuss mailing list >>> es-discuss at mozilla.org >>> https://mail.mozilla.org/listinfo/es-discuss >>> >> >> _______________________________________________ > es-discuss mailing list > es-discuss at mozilla.org > https://mail.mozilla.org/listinfo/es-discuss > -- Wesley W. Garland Director, Product Development PageMail, Inc. +1 613 542 2787 x 102 -------------- next part -------------- An HTML attachment was scrubbed... URL: <http://mail.mozilla.org/pipermail/es-discuss/attachments/20190525/1f632f1e/attachment.html>
If you come up with a benchmark for this, would you mind sharing the code and not just the results? I'm curious how my stuff will fare.
What specifically should be tested and compared and benchmarked? The same code being used at different computers; or different code used at the same computer? What are you trying to determine?
The current question asks
how many async-modules can js-app practically load?
which leads to asking how many async-modules are actually needed?
From the outset one primary limiting factor as to "how many" would probably be the available RAM and hard disk space of the computer used (and browser preferences; cache policies; configuration) to load the modules (before the browser/OS freezes), similar to asking the maximum content-length of a file which can be fetched and downloaded and the length of time such a procedure takes in the browser, which depends on the available RAM and hard-disk space of the computer(s) used (e.g., see How to solve Uncaught RangeError when download large size json stackoverflow.com/q/39959467 ; stackoverflow.com/questions/39959467#comment67315240_40017582) where the result can vary considerably when testing code on different computers, depending on available RAM and hard-disk space of the computer (for example, comparing results at a minimal OS at Raspberry Pi with 500MB of available RAM and the same OS having 16GB RAM; or a non-minimal OS with multiple applications and the browser running compared to only the browser application running; including or not including the cost of loading the code which loads the async modules - if the code is not shipped with the browser - in the test results; etc.). The tentative answer to the original question "how many async-modules can js-app practically load?" would be until memory and available disk space runs out.
Tests of such code should also include the hardware and software used for the test and perform the various tests at the same computer - which will be compared to the other tests performed at the same computer, locally. Then those test results can be compared to different architectures, browsers (browsers implement specifications and code differently; consider Why does Firefox produce larger WebM video files compared with Chrome? stackoverflow.com/q/54651869 "However, Firefox still ends up creating up to 4 times larger files compared with Chrome."; stackoverflow.com/a/54652768 "Because they don't use the same settings..."; gist.github.com/guest271314/f942fb9febd9c197bd3824973794ba3e ; gist.github.com/guest271314/17d62bf74a97d3f111aa25605a9cd1ca), OS's, configurations to create a graph of the various combinations for comparative analysis.
Online tests of code (e.g. jsPerf) can provide inaccurate results, see stackoverflow.com/questions/46516234#comment80198567_46623314 ; microbenchmarks fairy tale mrale.ph/blog/2012/12/15/microbenchmarks-fairy-tale.html (note also the list item links at this answer stackoverflow.com/a/47173390 at Why is using a loop to iterate from start of array to end faster than iterating both start to end and end to start? stackoverflow.com/q/47049004); Is TIO acceptable for fastest-code questions? codegolf.meta.stackexchange.com/q/12707 ; codegolf.meta.stackexchange.com/a/12708
Unfortunately, I don't think TIO is a very reliable way of timing code, even if counting CPU time rather than wall time.
First of all, TIO uses multiple arena servers, where all user-supplied code is run. At point, there are only two arenas and both have identical specs, but even now, one of them is consistently and considerably slower than the other. I have no idea why this happens, but it does.
Also – and this applies to all method of timing code – two processes running at the same time can affect each other in subtle ways that will impact CPU time. E.g., speed of memory access may be affected, especially if the data should already be in the CPU's cache, but was pushed out by another process. Computers also tend to be measurably faster after a restart.
Of course, running code on TIO is still better than having everyone time their code on their own machines. I wouldn't even consider the latter an objective winning criterion for a fastest-code challenge.
codegolf.meta.stackexchange.com/questions/12707#comment43256_12708
Sorry, I meant having people time their code on their own machines. That's a fastest-computer challenge, not a fastest-code challenge. There's also no way of verifying the scores.
Again, have not tried babel or webpack for the purpose of loading modules. Where possible, try to use only and test code that is shipped with FOSS browsers, when the code is being used in the FOSS browser.
> If you come up with a benchmark for this, would you mind sharing the code and not just the results? I'm curious how my stuff will fare. What specifically should be compared? What are you trying to determine? The current question asks > how many async-modules can js-app practically load? which leads to asking how many async-modules are actually needed? >From the outset the presumptive answer would probably be the available RAM and hard disk space of the computer used (and browser preferences, policies, configuration) to load the modules, similar to asking the maximum content-length of a file which can be fetched and downloaded and the length of time such a procedure takes in the browser, which depends on the available RAM and hard-disk space of the computer(s) used; e.g., see How to solve Uncaught RangeError when download large size json https://stackoverflow.com/q/39959467 where the result is can be vary vastly when using devices having different available RAM and hard-disk space. Again, have not tried babel or webpack for the purpose of loading modules. Normally try to use only code that is shipped with FOSS browsers, when the code is being used in the browser, where possible. On Sat, May 25, 2019 at 7:57 PM Wes Garland <wes at page.ca> wrote: > If you come up with a benchmark for this, would you mind sharing the code > and not just the results? I'm curious how my stuff will fare. > > I'm in an environment where it is still not practical to use ES modules, > and have started work again on BravoJS, which implements the old CommonJS > Modules/2.0 strawman. (Same primordial development soup as AMD, but with a > different set of flaws; favouring correctness/compatibility instead of > brevity) > > How I've solved this problem historically is to have some smarts on the > server side, that feeds (transitive) dependencies of a module at the same > time as the module. It will be interesting to play with that type of > loader -- if possible -- once ES module loaders become > well-defined/implemented/available. > > We also have to remember that loading via SCRIPT tags -- type=module or > not -- is important to developers, so that we can load modules from CDNs > and so on without cross-site security pain. > > Thanks, > Wes > > On Sat, 25 May 2019 at 02:41, guest271314 <guest271314 at gmail.com> wrote: > >> Have not tried babel or webpack. You can write the test to answer your >> own inquiry and post the result at a gist. >> >> On Sat, May 25, 2019 at 6:34 AM kai zhu <kaizhu256 at gmail.com> wrote: >> >>> Why would 50 separate ```<script type="module">``` tags be needed? >>> >>> >>> because a reason for es-module's existence in the first place is to >>> bring "large-scale modular development" to the browser. i want to test >>> that claim (hence this thread's subject-title). >>> >>> Have you tried the two described approaches and compared the result? How >>> is "identically" determined? >>> >>> >>> no i haven't, and i suspect nobody does in practice, because they all >>> use babel/webpack. identicality would be determined by if the app >>> functions the same regardless whether you used a webpack-rollup or >>> individual ```<script type="module">``` tags. >>> >>> -kai >>> >>> >>> >>> On 25 May 2019, at 01:20, guest271314 <guest271314 at gmail.com> wrote: >>> >>> > so async-loading 50 ```<script type="module">``` tags has equivalent >>> side-effect >>> as sync-loading single webpack-rollup (of same 50 modules)? >>> >>> Why would 50 separate ```<script type="module">``` tags be needed? >>> >>> > has anyone tried native async-loading large numbers (>10) of ```<script >>> type="module">``` tags, and verify it resolves identically to using a >>> single webpack-rollup? >>> >>> Have you tried the two described approaches and compared the result? >>> >>> How is "identically" determined? >>> >>> On Sat, May 25, 2019 at 6:12 AM kai zhu <kaizhu256 at gmail.com> wrote: >>> >>>> Asynchronous loading differs only in >>>> that it takes more code to express the same logic and you have to take >>>> into account concurrent requests (and you need to cache the request, >>>> not the result), but it's otherwise the same from 1km away. >>>> >>>> >>>> so async-loading 50 ```<script type="module">``` tags >>>> has equivalent side-effect >>>> as sync-loading single webpack-rollup (of same 50 modules)? >>>> >>>> i have nagging suspicion of doubts. has anyone tried native >>>> async-loading large numbers (>10) of >>>> ```<script type="module">``` tags, and verify it resolves identically >>>> to using a single webpack-rollup? >>>> >>>> again, i'm not that knowledgeable on es-modules, so above question may >>>> be trivially true, and i'm just not aware. >>>> >>>> -kai >>>> >>>> On 24 May 2019, at 23:41, Isiah Meadows <isiahmeadows at gmail.com> wrote: >>>> >>>> There's two main reasons why it scales: >>>> >>>> 1. Modules are strongly encapsulated while minimizing global pollution. >>>> 2. The resolution algorithm applies the same logic no matter how many >>>> modules are loaded. >>>> >>>> It's much easier for it to scale when you write the code unaware of >>>> how many modules you might be loading and unaware of how deep their >>>> dependency graph is. Fewer assumptions here is key. It's an >>>> engineering problem, but a relatively simple one. >>>> >>>> If you want a short example of how sync module resolution works, you >>>> can take a look at this little utility I wrote: >>>> https://github.com/isiahmeadows/simple-require-loader. That doesn't >>>> asynchronously resolve modules, but it should help explain the process >>>> from a synchronous standpoint. Asynchronous loading differs only in >>>> that it takes more code to express the same logic and you have to take >>>> into account concurrent requests (and you need to cache the request, >>>> not the result), but it's otherwise the same from 1km away. >>>> >>>> ----- >>>> >>>> Isiah Meadows >>>> contact at isiahmeadows.com >>>> www.isiahmeadows.com >>>> >>>> On Thu, May 23, 2019 at 10:49 AM kai zhu <kaizhu256 at gmail.com> wrote: >>>> >>>> >>>> actually, i admit i don't know what i'm talking about. just generally >>>> confused (through ignorance) on how large-scale es-module dependencies >>>> resolve when loaded/imported asynchronously. >>>> >>>> On Wed, May 22, 2019 at 10:42 PM Logan Smyth <loganfsmyth at gmail.com> >>>> wrote: >>>> >>>> >>>> Can you elaborate on what loading state you need to keep track of? What >>>> is the bottleneck that you run into? Also to be sure, when you say >>>> async-load, do you mean `import()`? >>>> >>>> On Wed, May 22, 2019, 20:17 kai zhu <kaizhu256 at gmail.com> wrote: >>>> >>>> >>>> i don't use es-modules. >>>> but with amd/requirejs, I start having trouble with >>>> module-initializations in nodejs/browser at ~5 async modules (that may or >>>> may not have circular-references). 10 would be hard, and 20 would be near >>>> inhuman for me. >>>> >>>> can we say its somewhat impractical for most applications to load more >>>> than 50 async modules (with some of them having circular-references)? and >>>> perhaps better design/spec module-loading mechanisms with this usability >>>> concern in mind? >>>> >>>> p.s. its also impractical for me to async-load 5 or more modules >>>> without using globalThis to keep track of each module's loading-state. >>>> _______________________________________________ >>>> es-discuss mailing list >>>> es-discuss at mozilla.org >>>> https://mail.mozilla.org/listinfo/es-discuss >>>> >>>> >>>> _______________________________________________ >>>> es-discuss mailing list >>>> es-discuss at mozilla.org >>>> https://mail.mozilla.org/listinfo/es-discuss >>>> >>>> >>>> _______________________________________________ >>>> es-discuss mailing list >>>> es-discuss at mozilla.org >>>> https://mail.mozilla.org/listinfo/es-discuss >>>> >>> >>> _______________________________________________ >> es-discuss mailing list >> es-discuss at mozilla.org >> https://mail.mozilla.org/listinfo/es-discuss >> > > > -- > Wesley W. Garland > Director, Product Development > PageMail, Inc. > +1 613 542 2787 x 102 > -------------- next part -------------- An HTML attachment was scrubbed... URL: <http://mail.mozilla.org/pipermail/es-discuss/attachments/20190525/5fca06f2/attachment-0001.html>
Pretty sure your issue here is the multiple <script type="module"> tags.
In an ES module environment, you're supposed to set one entry point (with one script type module tag). Then use import statements to load in the other modules. The from string should be a URI that the browser can load modules from. To make this async, you would use the dynamic import( ... ) function syntax. Currently this has the issue that the browser has to parse each file to find and fetch it's dependencies. There's a couple of proposals to address this. Currently, in chromium based browsers, you can add module preload links in the header like so:
<link rel="modulepreload" href="lib.mjs"> <link rel="modulepreload" href="main.mjs">
So for your example, you would use one <script type="module"> tag and 50 <link rel="modulepreload"> tags. "modulepreload" has been added to the HTML standard, but is not implemented everywhere.
There's also the import maps proposal WICG/import-maps which would use a single manifest file to hint the dependency map to the browser instead of a stack of tags. It also contains a method for recognising package names, so, like in node, you can import from a package name instead of from a URL
Pretty sure your issue here is the multiple <script type="module"> tags. In an ES module environment, you're supposed to set one entry point (with one script type module tag). Then use import statements to load in the other modules. The from string should be a URI that the browser can load modules from. To make this async, you would use the dynamic import( ... ) function syntax. Currently this has the issue that the browser has to parse each file to find and fetch it's dependencies. There's a couple of proposals to address this. Currently, in chromium based browsers, you can add module preload links in the header like so: <link rel="modulepreload" href="lib.mjs"> <link rel="modulepreload" href="main.mjs"> So for your example, you would use one <script type="module"> tag and 50 <link rel="modulepreload"> tags. "modulepreload" has been added to the HTML standard, but is not implemented everywhere. There's also the import maps proposal https://github.com/WICG/import-maps which would use a single manifest file to hint the dependency map to the browser instead of a stack of tags. It also contains a method for recognising package names, so, like in node, you can import from a package name instead of from a URL On May 26 2019, at 8:02 am, guest271314 <guest271314 at gmail.com> wrote: > > If you come up with a benchmark for this, would you mind sharing the code and not just the results? I'm curious how my stuff will fare. > > What specifically should be compared? What are you trying to determine? > > The current question asks > > > how many async-modules can js-app practically load? > > which leads to asking how many async-modules are actually needed? > > From the outset the presumptive answer would probably be the available RAM and hard disk space of the computer used (and browser preferences, policies, configuration) to load the modules, similar to asking the maximum content-length of a file which can be fetched and downloaded and the length of time such a procedure takes in the browser, which depends on the available RAM and hard-disk space of the computer(s) used; e.g., see How to solve Uncaught RangeError when download large size json > https://stackoverflow.com/q/39959467 where the result is can be vary vastly when using devices having different available RAM and hard-disk space. > > > Again, have not tried babel or webpack for the purpose of loading modules. Normally try to use only code that is shipped with FOSS browsers, when the code is being used in the browser, where possible. > On Sat, May 25, 2019 at 7:57 PM Wes Garland <wes at page.ca (mailto:wes at page.ca)> wrote: > > If you come up with a benchmark for this, would you mind sharing the code and not just the results? I'm curious how my stuff will fare. > > > > I'm in an environment where it is still not practical to use ES modules, and have started work again on BravoJS, which implements the old CommonJS Modules/2.0 strawman. (Same primordial development soup as AMD, but with a different set of flaws; favouring correctness/compatibility instead of brevity) > > How I've solved this problem historically is to have some smarts on the server side, that feeds (transitive) dependencies of a module at the same time as the module. It will be interesting to play with that type of loader -- if possible -- once ES module loaders become well-defined/implemented/available. > > We also have to remember that loading via SCRIPT tags -- type=module or not -- is important to developers, so that we can load modules from CDNs and so on without cross-site security pain. > > > > Thanks, > > Wes > > > > > > On Sat, 25 May 2019 at 02:41, guest271314 <guest271314 at gmail.com (mailto:guest271314 at gmail.com)> wrote: > > > Have not tried babel or webpack. You can write the test to answer your own inquiry and post the result at a gist. > > > > > > On Sat, May 25, 2019 at 6:34 AM kai zhu <kaizhu256 at gmail.com (mailto:kaizhu256 at gmail.com)> wrote: > > > > > Why would 50 separate ```<script type="module">``` tags be needed? > > > > > > > > > > > > > > > > > because a reason for es-module's existence in the first place is to bring "large-scale modular development" to the browser. i want to test that claim (hence this thread's subject-title). > > > > > Have you tried the two described approaches and compared the result? How is "identically" determined? > > > > > > > > no i haven't, and i suspect nobody does in practice, because they all use babel/webpack. identicality would be determined by if the app functions the same regardless whether you used a webpack-rollup or individual ```<script type="module">``` tags. > > > > > > > > -kai > > > > > > > > > > > > > > > > > On 25 May 2019, at 01:20, guest271314 <guest271314 at gmail.com (mailto:guest271314 at gmail.com)> wrote: > > > > > > so async-loading 50 ```<script type="module">``` tags has equivalent side-effect > > > > > as sync-loading single webpack-rollup (of same 50 modules)? > > > > > > > > > > Why would 50 separate ```<script type="module">``` tags be needed? > > > > > > > > > > > has anyone tried native async-loading large numbers (>10) of ```<script type="module">``` tags, and verify it resolves identically to using a single webpack-rollup? > > > > > > > > > > Have you tried the two described approaches and compared the result? > > > > > > > > > > How is "identically" determined? > > > > > On Sat, May 25, 2019 at 6:12 AM kai zhu <kaizhu256 at gmail.com (mailto:kaizhu256 at gmail.com)> wrote: > > > > > > > Asynchronous loading differs only in > > > > > > > that it takes more code to express the same logic and you have to take > > > > > > > into account concurrent requests (and you need to cache the request, > > > > > > > not the result), but it's otherwise the same from 1km away. > > > > > > > > > > > > > > > > > > so async-loading 50 ```<script type="module">``` tags > > > > > > has equivalent side-effect > > > > > > as sync-loading single webpack-rollup (of same 50 modules)? > > > > > > > > > > > > i have nagging suspicion of doubts. has anyone tried native async-loading large numbers (>10) of > > > > > > ```<script type="module">``` tags, and verify it resolves identically to using a single webpack-rollup? > > > > > > > > > > > > again, i'm not that knowledgeable on es-modules, so above question may be trivially true, and i'm just not aware. > > > > > > > > > > > > -kai > > > > > > > > > > > > > On 24 May 2019, at 23:41, Isiah Meadows <isiahmeadows at gmail.com (mailto:isiahmeadows at gmail.com)> wrote: > > > > > > > There's two main reasons why it scales: > > > > > > > 1. Modules are strongly encapsulated while minimizing global pollution. > > > > > > > 2. The resolution algorithm applies the same logic no matter how many > > > > > > > modules are loaded. > > > > > > > > > > > > > > It's much easier for it to scale when you write the code unaware of > > > > > > > how many modules you might be loading and unaware of how deep their > > > > > > > dependency graph is. Fewer assumptions here is key. It's an > > > > > > > engineering problem, but a relatively simple one. > > > > > > > > > > > > > > If you want a short example of how sync module resolution works, you > > > > > > > can take a look at this little utility I wrote: > > > > > > > https://github.com/isiahmeadows/simple-require-loader. That doesn't > > > > > > > asynchronously resolve modules, but it should help explain the process > > > > > > > from a synchronous standpoint. Asynchronous loading differs only in > > > > > > > that it takes more code to express the same logic and you have to take > > > > > > > into account concurrent requests (and you need to cache the request, > > > > > > > not the result), but it's otherwise the same from 1km away. > > > > > > > > > > > > > > ----- > > > > > > > Isiah Meadows > > > > > > > contact at isiahmeadows.com (mailto:contact at isiahmeadows.com) > > > > > > > www.isiahmeadows.com (http://www.isiahmeadows.com/) > > > > > > > > > > > > > > On Thu, May 23, 2019 at 10:49 AM kai zhu <kaizhu256 at gmail.com (mailto:kaizhu256 at gmail.com)> wrote: > > > > > > > > > > > > > > > > actually, i admit i don't know what i'm talking about. just generally confused (through ignorance) on how large-scale es-module dependencies resolve when loaded/imported asynchronously. > > > > > > > > On Wed, May 22, 2019 at 10:42 PM Logan Smyth <loganfsmyth at gmail.com (mailto:loganfsmyth at gmail.com)> wrote: > > > > > > > > > > > > > > > > > > Can you elaborate on what loading state you need to keep track of? What is the bottleneck that you run into? Also to be sure, when you say async-load, do you mean `import()`? > > > > > > > > > On Wed, May 22, 2019, 20:17 kai zhu <kaizhu256 at gmail.com (mailto:kaizhu256 at gmail.com)> wrote: > > > > > > > > > > > > > > > > > > > > i don't use es-modules. > > > > > > > > > > but with amd/requirejs, I start having trouble with module-initializations in nodejs/browser at ~5 async modules (that may or may not have circular-references). 10 would be hard, and 20 would be near inhuman for me. > > > > > > > > > > > > > > > > > > > > can we say its somewhat impractical for most applications to load more than 50 async modules (with some of them having circular-references)? and perhaps better design/spec module-loading mechanisms with this usability concern in mind? > > > > > > > > > > p.s. its also impractical for me to async-load 5 or more modules without using globalThis to keep track of each module's loading-state. > > > > > > > > > > _______________________________________________ > > > > > > > > > > es-discuss mailing list > > > > > > > > > > es-discuss at mozilla.org (mailto:es-discuss at mozilla.org) > > > > > > > > > > https://mail.mozilla.org/listinfo/es-discuss > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > _______________________________________________ > > > > > > > > es-discuss mailing list > > > > > > > > es-discuss at mozilla.org (mailto:es-discuss at mozilla.org) > > > > > > > > https://mail.mozilla.org/listinfo/es-discuss > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > _______________________________________________ > > > > > > es-discuss mailing list > > > > > > es-discuss at mozilla.org (mailto:es-discuss at mozilla.org) > > > > > > https://mail.mozilla.org/listinfo/es-discuss > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > _______________________________________________ > > > es-discuss mailing list > > > es-discuss at mozilla.org (mailto:es-discuss at mozilla.org) > > > https://mail.mozilla.org/listinfo/es-discuss > > > > > > > > > > -- > > Wesley W. Garland > > Director, Product Development > > PageMail, Inc. > > +1 613 542 2787 x 102 > > > > > _______________________________________________ > es-discuss mailing list > es-discuss at mozilla.org > https://mail.mozilla.org/listinfo/es-discuss > -------------- next part -------------- An HTML attachment was scrubbed... URL: <http://mail.mozilla.org/pipermail/es-discuss/attachments/20190531/e8b0bef5/attachment-0001.html>
If it's bundled by Rollup or Webpack into a single bundle, it's
equivalent to a single <script type="module" src="...">
pointing
towards the original entry point, excluding network requests.* But in either case, you aren't listing 50 scripts, you're only listing the entry module and importing child modules within parent modules. Rollup and Webpack do mostly the same thing browsers do when it comes to resolving dependencies, just they generate a bundle afterwards where browsers execute code afterwards. Also, it's worth noting that the gap between a single large request and multiple smaller requests has shrunk a lot since HTTP/2 came along, since it's binary, it allows requests and response data to be interleaved, it better leverages the underlying TCP protocol format, and it allows servers to send data pre-emptively without the client requesting it first. (Web sockets are built on this functionality.) It's still better to bundle in general, but it's less of a problem not to.
This is not the case for <script type="module">
elements - those
operate more like inline scripts that happen to have the ability to
import
.
Oh, and yes, I've loaded upwards of 50-100 modules in development. 20 modules is easy to achieve in single-page apps.
- This is, of course, not the case if you are using pure ES6 and you aren't using any plugins to, say, run the original source through Babel for React + JSX or something.
Isiah Meadows contact at isiahmeadows.com, www.isiahmeadows.com
If it's bundled by Rollup or Webpack into a single bundle, it's equivalent to a single `<script type="module" src="...">` pointing towards the original entry point, excluding network requests.* But in either case, you aren't listing 50 scripts, you're only listing the entry module and importing child modules within parent modules. Rollup and Webpack do mostly the same thing browsers do when it comes to resolving dependencies, just they generate a bundle afterwards where browsers execute code afterwards. Also, it's worth noting that the gap between a single large request and multiple smaller requests has shrunk a lot since HTTP/2 came along, since it's binary, it allows requests and response data to be interleaved, it better leverages the underlying TCP protocol format, and it allows servers to send data pre-emptively without the client requesting it first. (Web sockets are built on this functionality.) It's still better to bundle in general, but it's less of a problem not to. This is *not* the case for `<script type="module">` elements - those operate more like inline scripts that happen to have the ability to `import`. Oh, and yes, I've loaded upwards of 50-100 modules in development. 20 modules is *easy* to achieve in single-page apps. * This is, of course, not the case if you are using pure ES6 and you aren't using any plugins to, say, run the original source through Babel for React + JSX or something. ----- Isiah Meadows contact at isiahmeadows.com www.isiahmeadows.com On Sat, May 25, 2019 at 2:12 AM kai zhu <kaizhu256 at gmail.com> wrote: > > Asynchronous loading differs only in > that it takes more code to express the same logic and you have to take > into account concurrent requests (and you need to cache the request, > not the result), but it's otherwise the same from 1km away. > > > so async-loading 50 ```<script type="module">``` tags > has equivalent side-effect > as sync-loading single webpack-rollup (of same 50 modules)? > > i have nagging suspicion of doubts. has anyone tried native async-loading large numbers (>10) of > ```<script type="module">``` tags, and verify it resolves identically to using a single webpack-rollup? > > again, i'm not that knowledgeable on es-modules, so above question may be trivially true, and i'm just not aware. > > -kai > > On 24 May 2019, at 23:41, Isiah Meadows <isiahmeadows at gmail.com> wrote: > > There's two main reasons why it scales: > > 1. Modules are strongly encapsulated while minimizing global pollution. > 2. The resolution algorithm applies the same logic no matter how many > modules are loaded. > > It's much easier for it to scale when you write the code unaware of > how many modules you might be loading and unaware of how deep their > dependency graph is. Fewer assumptions here is key. It's an > engineering problem, but a relatively simple one. > > If you want a short example of how sync module resolution works, you > can take a look at this little utility I wrote: > https://github.com/isiahmeadows/simple-require-loader. That doesn't > asynchronously resolve modules, but it should help explain the process > from a synchronous standpoint. Asynchronous loading differs only in > that it takes more code to express the same logic and you have to take > into account concurrent requests (and you need to cache the request, > not the result), but it's otherwise the same from 1km away. > > ----- > > Isiah Meadows > contact at isiahmeadows.com > www.isiahmeadows.com > > On Thu, May 23, 2019 at 10:49 AM kai zhu <kaizhu256 at gmail.com> wrote: > > > actually, i admit i don't know what i'm talking about. just generally confused (through ignorance) on how large-scale es-module dependencies resolve when loaded/imported asynchronously. > > On Wed, May 22, 2019 at 10:42 PM Logan Smyth <loganfsmyth at gmail.com> wrote: > > > Can you elaborate on what loading state you need to keep track of? What is the bottleneck that you run into? Also to be sure, when you say async-load, do you mean `import()`? > > On Wed, May 22, 2019, 20:17 kai zhu <kaizhu256 at gmail.com> wrote: > > > i don't use es-modules. > but with amd/requirejs, I start having trouble with module-initializations in nodejs/browser at ~5 async modules (that may or may not have circular-references). 10 would be hard, and 20 would be near inhuman for me. > > can we say its somewhat impractical for most applications to load more than 50 async modules (with some of them having circular-references)? and perhaps better design/spec module-loading mechanisms with this usability concern in mind? > > p.s. its also impractical for me to async-load 5 or more modules without using globalThis to keep track of each module's loading-state. > _______________________________________________ > es-discuss mailing list > es-discuss at mozilla.org > https://mail.mozilla.org/listinfo/es-discuss > > > _______________________________________________ > es-discuss mailing list > es-discuss at mozilla.org > https://mail.mozilla.org/listinfo/es-discuss > >
Oh, and yes, I've loaded upwards of 50-100 modules in development. 20
modules is easy to achieve in single-page apps.
was that with some combination of babel/rollup/webpack or pure-es6? if i want to develop a pure-es6 webapp (no babel), how would i transition from development-mode (20 es-module files) -> production-mode (1 rollup
file)?
> Oh, and yes, I've loaded upwards of 50-100 modules in development. 20 modules is *easy* to achieve in single-page apps. was that with some combination of babel/rollup/webpack or pure-es6? if i want to develop a pure-es6 webapp (no babel), how would i transition from development-mode (20 es-module files) -> production-mode (1 rollup file)? On Fri, May 31, 2019 at 10:47 AM Isiah Meadows <isiahmeadows at gmail.com> wrote: > If it's bundled by Rollup or Webpack into a single bundle, it's > equivalent to a single `<script type="module" src="...">` pointing > towards the original entry point, excluding network requests.* But in > either case, you aren't listing 50 scripts, you're only listing the > entry module and importing child modules within parent modules. Rollup > and Webpack do mostly the same thing browsers do when it comes to > resolving dependencies, just they generate a bundle afterwards where > browsers execute code afterwards. Also, it's worth noting that the gap > between a single large request and multiple smaller requests has > shrunk a lot since HTTP/2 came along, since it's binary, it allows > requests and response data to be interleaved, it better leverages the > underlying TCP protocol format, and it allows servers to send data > pre-emptively without the client requesting it first. (Web sockets are > built on this functionality.) It's still better to bundle in general, > but it's less of a problem not to. > > This is *not* the case for `<script type="module">` elements - those > operate more like inline scripts that happen to have the ability to > `import`. > > Oh, and yes, I've loaded upwards of 50-100 modules in development. 20 > modules is *easy* to achieve in single-page apps. > > * This is, of course, not the case if you are using pure ES6 and you > aren't using any plugins to, say, run the original source through > Babel for React + JSX or something. > > ----- > > Isiah Meadows > contact at isiahmeadows.com > www.isiahmeadows.com > On Sat, May 25, 2019 at 2:12 AM kai zhu <kaizhu256 at gmail.com> wrote: > > > > Asynchronous loading differs only in > > that it takes more code to express the same logic and you have to take > > into account concurrent requests (and you need to cache the request, > > not the result), but it's otherwise the same from 1km away. > > > > > > so async-loading 50 ```<script type="module">``` tags > > has equivalent side-effect > > as sync-loading single webpack-rollup (of same 50 modules)? > > > > i have nagging suspicion of doubts. has anyone tried native > async-loading large numbers (>10) of > > ```<script type="module">``` tags, and verify it resolves identically to > using a single webpack-rollup? > > > > again, i'm not that knowledgeable on es-modules, so above question may > be trivially true, and i'm just not aware. > > > > -kai > > > > On 24 May 2019, at 23:41, Isiah Meadows <isiahmeadows at gmail.com> wrote: > > > > There's two main reasons why it scales: > > > > 1. Modules are strongly encapsulated while minimizing global pollution. > > 2. The resolution algorithm applies the same logic no matter how many > > modules are loaded. > > > > It's much easier for it to scale when you write the code unaware of > > how many modules you might be loading and unaware of how deep their > > dependency graph is. Fewer assumptions here is key. It's an > > engineering problem, but a relatively simple one. > > > > If you want a short example of how sync module resolution works, you > > can take a look at this little utility I wrote: > > https://github.com/isiahmeadows/simple-require-loader. That doesn't > > asynchronously resolve modules, but it should help explain the process > > from a synchronous standpoint. Asynchronous loading differs only in > > that it takes more code to express the same logic and you have to take > > into account concurrent requests (and you need to cache the request, > > not the result), but it's otherwise the same from 1km away. > > > > ----- > > > > Isiah Meadows > > contact at isiahmeadows.com > > www.isiahmeadows.com > > > > On Thu, May 23, 2019 at 10:49 AM kai zhu <kaizhu256 at gmail.com> wrote: > > > > > > actually, i admit i don't know what i'm talking about. just generally > confused (through ignorance) on how large-scale es-module dependencies > resolve when loaded/imported asynchronously. > > > > On Wed, May 22, 2019 at 10:42 PM Logan Smyth <loganfsmyth at gmail.com> > wrote: > > > > > > Can you elaborate on what loading state you need to keep track of? What > is the bottleneck that you run into? Also to be sure, when you say > async-load, do you mean `import()`? > > > > On Wed, May 22, 2019, 20:17 kai zhu <kaizhu256 at gmail.com> wrote: > > > > > > i don't use es-modules. > > but with amd/requirejs, I start having trouble with > module-initializations in nodejs/browser at ~5 async modules (that may or > may not have circular-references). 10 would be hard, and 20 would be near > inhuman for me. > > > > can we say its somewhat impractical for most applications to load more > than 50 async modules (with some of them having circular-references)? and > perhaps better design/spec module-loading mechanisms with this usability > concern in mind? > > > > p.s. its also impractical for me to async-load 5 or more modules without > using globalThis to keep track of each module's loading-state. > > _______________________________________________ > > es-discuss mailing list > > es-discuss at mozilla.org > > https://mail.mozilla.org/listinfo/es-discuss > > > > > > _______________________________________________ > > es-discuss mailing list > > es-discuss at mozilla.org > > https://mail.mozilla.org/listinfo/es-discuss > > > > > -------------- next part -------------- An HTML attachment was scrubbed... URL: <http://mail.mozilla.org/pipermail/es-discuss/attachments/20190531/5ea8d4c9/attachment.html>
how would i transition from development-mode (20 es-module files) -> production-mode (1 rollup file)?
Place all of the code to be exported in 1 file?
with some of them having circular-references
Not certain how that is possible when using import
within <script type="module">
?
how many async-modules can js-app practically load?
Again, how many have you tried to load? 100? 500? 1000? Either should be possible.
What specific issue are you actually to resolve? Naming identifiers within exported and imported modules (JavaScript code)?
> how would i transition from development-mode (20 es-module files) -> production-mode (1 rollup file)? Place all of the code to be exported in 1 file? > with some of them having circular-references Not certain how that is possible when using ```import``` within ```<script type="module">```? > how many async-modules can js-app practically load? Again, how many have you tried to load? 100? 500? 1000? Either should be possible. What specific issue are you actually to resolve? On Fri, May 31, 2019 at 5:40 PM kai zhu <kaizhu256 at gmail.com> wrote: > > Oh, and yes, I've loaded upwards of 50-100 modules in development. 20 > modules is *easy* to achieve in single-page apps. > > was that with some combination of babel/rollup/webpack or pure-es6? > if i want to develop a pure-es6 webapp (no babel), how would i transition > from development-mode (20 es-module files) -> production-mode (1 rollup > file)? > > > On Fri, May 31, 2019 at 10:47 AM Isiah Meadows <isiahmeadows at gmail.com> > wrote: > >> If it's bundled by Rollup or Webpack into a single bundle, it's >> equivalent to a single `<script type="module" src="...">` pointing >> towards the original entry point, excluding network requests.* But in >> either case, you aren't listing 50 scripts, you're only listing the >> entry module and importing child modules within parent modules. Rollup >> and Webpack do mostly the same thing browsers do when it comes to >> resolving dependencies, just they generate a bundle afterwards where >> browsers execute code afterwards. Also, it's worth noting that the gap >> between a single large request and multiple smaller requests has >> shrunk a lot since HTTP/2 came along, since it's binary, it allows >> requests and response data to be interleaved, it better leverages the >> underlying TCP protocol format, and it allows servers to send data >> pre-emptively without the client requesting it first. (Web sockets are >> built on this functionality.) It's still better to bundle in general, >> but it's less of a problem not to. >> >> This is *not* the case for `<script type="module">` elements - those >> operate more like inline scripts that happen to have the ability to >> `import`. >> >> Oh, and yes, I've loaded upwards of 50-100 modules in development. 20 >> modules is *easy* to achieve in single-page apps. >> >> * This is, of course, not the case if you are using pure ES6 and you >> aren't using any plugins to, say, run the original source through >> Babel for React + JSX or something. >> >> ----- >> >> Isiah Meadows >> contact at isiahmeadows.com >> www.isiahmeadows.com >> On Sat, May 25, 2019 at 2:12 AM kai zhu <kaizhu256 at gmail.com> wrote: >> > >> > Asynchronous loading differs only in >> > that it takes more code to express the same logic and you have to take >> > into account concurrent requests (and you need to cache the request, >> > not the result), but it's otherwise the same from 1km away. >> > >> > >> > so async-loading 50 ```<script type="module">``` tags >> > has equivalent side-effect >> > as sync-loading single webpack-rollup (of same 50 modules)? >> > >> > i have nagging suspicion of doubts. has anyone tried native >> async-loading large numbers (>10) of >> > ```<script type="module">``` tags, and verify it resolves identically >> to using a single webpack-rollup? >> > >> > again, i'm not that knowledgeable on es-modules, so above question may >> be trivially true, and i'm just not aware. >> > >> > -kai >> > >> > On 24 May 2019, at 23:41, Isiah Meadows <isiahmeadows at gmail.com> wrote: >> > >> > There's two main reasons why it scales: >> > >> > 1. Modules are strongly encapsulated while minimizing global pollution. >> > 2. The resolution algorithm applies the same logic no matter how many >> > modules are loaded. >> > >> > It's much easier for it to scale when you write the code unaware of >> > how many modules you might be loading and unaware of how deep their >> > dependency graph is. Fewer assumptions here is key. It's an >> > engineering problem, but a relatively simple one. >> > >> > If you want a short example of how sync module resolution works, you >> > can take a look at this little utility I wrote: >> > https://github.com/isiahmeadows/simple-require-loader. That doesn't >> > asynchronously resolve modules, but it should help explain the process >> > from a synchronous standpoint. Asynchronous loading differs only in >> > that it takes more code to express the same logic and you have to take >> > into account concurrent requests (and you need to cache the request, >> > not the result), but it's otherwise the same from 1km away. >> > >> > ----- >> > >> > Isiah Meadows >> > contact at isiahmeadows.com >> > www.isiahmeadows.com >> > >> > On Thu, May 23, 2019 at 10:49 AM kai zhu <kaizhu256 at gmail.com> wrote: >> > >> > >> > actually, i admit i don't know what i'm talking about. just generally >> confused (through ignorance) on how large-scale es-module dependencies >> resolve when loaded/imported asynchronously. >> > >> > On Wed, May 22, 2019 at 10:42 PM Logan Smyth <loganfsmyth at gmail.com> >> wrote: >> > >> > >> > Can you elaborate on what loading state you need to keep track of? What >> is the bottleneck that you run into? Also to be sure, when you say >> async-load, do you mean `import()`? >> > >> > On Wed, May 22, 2019, 20:17 kai zhu <kaizhu256 at gmail.com> wrote: >> > >> > >> > i don't use es-modules. >> > but with amd/requirejs, I start having trouble with >> module-initializations in nodejs/browser at ~5 async modules (that may or >> may not have circular-references). 10 would be hard, and 20 would be near >> inhuman for me. >> > >> > can we say its somewhat impractical for most applications to load more >> than 50 async modules (with some of them having circular-references)? and >> perhaps better design/spec module-loading mechanisms with this usability >> concern in mind? >> > >> > p.s. its also impractical for me to async-load 5 or more modules >> without using globalThis to keep track of each module's loading-state. >> > _______________________________________________ >> > es-discuss mailing list >> > es-discuss at mozilla.org >> > https://mail.mozilla.org/listinfo/es-discuss >> > >> > >> > _______________________________________________ >> > es-discuss mailing list >> > es-discuss at mozilla.org >> > https://mail.mozilla.org/listinfo/es-discuss >> > >> > >> > _______________________________________________ > es-discuss mailing list > es-discuss at mozilla.org > https://mail.mozilla.org/listinfo/es-discuss > -------------- next part -------------- An HTML attachment was scrubbed... URL: <http://mail.mozilla.org/pipermail/es-discuss/attachments/20190601/8de8dec1/attachment-0001.html>
Place all of the code to be exported in 1 file?
that obviously will not work, because of module-scope collision. can anyone share their experience on deploying a [babel-free] pure-es6 application with 20 es-modules rolled-up into one [production] bundle? is it even possible?
> Place all of the code to be exported in 1 file? that obviously will not work, because of module-scope collision. can anyone share their experience on deploying a [babel-free] pure-es6 application with 20 es-modules rolled-up into one [production] bundle? is it even possible? On Fri, May 31, 2019 at 7:55 PM guest271314 <guest271314 at gmail.com> wrote: > > how would i transition from development-mode (20 es-module files) -> > production-mode (1 rollup file)? > > Place all of the code to be exported in 1 file? > > > with some of them having circular-references > > Not certain how that is possible when using ```import``` within ```<script > type="module">```? > > > how many async-modules can js-app practically load? > > Again, how many have you tried to load? 100? 500? 1000? Either should be > possible. > > What specific issue are you actually to resolve? > > On Fri, May 31, 2019 at 5:40 PM kai zhu <kaizhu256 at gmail.com> wrote: > >> > Oh, and yes, I've loaded upwards of 50-100 modules in development. 20 >> modules is *easy* to achieve in single-page apps. >> >> was that with some combination of babel/rollup/webpack or pure-es6? >> if i want to develop a pure-es6 webapp (no babel), how would i transition >> from development-mode (20 es-module files) -> production-mode (1 rollup >> file)? >> >> >> On Fri, May 31, 2019 at 10:47 AM Isiah Meadows <isiahmeadows at gmail.com> >> wrote: >> >>> If it's bundled by Rollup or Webpack into a single bundle, it's >>> equivalent to a single `<script type="module" src="...">` pointing >>> towards the original entry point, excluding network requests.* But in >>> either case, you aren't listing 50 scripts, you're only listing the >>> entry module and importing child modules within parent modules. Rollup >>> and Webpack do mostly the same thing browsers do when it comes to >>> resolving dependencies, just they generate a bundle afterwards where >>> browsers execute code afterwards. Also, it's worth noting that the gap >>> between a single large request and multiple smaller requests has >>> shrunk a lot since HTTP/2 came along, since it's binary, it allows >>> requests and response data to be interleaved, it better leverages the >>> underlying TCP protocol format, and it allows servers to send data >>> pre-emptively without the client requesting it first. (Web sockets are >>> built on this functionality.) It's still better to bundle in general, >>> but it's less of a problem not to. >>> >>> This is *not* the case for `<script type="module">` elements - those >>> operate more like inline scripts that happen to have the ability to >>> `import`. >>> >>> Oh, and yes, I've loaded upwards of 50-100 modules in development. 20 >>> modules is *easy* to achieve in single-page apps. >>> >>> * This is, of course, not the case if you are using pure ES6 and you >>> aren't using any plugins to, say, run the original source through >>> Babel for React + JSX or something. >>> >>> ----- >>> >>> Isiah Meadows >>> contact at isiahmeadows.com >>> www.isiahmeadows.com >>> On Sat, May 25, 2019 at 2:12 AM kai zhu <kaizhu256 at gmail.com> wrote: >>> > >>> > Asynchronous loading differs only in >>> > that it takes more code to express the same logic and you have to take >>> > into account concurrent requests (and you need to cache the request, >>> > not the result), but it's otherwise the same from 1km away. >>> > >>> > >>> > so async-loading 50 ```<script type="module">``` tags >>> > has equivalent side-effect >>> > as sync-loading single webpack-rollup (of same 50 modules)? >>> > >>> > i have nagging suspicion of doubts. has anyone tried native >>> async-loading large numbers (>10) of >>> > ```<script type="module">``` tags, and verify it resolves identically >>> to using a single webpack-rollup? >>> > >>> > again, i'm not that knowledgeable on es-modules, so above question may >>> be trivially true, and i'm just not aware. >>> > >>> > -kai >>> > >>> > On 24 May 2019, at 23:41, Isiah Meadows <isiahmeadows at gmail.com> >>> wrote: >>> > >>> > There's two main reasons why it scales: >>> > >>> > 1. Modules are strongly encapsulated while minimizing global pollution. >>> > 2. The resolution algorithm applies the same logic no matter how many >>> > modules are loaded. >>> > >>> > It's much easier for it to scale when you write the code unaware of >>> > how many modules you might be loading and unaware of how deep their >>> > dependency graph is. Fewer assumptions here is key. It's an >>> > engineering problem, but a relatively simple one. >>> > >>> > If you want a short example of how sync module resolution works, you >>> > can take a look at this little utility I wrote: >>> > https://github.com/isiahmeadows/simple-require-loader. That doesn't >>> > asynchronously resolve modules, but it should help explain the process >>> > from a synchronous standpoint. Asynchronous loading differs only in >>> > that it takes more code to express the same logic and you have to take >>> > into account concurrent requests (and you need to cache the request, >>> > not the result), but it's otherwise the same from 1km away. >>> > >>> > ----- >>> > >>> > Isiah Meadows >>> > contact at isiahmeadows.com >>> > www.isiahmeadows.com >>> > >>> > On Thu, May 23, 2019 at 10:49 AM kai zhu <kaizhu256 at gmail.com> wrote: >>> > >>> > >>> > actually, i admit i don't know what i'm talking about. just generally >>> confused (through ignorance) on how large-scale es-module dependencies >>> resolve when loaded/imported asynchronously. >>> > >>> > On Wed, May 22, 2019 at 10:42 PM Logan Smyth <loganfsmyth at gmail.com> >>> wrote: >>> > >>> > >>> > Can you elaborate on what loading state you need to keep track of? >>> What is the bottleneck that you run into? Also to be sure, when you say >>> async-load, do you mean `import()`? >>> > >>> > On Wed, May 22, 2019, 20:17 kai zhu <kaizhu256 at gmail.com> wrote: >>> > >>> > >>> > i don't use es-modules. >>> > but with amd/requirejs, I start having trouble with >>> module-initializations in nodejs/browser at ~5 async modules (that may or >>> may not have circular-references). 10 would be hard, and 20 would be near >>> inhuman for me. >>> > >>> > can we say its somewhat impractical for most applications to load more >>> than 50 async modules (with some of them having circular-references)? and >>> perhaps better design/spec module-loading mechanisms with this usability >>> concern in mind? >>> > >>> > p.s. its also impractical for me to async-load 5 or more modules >>> without using globalThis to keep track of each module's loading-state. >>> > _______________________________________________ >>> > es-discuss mailing list >>> > es-discuss at mozilla.org >>> > https://mail.mozilla.org/listinfo/es-discuss >>> > >>> > >>> > _______________________________________________ >>> > es-discuss mailing list >>> > es-discuss at mozilla.org >>> > https://mail.mozilla.org/listinfo/es-discuss >>> > >>> > >>> >> _______________________________________________ >> es-discuss mailing list >> es-discuss at mozilla.org >> https://mail.mozilla.org/listinfo/es-discuss >> > -------------- next part -------------- An HTML attachment was scrubbed... URL: <http://mail.mozilla.org/pipermail/es-discuss/attachments/20190531/6668dc6a/attachment.html>
Where identifiers have unique names there should not be any collisions. What is the actual code tried?
Where identifiers have unique names there should not be any collisions. What is the actual code tried? On Sat, Jun 1, 2019 at 1:51 AM kai zhu <kaizhu256 at gmail.com> wrote: > > Place all of the code to be exported in 1 file? > > that obviously will not work, because of module-scope collision. can > anyone share their experience on deploying a [babel-free] pure-es6 > application with 20 es-modules rolled-up into one [production] bundle? is > it even possible? > > > On Fri, May 31, 2019 at 7:55 PM guest271314 <guest271314 at gmail.com> wrote: > >> > how would i transition from development-mode (20 es-module files) -> >> production-mode (1 rollup file)? >> >> Place all of the code to be exported in 1 file? >> >> > with some of them having circular-references >> >> Not certain how that is possible when using ```import``` within >> ```<script type="module">```? >> >> > how many async-modules can js-app practically load? >> >> Again, how many have you tried to load? 100? 500? 1000? Either should be >> possible. >> >> What specific issue are you actually to resolve? >> >> On Fri, May 31, 2019 at 5:40 PM kai zhu <kaizhu256 at gmail.com> wrote: >> >>> > Oh, and yes, I've loaded upwards of 50-100 modules in development. 20 >>> modules is *easy* to achieve in single-page apps. >>> >>> was that with some combination of babel/rollup/webpack or pure-es6? >>> if i want to develop a pure-es6 webapp (no babel), how would i >>> transition from development-mode (20 es-module files) -> production-mode (1 >>> rollup file)? >>> >>> >>> On Fri, May 31, 2019 at 10:47 AM Isiah Meadows <isiahmeadows at gmail.com> >>> wrote: >>> >>>> If it's bundled by Rollup or Webpack into a single bundle, it's >>>> equivalent to a single `<script type="module" src="...">` pointing >>>> towards the original entry point, excluding network requests.* But in >>>> either case, you aren't listing 50 scripts, you're only listing the >>>> entry module and importing child modules within parent modules. Rollup >>>> and Webpack do mostly the same thing browsers do when it comes to >>>> resolving dependencies, just they generate a bundle afterwards where >>>> browsers execute code afterwards. Also, it's worth noting that the gap >>>> between a single large request and multiple smaller requests has >>>> shrunk a lot since HTTP/2 came along, since it's binary, it allows >>>> requests and response data to be interleaved, it better leverages the >>>> underlying TCP protocol format, and it allows servers to send data >>>> pre-emptively without the client requesting it first. (Web sockets are >>>> built on this functionality.) It's still better to bundle in general, >>>> but it's less of a problem not to. >>>> >>>> This is *not* the case for `<script type="module">` elements - those >>>> operate more like inline scripts that happen to have the ability to >>>> `import`. >>>> >>>> Oh, and yes, I've loaded upwards of 50-100 modules in development. 20 >>>> modules is *easy* to achieve in single-page apps. >>>> >>>> * This is, of course, not the case if you are using pure ES6 and you >>>> aren't using any plugins to, say, run the original source through >>>> Babel for React + JSX or something. >>>> >>>> ----- >>>> >>>> Isiah Meadows >>>> contact at isiahmeadows.com >>>> www.isiahmeadows.com >>>> On Sat, May 25, 2019 at 2:12 AM kai zhu <kaizhu256 at gmail.com> wrote: >>>> > >>>> > Asynchronous loading differs only in >>>> > that it takes more code to express the same logic and you have to take >>>> > into account concurrent requests (and you need to cache the request, >>>> > not the result), but it's otherwise the same from 1km away. >>>> > >>>> > >>>> > so async-loading 50 ```<script type="module">``` tags >>>> > has equivalent side-effect >>>> > as sync-loading single webpack-rollup (of same 50 modules)? >>>> > >>>> > i have nagging suspicion of doubts. has anyone tried native >>>> async-loading large numbers (>10) of >>>> > ```<script type="module">``` tags, and verify it resolves identically >>>> to using a single webpack-rollup? >>>> > >>>> > again, i'm not that knowledgeable on es-modules, so above question >>>> may be trivially true, and i'm just not aware. >>>> > >>>> > -kai >>>> > >>>> > On 24 May 2019, at 23:41, Isiah Meadows <isiahmeadows at gmail.com> >>>> wrote: >>>> > >>>> > There's two main reasons why it scales: >>>> > >>>> > 1. Modules are strongly encapsulated while minimizing global >>>> pollution. >>>> > 2. The resolution algorithm applies the same logic no matter how many >>>> > modules are loaded. >>>> > >>>> > It's much easier for it to scale when you write the code unaware of >>>> > how many modules you might be loading and unaware of how deep their >>>> > dependency graph is. Fewer assumptions here is key. It's an >>>> > engineering problem, but a relatively simple one. >>>> > >>>> > If you want a short example of how sync module resolution works, you >>>> > can take a look at this little utility I wrote: >>>> > https://github.com/isiahmeadows/simple-require-loader. That doesn't >>>> > asynchronously resolve modules, but it should help explain the process >>>> > from a synchronous standpoint. Asynchronous loading differs only in >>>> > that it takes more code to express the same logic and you have to take >>>> > into account concurrent requests (and you need to cache the request, >>>> > not the result), but it's otherwise the same from 1km away. >>>> > >>>> > ----- >>>> > >>>> > Isiah Meadows >>>> > contact at isiahmeadows.com >>>> > www.isiahmeadows.com >>>> > >>>> > On Thu, May 23, 2019 at 10:49 AM kai zhu <kaizhu256 at gmail.com> wrote: >>>> > >>>> > >>>> > actually, i admit i don't know what i'm talking about. just >>>> generally confused (through ignorance) on how large-scale es-module >>>> dependencies resolve when loaded/imported asynchronously. >>>> > >>>> > On Wed, May 22, 2019 at 10:42 PM Logan Smyth <loganfsmyth at gmail.com> >>>> wrote: >>>> > >>>> > >>>> > Can you elaborate on what loading state you need to keep track of? >>>> What is the bottleneck that you run into? Also to be sure, when you say >>>> async-load, do you mean `import()`? >>>> > >>>> > On Wed, May 22, 2019, 20:17 kai zhu <kaizhu256 at gmail.com> wrote: >>>> > >>>> > >>>> > i don't use es-modules. >>>> > but with amd/requirejs, I start having trouble with >>>> module-initializations in nodejs/browser at ~5 async modules (that may or >>>> may not have circular-references). 10 would be hard, and 20 would be near >>>> inhuman for me. >>>> > >>>> > can we say its somewhat impractical for most applications to load >>>> more than 50 async modules (with some of them having circular-references)? >>>> and perhaps better design/spec module-loading mechanisms with this >>>> usability concern in mind? >>>> > >>>> > p.s. its also impractical for me to async-load 5 or more modules >>>> without using globalThis to keep track of each module's loading-state. >>>> > _______________________________________________ >>>> > es-discuss mailing list >>>> > es-discuss at mozilla.org >>>> > https://mail.mozilla.org/listinfo/es-discuss >>>> > >>>> > >>>> > _______________________________________________ >>>> > es-discuss mailing list >>>> > es-discuss at mozilla.org >>>> > https://mail.mozilla.org/listinfo/es-discuss >>>> > >>>> > >>>> >>> _______________________________________________ >>> es-discuss mailing list >>> es-discuss at mozilla.org >>> https://mail.mozilla.org/listinfo/es-discuss >>> >> -------------- next part -------------- An HTML attachment was scrubbed... URL: <http://mail.mozilla.org/pipermail/es-discuss/attachments/20190601/4ab816ca/attachment-0001.html>
Re: how many async-modules can js-app practically load?
An example of exporting and importing loading 1000 properties in a single module, where duplicate property names are checked for. Since JavaScript plain objects cannot have duplicate property names there should not be any "collisions"; the code can check for and modify the object to be exported, though the last duplicate property name will be exported without any errors thrown unless the code is composed to throw such an error.
(async() => {
const oneThousandModules = encodeURIComponent(`// substitute rand for a Set of module names to be exported
// e.g. const moduleNames = ['moduleA', 'moduleB', ...moduleZ]
const modules = {};
// set a function to be exported
modules.fn = function() {return 'a function'};
// do stuff
modules.image = ${await (await fetch('https://gist.githubusercontent.com/guest271314/6042f6e438f1e4bfa65b3dcba8ef1309/raw/4df4817ccfafa0a142934630cd9818b1190f7992/imageData.json')).json()};
// function to set (1000) 'random' module names to be exported
const rand = (seed = 'abcdefghijklmnopqrstuvwxyz0123456789', n = 5, len = seed.length) =>
'.'.repeat(n).replace(/./g, _ => seed[~~(Math.random() * len)]);
// use Set for unique module identifiers
const moduleNames = [...Array(1000)].map(_ => rand());
const moduleIdentifiers = new Set(moduleNames);
// below line will cause ReferenceError to be thrown
moduleNames.push(moduleNames[0]);
try {
if (moduleIdentifiers.size !== moduleNames.length) {
// check for duplicates
const duplicates = moduleNames.filter((moduleName, index) => moduleNames.indexOf(moduleName) !== index);
// notification of duplicate module names
throw new ReferenceError('module names ' + JSON.stringify(duplicates) + ' are not unique');
// perform the designated task if duplicate module names are found here
}
} catch (e) {
console.error(e);
console.trace();
}
// get, set (sync or async) exported module here
Object.assign(modules, ...[...moduleIdentifiers].map((id, value) => ({[id]:value})));
// since JavaScript plain object cannot have duplicate property names
// modules object will still be exported without duplicate property names
// without collisions
export {modules}`);
const scriptText = `import {modules} from "data:application/javascript,${oneThousandModules};";`;
const script = document.createElement("script");
script.type = "module";
script.textContent = scriptText;
script.textContent += "\nconsole.log(modules); const imageModule = () => { if (modules['image']) { console.log('image module loaded'); const canvas = document.createElement('canvas'); canvas.width = 200; canvas.height = 200; const ctx = canvas.getContext('2d'); document.body.appendChild(canvas); ctx.putImageData(new ImageData(new Uint8ClampedArray(modules.image),200,200),0,0); } else { console.log('image module not loaded'); } }; imageModule(); for (const key in modules) {if (typeof modules[key] === 'function') {console.log(modules[key]());}}";
document.head.appendChild(script);
})();
Re: how many async-modules can js-app practically load? An example of exporting and importing loading 1000 properties in a single module, where duplicate property names are checked for. Since JavaScript plain objects cannot have duplicate property names there should not be any "collisions"; the code can check for and modify the object to be exported, though the last duplicate property name will be exported without any errors thrown unless the code is composed to throw such an error. ``` (async() => { const oneThousandModules = encodeURIComponent( // substitute rand for a Set of module names to be exported // e.g. const moduleNames = ['moduleA', 'moduleB', ...moduleZ] ` const modules = {}; // set a function to be exported modules.fn = function() {return 'a function'}; // function to set (1000) 'random' module names to be exported const rand = (seed = 'abcdefghijklmnopqrstuvwxyz0123456789', n = 5, len = seed.length) => '.'.repeat(n).replace(/./g, _ => seed[~~(Math.random() * len)]); // use Set for unique module identifiers const moduleNames = [...Array(1000)].map(_ => rand()); const moduleIdentifiers = new Set(moduleNames); // below line will cause ReferenceError to be thrown moduleNames.push(moduleNames[0]); try { if (moduleIdentifiers.size !== moduleNames.length) { // check for duplicates const duplicates = moduleNames.filter((moduleName, index) => moduleNames.indexOf(moduleName) !== index); // notification of duplicate module names throw new ReferenceError('module names ' + JSON.stringify(duplicates) + ' are not unique'); // perform the designated task if duplicate module names are found here } } catch (e) { console.error(e); console.trace(); } // get, set (sync or async) exported module here Object.assign(modules, ...[...moduleIdentifiers].map((id, value) => ({[id]:value}))); // since JavaScript plain object cannot have duplicate property names // modules object will still be exported without duplicate property names // without collisions export {modules} `); const scriptText = `import {modules} from "data:application/javascript,${oneThousandModules};${encodeURIComponent('console.log(modules);for (const key in modules) {if (typeof modules[key] === \'function\') {console.log(modules[key]());}}')}"`; const script = document.createElement("script"); script.type = "module"; script.textContent = scriptText; document.head.appendChild(script); })(); ``` plnkr https://plnkr.co/edit/CgEhBY?p=preview On Sat, Jun 1, 2019 at 1:51 AM kai zhu <kaizhu256 at gmail.com> wrote: > > Place all of the code to be exported in 1 file? > > that obviously will not work, because of module-scope collision. can > anyone share their experience on deploying a [babel-free] pure-es6 > application with 20 es-modules rolled-up into one [production] bundle? is > it even possible? > > > On Fri, May 31, 2019 at 7:55 PM guest271314 <guest271314 at gmail.com> wrote: > >> > how would i transition from development-mode (20 es-module files) -> >> production-mode (1 rollup file)? >> >> Place all of the code to be exported in 1 file? >> >> > with some of them having circular-references >> >> Not certain how that is possible when using ```import``` within >> ```<script type="module">```? >> >> > how many async-modules can js-app practically load? >> >> Again, how many have you tried to load? 100? 500? 1000? Either should be >> possible. >> >> What specific issue are you actually to resolve? >> >> On Fri, May 31, 2019 at 5:40 PM kai zhu <kaizhu256 at gmail.com> wrote: >> >>> > Oh, and yes, I've loaded upwards of 50-100 modules in development. 20 >>> modules is *easy* to achieve in single-page apps. >>> >>> was that with some combination of babel/rollup/webpack or pure-es6? >>> if i want to develop a pure-es6 webapp (no babel), how would i >>> transition from development-mode (20 es-module files) -> production-mode (1 >>> rollup file)? >>> >>> >>> On Fri, May 31, 2019 at 10:47 AM Isiah Meadows <isiahmeadows at gmail.com> >>> wrote: >>> >>>> If it's bundled by Rollup or Webpack into a single bundle, it's >>>> equivalent to a single `<script type="module" src="...">` pointing >>>> towards the original entry point, excluding network requests.* But in >>>> either case, you aren't listing 50 scripts, you're only listing the >>>> entry module and importing child modules within parent modules. Rollup >>>> and Webpack do mostly the same thing browsers do when it comes to >>>> resolving dependencies, just they generate a bundle afterwards where >>>> browsers execute code afterwards. Also, it's worth noting that the gap >>>> between a single large request and multiple smaller requests has >>>> shrunk a lot since HTTP/2 came along, since it's binary, it allows >>>> requests and response data to be interleaved, it better leverages the >>>> underlying TCP protocol format, and it allows servers to send data >>>> pre-emptively without the client requesting it first. (Web sockets are >>>> built on this functionality.) It's still better to bundle in general, >>>> but it's less of a problem not to. >>>> >>>> This is *not* the case for `<script type="module">` elements - those >>>> operate more like inline scripts that happen to have the ability to >>>> `import`. >>>> >>>> Oh, and yes, I've loaded upwards of 50-100 modules in development. 20 >>>> modules is *easy* to achieve in single-page apps. >>>> >>>> * This is, of course, not the case if you are using pure ES6 and you >>>> aren't using any plugins to, say, run the original source through >>>> Babel for React + JSX or something. >>>> >>>> ----- >>>> >>>> Isiah Meadows >>>> contact at isiahmeadows.com >>>> www.isiahmeadows.com >>>> On Sat, May 25, 2019 at 2:12 AM kai zhu <kaizhu256 at gmail.com> wrote: >>>> > >>>> > Asynchronous loading differs only in >>>> > that it takes more code to express the same logic and you have to take >>>> > into account concurrent requests (and you need to cache the request, >>>> > not the result), but it's otherwise the same from 1km away. >>>> > >>>> > >>>> > so async-loading 50 ```<script type="module">``` tags >>>> > has equivalent side-effect >>>> > as sync-loading single webpack-rollup (of same 50 modules)? >>>> > >>>> > i have nagging suspicion of doubts. has anyone tried native >>>> async-loading large numbers (>10) of >>>> > ```<script type="module">``` tags, and verify it resolves identically >>>> to using a single webpack-rollup? >>>> > >>>> > again, i'm not that knowledgeable on es-modules, so above question >>>> may be trivially true, and i'm just not aware. >>>> > >>>> > -kai >>>> > >>>> > On 24 May 2019, at 23:41, Isiah Meadows <isiahmeadows at gmail.com> >>>> wrote: >>>> > >>>> > There's two main reasons why it scales: >>>> > >>>> > 1. Modules are strongly encapsulated while minimizing global >>>> pollution. >>>> > 2. The resolution algorithm applies the same logic no matter how many >>>> > modules are loaded. >>>> > >>>> > It's much easier for it to scale when you write the code unaware of >>>> > how many modules you might be loading and unaware of how deep their >>>> > dependency graph is. Fewer assumptions here is key. It's an >>>> > engineering problem, but a relatively simple one. >>>> > >>>> > If you want a short example of how sync module resolution works, you >>>> > can take a look at this little utility I wrote: >>>> > https://github.com/isiahmeadows/simple-require-loader. That doesn't >>>> > asynchronously resolve modules, but it should help explain the process >>>> > from a synchronous standpoint. Asynchronous loading differs only in >>>> > that it takes more code to express the same logic and you have to take >>>> > into account concurrent requests (and you need to cache the request, >>>> > not the result), but it's otherwise the same from 1km away. >>>> > >>>> > ----- >>>> > >>>> > Isiah Meadows >>>> > contact at isiahmeadows.com >>>> > www.isiahmeadows.com >>>> > >>>> > On Thu, May 23, 2019 at 10:49 AM kai zhu <kaizhu256 at gmail.com> wrote: >>>> > >>>> > >>>> > actually, i admit i don't know what i'm talking about. just >>>> generally confused (through ignorance) on how large-scale es-module >>>> dependencies resolve when loaded/imported asynchronously. >>>> > >>>> > On Wed, May 22, 2019 at 10:42 PM Logan Smyth <loganfsmyth at gmail.com> >>>> wrote: >>>> > >>>> > >>>> > Can you elaborate on what loading state you need to keep track of? >>>> What is the bottleneck that you run into? Also to be sure, when you say >>>> async-load, do you mean `import()`? >>>> > >>>> > On Wed, May 22, 2019, 20:17 kai zhu <kaizhu256 at gmail.com> wrote: >>>> > >>>> > >>>> > i don't use es-modules. >>>> > but with amd/requirejs, I start having trouble with >>>> module-initializations in nodejs/browser at ~5 async modules (that may or >>>> may not have circular-references). 10 would be hard, and 20 would be near >>>> inhuman for me. >>>> > >>>> > can we say its somewhat impractical for most applications to load >>>> more than 50 async modules (with some of them having circular-references)? >>>> and perhaps better design/spec module-loading mechanisms with this >>>> usability concern in mind? >>>> > >>>> > p.s. its also impractical for me to async-load 5 or more modules >>>> without using globalThis to keep track of each module's loading-state. >>>> > _______________________________________________ >>>> > es-discuss mailing list >>>> > es-discuss at mozilla.org >>>> > https://mail.mozilla.org/listinfo/es-discuss >>>> > >>>> > >>>> > _______________________________________________ >>>> > es-discuss mailing list >>>> > es-discuss at mozilla.org >>>> > https://mail.mozilla.org/listinfo/es-discuss >>>> > >>>> > >>>> >>> _______________________________________________ >>> es-discuss mailing list >>> es-discuss at mozilla.org >>> https://mail.mozilla.org/listinfo/es-discuss >>> >> -------------- next part -------------- An HTML attachment was scrubbed... URL: <http://mail.mozilla.org/pipermail/es-discuss/attachments/20190601/c97d4ac9/attachment-0001.html>
your rollup solution is interesting, but i get an error when run in chrome (i changed to n=20 to prevent name-collision, but it still happens). don't completely understand how it works, but not sure of suitability for production-use, because of its dynamic <script> tag generation.
ReferenceError: module names ["yeqjqb02mvg3yze26rc5"] are not unique
at data:application/javascript,%0A%20%20%20%20%20%20const%20modules...
your rollup solution is interesting, but i get an error when run in chrome (i changed to n=20 to prevent name-collision, but it still happens). don't completely understand how it works, but not sure of suitability for production-use, because of its dynamic <script> tag generation. ```console ReferenceError: module names ["yeqjqb02mvg3yze26rc5"] are not unique at data:application/javascript,%0A%20%20%20%20%20%20const%20modules... ``` On Sat, Jun 1, 2019 at 2:33 PM guest271314 <guest271314 at gmail.com> wrote: > Re: how many async-modules can js-app practically load? > > An example of exporting and importing loading 1000 properties in a single > module, where duplicate property names are checked for. Since JavaScript > plain objects cannot have duplicate property names there should not be any > "collisions"; the code can check for and modify the object to be exported, > though the last duplicate property name will be exported without any errors > thrown unless the code is composed to throw such an error. > > ``` > (async() => { > const oneThousandModules = encodeURIComponent( > // substitute rand for a Set of module names to be exported > // e.g. const moduleNames = ['moduleA', 'moduleB', ...moduleZ] > ` > const modules = {}; > // set a function to be exported > modules.fn = function() {return 'a function'}; > // function to set (1000) 'random' module names to be exported > const rand = (seed = 'abcdefghijklmnopqrstuvwxyz0123456789', n = 5, > len = seed.length) => > '.'.repeat(n).replace(/./g, _ => seed[~~(Math.random() * len)]); > // use Set for unique module identifiers > const moduleNames = [...Array(1000)].map(_ => rand()); > const moduleIdentifiers = new Set(moduleNames); > // below line will cause ReferenceError to be thrown > moduleNames.push(moduleNames[0]); > try { > if (moduleIdentifiers.size !== moduleNames.length) { > // check for duplicates > const duplicates = moduleNames.filter((moduleName, index) => > moduleNames.indexOf(moduleName) !== index); > // notification of duplicate module names > throw new ReferenceError('module names ' + > JSON.stringify(duplicates) + ' are not unique'); > // perform the designated task if duplicate module names are > found here > } > } catch (e) { > console.error(e); > console.trace(); > } > // get, set (sync or async) exported module here > Object.assign(modules, ...[...moduleIdentifiers].map((id, value) > => ({[id]:value}))); > // since JavaScript plain object cannot have duplicate property > names > // modules object will still be exported without duplicate > property names > // without collisions > export {modules} > `); > const scriptText = `import {modules} from > "data:application/javascript,${oneThousandModules};${encodeURIComponent('console.log(modules);for > (const key in modules) {if (typeof modules[key] === \'function\') > {console.log(modules[key]());}}')}"`; > const script = document.createElement("script"); > script.type = "module"; > script.textContent = scriptText; > document.head.appendChild(script); > })(); > ``` > > plnkr https://plnkr.co/edit/CgEhBY?p=preview > > On Sat, Jun 1, 2019 at 1:51 AM kai zhu <kaizhu256 at gmail.com> wrote: > >> > Place all of the code to be exported in 1 file? >> >> that obviously will not work, because of module-scope collision. can >> anyone share their experience on deploying a [babel-free] pure-es6 >> application with 20 es-modules rolled-up into one [production] bundle? is >> it even possible? >> >> >> On Fri, May 31, 2019 at 7:55 PM guest271314 <guest271314 at gmail.com> >> wrote: >> >>> > how would i transition from development-mode (20 es-module files) -> >>> production-mode (1 rollup file)? >>> >>> Place all of the code to be exported in 1 file? >>> >>> > with some of them having circular-references >>> >>> Not certain how that is possible when using ```import``` within >>> ```<script type="module">```? >>> >>> > how many async-modules can js-app practically load? >>> >>> Again, how many have you tried to load? 100? 500? 1000? Either should be >>> possible. >>> >>> What specific issue are you actually to resolve? >>> >>> On Fri, May 31, 2019 at 5:40 PM kai zhu <kaizhu256 at gmail.com> wrote: >>> >>>> > Oh, and yes, I've loaded upwards of 50-100 modules in development. 20 >>>> modules is *easy* to achieve in single-page apps. >>>> >>>> was that with some combination of babel/rollup/webpack or pure-es6? >>>> if i want to develop a pure-es6 webapp (no babel), how would i >>>> transition from development-mode (20 es-module files) -> production-mode (1 >>>> rollup file)? >>>> >>>> >>>> On Fri, May 31, 2019 at 10:47 AM Isiah Meadows <isiahmeadows at gmail.com> >>>> wrote: >>>> >>>>> If it's bundled by Rollup or Webpack into a single bundle, it's >>>>> equivalent to a single `<script type="module" src="...">` pointing >>>>> towards the original entry point, excluding network requests.* But in >>>>> either case, you aren't listing 50 scripts, you're only listing the >>>>> entry module and importing child modules within parent modules. Rollup >>>>> and Webpack do mostly the same thing browsers do when it comes to >>>>> resolving dependencies, just they generate a bundle afterwards where >>>>> browsers execute code afterwards. Also, it's worth noting that the gap >>>>> between a single large request and multiple smaller requests has >>>>> shrunk a lot since HTTP/2 came along, since it's binary, it allows >>>>> requests and response data to be interleaved, it better leverages the >>>>> underlying TCP protocol format, and it allows servers to send data >>>>> pre-emptively without the client requesting it first. (Web sockets are >>>>> built on this functionality.) It's still better to bundle in general, >>>>> but it's less of a problem not to. >>>>> >>>>> This is *not* the case for `<script type="module">` elements - those >>>>> operate more like inline scripts that happen to have the ability to >>>>> `import`. >>>>> >>>>> Oh, and yes, I've loaded upwards of 50-100 modules in development. 20 >>>>> modules is *easy* to achieve in single-page apps. >>>>> >>>>> * This is, of course, not the case if you are using pure ES6 and you >>>>> aren't using any plugins to, say, run the original source through >>>>> Babel for React + JSX or something. >>>>> >>>>> ----- >>>>> >>>>> Isiah Meadows >>>>> contact at isiahmeadows.com >>>>> www.isiahmeadows.com >>>>> On Sat, May 25, 2019 at 2:12 AM kai zhu <kaizhu256 at gmail.com> wrote: >>>>> > >>>>> > Asynchronous loading differs only in >>>>> > that it takes more code to express the same logic and you have to >>>>> take >>>>> > into account concurrent requests (and you need to cache the request, >>>>> > not the result), but it's otherwise the same from 1km away. >>>>> > >>>>> > >>>>> > so async-loading 50 ```<script type="module">``` tags >>>>> > has equivalent side-effect >>>>> > as sync-loading single webpack-rollup (of same 50 modules)? >>>>> > >>>>> > i have nagging suspicion of doubts. has anyone tried native >>>>> async-loading large numbers (>10) of >>>>> > ```<script type="module">``` tags, and verify it resolves >>>>> identically to using a single webpack-rollup? >>>>> > >>>>> > again, i'm not that knowledgeable on es-modules, so above question >>>>> may be trivially true, and i'm just not aware. >>>>> > >>>>> > -kai >>>>> > >>>>> > On 24 May 2019, at 23:41, Isiah Meadows <isiahmeadows at gmail.com> >>>>> wrote: >>>>> > >>>>> > There's two main reasons why it scales: >>>>> > >>>>> > 1. Modules are strongly encapsulated while minimizing global >>>>> pollution. >>>>> > 2. The resolution algorithm applies the same logic no matter how many >>>>> > modules are loaded. >>>>> > >>>>> > It's much easier for it to scale when you write the code unaware of >>>>> > how many modules you might be loading and unaware of how deep their >>>>> > dependency graph is. Fewer assumptions here is key. It's an >>>>> > engineering problem, but a relatively simple one. >>>>> > >>>>> > If you want a short example of how sync module resolution works, you >>>>> > can take a look at this little utility I wrote: >>>>> > https://github.com/isiahmeadows/simple-require-loader. That doesn't >>>>> > asynchronously resolve modules, but it should help explain the >>>>> process >>>>> > from a synchronous standpoint. Asynchronous loading differs only in >>>>> > that it takes more code to express the same logic and you have to >>>>> take >>>>> > into account concurrent requests (and you need to cache the request, >>>>> > not the result), but it's otherwise the same from 1km away. >>>>> > >>>>> > ----- >>>>> > >>>>> > Isiah Meadows >>>>> > contact at isiahmeadows.com >>>>> > www.isiahmeadows.com >>>>> > >>>>> > On Thu, May 23, 2019 at 10:49 AM kai zhu <kaizhu256 at gmail.com> >>>>> wrote: >>>>> > >>>>> > >>>>> > actually, i admit i don't know what i'm talking about. just >>>>> generally confused (through ignorance) on how large-scale es-module >>>>> dependencies resolve when loaded/imported asynchronously. >>>>> > >>>>> > On Wed, May 22, 2019 at 10:42 PM Logan Smyth <loganfsmyth at gmail.com> >>>>> wrote: >>>>> > >>>>> > >>>>> > Can you elaborate on what loading state you need to keep track of? >>>>> What is the bottleneck that you run into? Also to be sure, when you say >>>>> async-load, do you mean `import()`? >>>>> > >>>>> > On Wed, May 22, 2019, 20:17 kai zhu <kaizhu256 at gmail.com> wrote: >>>>> > >>>>> > >>>>> > i don't use es-modules. >>>>> > but with amd/requirejs, I start having trouble with >>>>> module-initializations in nodejs/browser at ~5 async modules (that may or >>>>> may not have circular-references). 10 would be hard, and 20 would be near >>>>> inhuman for me. >>>>> > >>>>> > can we say its somewhat impractical for most applications to load >>>>> more than 50 async modules (with some of them having circular-references)? >>>>> and perhaps better design/spec module-loading mechanisms with this >>>>> usability concern in mind? >>>>> > >>>>> > p.s. its also impractical for me to async-load 5 or more modules >>>>> without using globalThis to keep track of each module's loading-state. >>>>> > _______________________________________________ >>>>> > es-discuss mailing list >>>>> > es-discuss at mozilla.org >>>>> > https://mail.mozilla.org/listinfo/es-discuss >>>>> > >>>>> > >>>>> > _______________________________________________ >>>>> > es-discuss mailing list >>>>> > es-discuss at mozilla.org >>>>> > https://mail.mozilla.org/listinfo/es-discuss >>>>> > >>>>> > >>>>> >>>> _______________________________________________ >>>> es-discuss mailing list >>>> es-discuss at mozilla.org >>>> https://mail.mozilla.org/listinfo/es-discuss >>>> >>> -------------- next part -------------- An HTML attachment was scrubbed... URL: <http://mail.mozilla.org/pipermail/es-discuss/attachments/20190601/3ba32afa/attachment-0001.html>
your rollup solution is interesting,
What is "rollup" referring to?
but i get an error when run in chrome (i changed to n=20 to prevent name-collision, but it still happens).
The duplicate ("collision") entry and try..catch
block is included in
the code to demonstrate given an array of module names to be exported and
imported as identifiers 1) duplicate entries at a list of module property identifiers (as strings) can be filtered; 2) if a plain object is exported duplicate identifiers ("collision") is not possible as a
JavaScript plain object does not have duplicate property names
("collision"); if there is an issue with identifiers in a module the cause
would not be the number of async-modules loaded ("how many"), but the
naming of the identifiers within the code, using or not using const
or let
.
As noted in comments within the code, you can set and check your own unique identifier names as strings that will be imported as module properties.
Still not sure what the actual issue is?
don't completely understand how it works,
Use an async
function to fetch data, check for the described
"collision" , create a data URL
(1 file) to be imported, optionally, append
addition code to be executed within the <script type="module">
.
but not sure of suitability for production-use, because of its dynamic <script> tag generation.
The export code ("module") is dynamic.
Each exported module entry (identifier) can be checked one at a time before proceeding, to ensure no "collision" at import.
What is the issue with dynamic <script>
tag generation?
There were no restrictions described at the OP and following messages other than other than
pure-es6 application with 20 es-modules rolled-up into one [production] bundle?
The example code uses only JavaScript implementation shipped with the browser without any external, third-party libraries.
If by "bundle" is meant exporting multiple resources (sync or async) in a single JavaScript plain object, without "collision", that is what the code achieves.
What standard or definition are you relying for the meaning of the term "production-use"? What procedure are you using to determine code "suitability" for "production-use"? How is that procedure related to "how many async-modules can js-app practically load?"?
There is more than one possible approach to achieve the presumptive requirement; that is still not clear to the exclusion of what is not the expected result besides loading N "async-modules" using "pure-es6"; "how many" (the gist of the code) would still be until memory runs out, if you were able to run the code at least 1000.
> your rollup solution is interesting, What is "rollup" referring to? > but i get an error when run in chrome (i changed to n=20 to prevent name-collision, but it still happens). The duplicate ("collision") entry an ```try..catch``` block is included in the code to demonstrate given an array of module names to be exported and imported as identifiers 1) duplicate entries can be filtered; 2) if a plain object is exported duplicate identifiers ("collision") is not possible as a JavaScript plain object does not have duplicate property names ("collision"); if there is an issue with identifiers in a module the cause would not be the number of async-modules loaded ("how many"), but the naming of the identifiers within the code, using or not using ```const``` or ```let```. Still not sure what the actual issue is? > don't completely understand how it works, Use an ```async``` function to fetch data, check for the described "collision" , create a ```data URI``` to be imported, optionally, append addition code to be executed within the ```<script type="module">```. > but not sure of suitability for production-use, because of its dynamic <script> tag generation. What is the issue with dynamic ```<script>``` tag generation? There is more than one possible approach to achieve the presumptive requirement, that is still not clear to the exclusion of what is not the expected result. There were no restrictions described at the OP and following messages other than other than > pure-es6 application with 20 es-modules rolled-up into one [production] bundle? The example code uses only JavaScript implementation shipped with the browser without any external, third-party libraries. What standard or definition are you relying for the meaning of the term "production-use"? What procedure are you using to determine if code is "production-use" "suitable"? How is that procedure related to "how many async-modules can js-app practically load?"? On Sat, Jun 1, 2019 at 9:42 PM kai zhu <kaizhu256 at gmail.com> wrote: > your rollup solution is interesting, but i get an error when run in chrome > (i changed to n=20 to prevent name-collision, but it still happens). don't > completely understand how it works, but not sure of suitability for > production-use, because of its dynamic <script> tag generation. > > ```console > ReferenceError: module names ["yeqjqb02mvg3yze26rc5"] are not unique > at data:application/javascript,%0A%20%20%20%20%20%20const%20modules... > ``` > > On Sat, Jun 1, 2019 at 2:33 PM guest271314 <guest271314 at gmail.com> wrote: > >> Re: how many async-modules can js-app practically load? >> >> An example of exporting and importing loading 1000 properties in a single >> module, where duplicate property names are checked for. Since JavaScript >> plain objects cannot have duplicate property names there should not be any >> "collisions"; the code can check for and modify the object to be exported, >> though the last duplicate property name will be exported without any errors >> thrown unless the code is composed to throw such an error. >> >> ``` >> (async() => { >> const oneThousandModules = encodeURIComponent( >> // substitute rand for a Set of module names to be exported >> // e.g. const moduleNames = ['moduleA', 'moduleB', ...moduleZ] >> ` >> const modules = {}; >> // set a function to be exported >> modules.fn = function() {return 'a function'}; >> // function to set (1000) 'random' module names to be exported >> const rand = (seed = 'abcdefghijklmnopqrstuvwxyz0123456789', n = 5, >> len = seed.length) => >> '.'.repeat(n).replace(/./g, _ => seed[~~(Math.random() * len)]); >> // use Set for unique module identifiers >> const moduleNames = [...Array(1000)].map(_ => rand()); >> const moduleIdentifiers = new Set(moduleNames); >> // below line will cause ReferenceError to be thrown >> moduleNames.push(moduleNames[0]); >> try { >> if (moduleIdentifiers.size !== moduleNames.length) { >> // check for duplicates >> const duplicates = moduleNames.filter((moduleName, index) => >> moduleNames.indexOf(moduleName) !== index); >> // notification of duplicate module names >> throw new ReferenceError('module names ' + >> JSON.stringify(duplicates) + ' are not unique'); >> // perform the designated task if duplicate module names are >> found here >> } >> } catch (e) { >> console.error(e); >> console.trace(); >> } >> // get, set (sync or async) exported module here >> Object.assign(modules, ...[...moduleIdentifiers].map((id, value) >> => ({[id]:value}))); >> // since JavaScript plain object cannot have duplicate property >> names >> // modules object will still be exported without duplicate >> property names >> // without collisions >> export {modules} >> `); >> const scriptText = `import {modules} from >> "data:application/javascript,${oneThousandModules};${encodeURIComponent('console.log(modules);for >> (const key in modules) {if (typeof modules[key] === \'function\') >> {console.log(modules[key]());}}')}"`; >> const script = document.createElement("script"); >> script.type = "module"; >> script.textContent = scriptText; >> document.head.appendChild(script); >> })(); >> ``` >> >> plnkr https://plnkr.co/edit/CgEhBY?p=preview >> >> On Sat, Jun 1, 2019 at 1:51 AM kai zhu <kaizhu256 at gmail.com> wrote: >> >>> > Place all of the code to be exported in 1 file? >>> >>> that obviously will not work, because of module-scope collision. can >>> anyone share their experience on deploying a [babel-free] pure-es6 >>> application with 20 es-modules rolled-up into one [production] bundle? is >>> it even possible? >>> >>> >>> On Fri, May 31, 2019 at 7:55 PM guest271314 <guest271314 at gmail.com> >>> wrote: >>> >>>> > how would i transition from development-mode (20 es-module files) -> >>>> production-mode (1 rollup file)? >>>> >>>> Place all of the code to be exported in 1 file? >>>> >>>> > with some of them having circular-references >>>> >>>> Not certain how that is possible when using ```import``` within >>>> ```<script type="module">```? >>>> >>>> > how many async-modules can js-app practically load? >>>> >>>> Again, how many have you tried to load? 100? 500? 1000? Either should >>>> be possible. >>>> >>>> What specific issue are you actually to resolve? >>>> >>>> On Fri, May 31, 2019 at 5:40 PM kai zhu <kaizhu256 at gmail.com> wrote: >>>> >>>>> > Oh, and yes, I've loaded upwards of 50-100 modules in development. 20 >>>>> modules is *easy* to achieve in single-page apps. >>>>> >>>>> was that with some combination of babel/rollup/webpack or pure-es6? >>>>> if i want to develop a pure-es6 webapp (no babel), how would i >>>>> transition from development-mode (20 es-module files) -> production-mode (1 >>>>> rollup file)? >>>>> >>>>> >>>>> On Fri, May 31, 2019 at 10:47 AM Isiah Meadows <isiahmeadows at gmail.com> >>>>> wrote: >>>>> >>>>>> If it's bundled by Rollup or Webpack into a single bundle, it's >>>>>> equivalent to a single `<script type="module" src="...">` pointing >>>>>> towards the original entry point, excluding network requests.* But in >>>>>> either case, you aren't listing 50 scripts, you're only listing the >>>>>> entry module and importing child modules within parent modules. Rollup >>>>>> and Webpack do mostly the same thing browsers do when it comes to >>>>>> resolving dependencies, just they generate a bundle afterwards where >>>>>> browsers execute code afterwards. Also, it's worth noting that the gap >>>>>> between a single large request and multiple smaller requests has >>>>>> shrunk a lot since HTTP/2 came along, since it's binary, it allows >>>>>> requests and response data to be interleaved, it better leverages the >>>>>> underlying TCP protocol format, and it allows servers to send data >>>>>> pre-emptively without the client requesting it first. (Web sockets are >>>>>> built on this functionality.) It's still better to bundle in general, >>>>>> but it's less of a problem not to. >>>>>> >>>>>> This is *not* the case for `<script type="module">` elements - those >>>>>> operate more like inline scripts that happen to have the ability to >>>>>> `import`. >>>>>> >>>>>> Oh, and yes, I've loaded upwards of 50-100 modules in development. 20 >>>>>> modules is *easy* to achieve in single-page apps. >>>>>> >>>>>> * This is, of course, not the case if you are using pure ES6 and you >>>>>> aren't using any plugins to, say, run the original source through >>>>>> Babel for React + JSX or something. >>>>>> >>>>>> ----- >>>>>> >>>>>> Isiah Meadows >>>>>> contact at isiahmeadows.com >>>>>> www.isiahmeadows.com >>>>>> On Sat, May 25, 2019 at 2:12 AM kai zhu <kaizhu256 at gmail.com> wrote: >>>>>> > >>>>>> > Asynchronous loading differs only in >>>>>> > that it takes more code to express the same logic and you have to >>>>>> take >>>>>> > into account concurrent requests (and you need to cache the request, >>>>>> > not the result), but it's otherwise the same from 1km away. >>>>>> > >>>>>> > >>>>>> > so async-loading 50 ```<script type="module">``` tags >>>>>> > has equivalent side-effect >>>>>> > as sync-loading single webpack-rollup (of same 50 modules)? >>>>>> > >>>>>> > i have nagging suspicion of doubts. has anyone tried native >>>>>> async-loading large numbers (>10) of >>>>>> > ```<script type="module">``` tags, and verify it resolves >>>>>> identically to using a single webpack-rollup? >>>>>> > >>>>>> > again, i'm not that knowledgeable on es-modules, so above question >>>>>> may be trivially true, and i'm just not aware. >>>>>> > >>>>>> > -kai >>>>>> > >>>>>> > On 24 May 2019, at 23:41, Isiah Meadows <isiahmeadows at gmail.com> >>>>>> wrote: >>>>>> > >>>>>> > There's two main reasons why it scales: >>>>>> > >>>>>> > 1. Modules are strongly encapsulated while minimizing global >>>>>> pollution. >>>>>> > 2. The resolution algorithm applies the same logic no matter how >>>>>> many >>>>>> > modules are loaded. >>>>>> > >>>>>> > It's much easier for it to scale when you write the code unaware of >>>>>> > how many modules you might be loading and unaware of how deep their >>>>>> > dependency graph is. Fewer assumptions here is key. It's an >>>>>> > engineering problem, but a relatively simple one. >>>>>> > >>>>>> > If you want a short example of how sync module resolution works, you >>>>>> > can take a look at this little utility I wrote: >>>>>> > https://github.com/isiahmeadows/simple-require-loader. That doesn't >>>>>> > asynchronously resolve modules, but it should help explain the >>>>>> process >>>>>> > from a synchronous standpoint. Asynchronous loading differs only in >>>>>> > that it takes more code to express the same logic and you have to >>>>>> take >>>>>> > into account concurrent requests (and you need to cache the request, >>>>>> > not the result), but it's otherwise the same from 1km away. >>>>>> > >>>>>> > ----- >>>>>> > >>>>>> > Isiah Meadows >>>>>> > contact at isiahmeadows.com >>>>>> > www.isiahmeadows.com >>>>>> > >>>>>> > On Thu, May 23, 2019 at 10:49 AM kai zhu <kaizhu256 at gmail.com> >>>>>> wrote: >>>>>> > >>>>>> > >>>>>> > actually, i admit i don't know what i'm talking about. just >>>>>> generally confused (through ignorance) on how large-scale es-module >>>>>> dependencies resolve when loaded/imported asynchronously. >>>>>> > >>>>>> > On Wed, May 22, 2019 at 10:42 PM Logan Smyth <loganfsmyth at gmail.com> >>>>>> wrote: >>>>>> > >>>>>> > >>>>>> > Can you elaborate on what loading state you need to keep track of? >>>>>> What is the bottleneck that you run into? Also to be sure, when you say >>>>>> async-load, do you mean `import()`? >>>>>> > >>>>>> > On Wed, May 22, 2019, 20:17 kai zhu <kaizhu256 at gmail.com> wrote: >>>>>> > >>>>>> > >>>>>> > i don't use es-modules. >>>>>> > but with amd/requirejs, I start having trouble with >>>>>> module-initializations in nodejs/browser at ~5 async modules (that may or >>>>>> may not have circular-references). 10 would be hard, and 20 would be near >>>>>> inhuman for me. >>>>>> > >>>>>> > can we say its somewhat impractical for most applications to load >>>>>> more than 50 async modules (with some of them having circular-references)? >>>>>> and perhaps better design/spec module-loading mechanisms with this >>>>>> usability concern in mind? >>>>>> > >>>>>> > p.s. its also impractical for me to async-load 5 or more modules >>>>>> without using globalThis to keep track of each module's loading-state. >>>>>> > _______________________________________________ >>>>>> > es-discuss mailing list >>>>>> > es-discuss at mozilla.org >>>>>> > https://mail.mozilla.org/listinfo/es-discuss >>>>>> > >>>>>> > >>>>>> > _______________________________________________ >>>>>> > es-discuss mailing list >>>>>> > es-discuss at mozilla.org >>>>>> > https://mail.mozilla.org/listinfo/es-discuss >>>>>> > >>>>>> > >>>>>> >>>>> _______________________________________________ >>>>> es-discuss mailing list >>>>> es-discuss at mozilla.org >>>>> https://mail.mozilla.org/listinfo/es-discuss >>>>> >>>> -------------- next part -------------- An HTML attachment was scrubbed... URL: <http://mail.mozilla.org/pipermail/es-discuss/attachments/20190601/1455967e/attachment-0001.html>
i played around with your code in jsfiddle [1], and understand it a little
more.
it doesn't actually import
1000+ es-modules inside the rollup-file.
it just creates one es-module that exports a dictionary
-- and assigns the dictionary 1000+ vanilla json-objects and functions.
// the "rollup-file" is a single es-module
// that exports 1000+ vanilla dictionary-entries
const modules = {};
// this is not a es-module, nor is it rolled-up (external fetch)
modules.image = <await fetch json from gist.github.com>
// this is not a [rolled-up] es-module
modules.fn = function () {...}
// these are not [rolled-up] es-modules
Object.assign(modules, <1000 json-entries>)
export {modules}
currently, as i'm aware, nobody uses native es-modules in production, because it cannot be rolled-up. in practice es-modules are [babel] transpiled down to es5-amd (or similar) for rollup-purposes.
if we're actually committed to native es-modules, then we either
- need to depend on embedders like loading-dev at chromium.org to create sophisticated cache-systems, or
- introduce new language-syntax to delimit es-modules for rollup-purposes, e.g.
// rollup.js with [hypothetical] # delimited es-modules
# module aa
import {bb} as bb;
export ...;
# module bb
export ...;
i'm generally skeptical of option 1, given how poorly npmjs.com has handled similar problems deduplicating children in node_modules/ directory.
[1] jsfiddle pseudo-module rollup jsfiddle.net/06twrLfd
i played around with your code in jsfiddle [1], and understand it a little more. it doesn't actually ```import``` 1000+ es-modules inside the rollup-file. it just creates one es-module that exports a dictionary -- and assigns the dictionary 1000+ vanilla json-objects and functions. ```js // the "rollup-file" is a single es-module // that exports 1000+ vanilla dictionary-entries const modules = {}; // this is not a es-module, nor is it rolled-up (external fetch) modules.image = <await fetch json from gist.github.com> // this is not a [rolled-up] es-module modules.fn = function () {...} // these are not [rolled-up] es-modules Object.assign(modules, <1000 json-entries>) export {modules} ``` currently, as i'm aware, nobody uses native es-modules in production, because it cannot be rolled-up. in practice es-modules are [babel] transpiled down to es5-amd (or similar) for rollup-purposes. if we're actually committed to native es-modules, then we either 1) need to depend on embedders like loading-dev at chromium.org to create sophisticated cache-systems, or 2) introduce new language-syntax to delimit es-modules for rollup-purposes, e.g. ```js // rollup.js with [hypothetical] # delimited es-modules # module aa import {bb} as bb; export ...; # module bb export ...; ``` i'm generally skeptical of option 1, given how poorly npmjs.com has handled similar problems deduplicating children in node_modules/ directory. [1] jsfiddle pseudo-module rollup https://jsfiddle.net/06twrLfd/ On Sat, Jun 1, 2019 at 5:30 PM guest271314 <guest271314 at gmail.com> wrote: > > your rollup solution is interesting, > > What is "rollup" referring to? > > > but i get an error when run in chrome (i changed to n=20 to prevent > name-collision, but it still happens). > > The duplicate ("collision") entry an ```try..catch``` block is included in > the code to demonstrate given an array of module names to be exported and > imported as identifiers 1) duplicate entries can be filtered; 2) if a plain > object is exported duplicate identifiers ("collision") is not possible as a > JavaScript plain object does not have duplicate property names > ("collision"); if there is an issue with identifiers in a module the cause > would not be the number of async-modules loaded ("how many"), but the > naming of the identifiers within the code, using or not using ```const``` > or ```let```. Still not sure what the actual issue is? > > > don't completely understand how it works, > > Use an ```async``` function to fetch data, check for the described > "collision" , create a ```data URI``` to be imported, optionally, append > addition code to be executed within the ```<script type="module">```. > > > but not sure of suitability for production-use, because of its dynamic > <script> tag generation. > > What is the issue with dynamic ```<script>``` tag generation? > > There is more than one possible approach to achieve the presumptive > requirement, that is still not clear to the exclusion of what is not the > expected result. > > There were no restrictions described at the OP and following messages > other than other than > > > pure-es6 application with 20 es-modules rolled-up into one [production] > bundle? > > The example code uses only JavaScript implementation shipped with the > browser without any external, third-party libraries. > > What standard or definition are you relying for the meaning of the term > "production-use"? What procedure are you using to determine if code is > "production-use" "suitable"? How is that procedure related to "how many > async-modules can js-app practically load?"? > > > > On Sat, Jun 1, 2019 at 9:42 PM kai zhu <kaizhu256 at gmail.com> wrote: > >> your rollup solution is interesting, but i get an error when run in >> chrome (i changed to n=20 to prevent name-collision, but it still >> happens). don't completely understand how it works, but not sure of >> suitability for production-use, because of its dynamic <script> tag >> generation. >> >> ```console >> ReferenceError: module names ["yeqjqb02mvg3yze26rc5"] are not unique >> at data:application/javascript,%0A%20%20%20%20%20%20const%20modules... >> ``` >> >> On Sat, Jun 1, 2019 at 2:33 PM guest271314 <guest271314 at gmail.com> wrote: >> >>> Re: how many async-modules can js-app practically load? >>> >>> An example of exporting and importing loading 1000 properties in a >>> single module, where duplicate property names are checked for. Since >>> JavaScript plain objects cannot have duplicate property names there should >>> not be any "collisions"; the code can check for and modify the object to be >>> exported, though the last duplicate property name will be exported without >>> any errors thrown unless the code is composed to throw such an error. >>> >>> ``` >>> (async() => { >>> const oneThousandModules = encodeURIComponent( >>> // substitute rand for a Set of module names to be exported >>> // e.g. const moduleNames = ['moduleA', 'moduleB', ...moduleZ] >>> ` >>> const modules = {}; >>> // set a function to be exported >>> modules.fn = function() {return 'a function'}; >>> // function to set (1000) 'random' module names to be exported >>> const rand = (seed = 'abcdefghijklmnopqrstuvwxyz0123456789', n = >>> 5, len = seed.length) => >>> '.'.repeat(n).replace(/./g, _ => seed[~~(Math.random() * len)]); >>> // use Set for unique module identifiers >>> const moduleNames = [...Array(1000)].map(_ => rand()); >>> const moduleIdentifiers = new Set(moduleNames); >>> // below line will cause ReferenceError to be thrown >>> moduleNames.push(moduleNames[0]); >>> try { >>> if (moduleIdentifiers.size !== moduleNames.length) { >>> // check for duplicates >>> const duplicates = moduleNames.filter((moduleName, index) => >>> moduleNames.indexOf(moduleName) !== index); >>> // notification of duplicate module names >>> throw new ReferenceError('module names ' + >>> JSON.stringify(duplicates) + ' are not unique'); >>> // perform the designated task if duplicate module names are >>> found here >>> } >>> } catch (e) { >>> console.error(e); >>> console.trace(); >>> } >>> // get, set (sync or async) exported module here >>> Object.assign(modules, ...[...moduleIdentifiers].map((id, value) >>> => ({[id]:value}))); >>> // since JavaScript plain object cannot have duplicate property >>> names >>> // modules object will still be exported without duplicate >>> property names >>> // without collisions >>> export {modules} >>> `); >>> const scriptText = `import {modules} from >>> "data:application/javascript,${oneThousandModules};${encodeURIComponent('console.log(modules);for >>> (const key in modules) {if (typeof modules[key] === \'function\') >>> {console.log(modules[key]());}}')}"`; >>> const script = document.createElement("script"); >>> script.type = "module"; >>> script.textContent = scriptText; >>> document.head.appendChild(script); >>> })(); >>> ``` >>> >>> plnkr https://plnkr.co/edit/CgEhBY?p=preview >>> >>> On Sat, Jun 1, 2019 at 1:51 AM kai zhu <kaizhu256 at gmail.com> wrote: >>> >>>> > Place all of the code to be exported in 1 file? >>>> >>>> that obviously will not work, because of module-scope collision. can >>>> anyone share their experience on deploying a [babel-free] pure-es6 >>>> application with 20 es-modules rolled-up into one [production] bundle? is >>>> it even possible? >>>> >>>> >>>> On Fri, May 31, 2019 at 7:55 PM guest271314 <guest271314 at gmail.com> >>>> wrote: >>>> >>>>> > how would i transition from development-mode (20 es-module files) >>>>> -> production-mode (1 rollup file)? >>>>> >>>>> Place all of the code to be exported in 1 file? >>>>> >>>>> > with some of them having circular-references >>>>> >>>>> Not certain how that is possible when using ```import``` within >>>>> ```<script type="module">```? >>>>> >>>>> > how many async-modules can js-app practically load? >>>>> >>>>> Again, how many have you tried to load? 100? 500? 1000? Either should >>>>> be possible. >>>>> >>>>> What specific issue are you actually to resolve? >>>>> >>>>> On Fri, May 31, 2019 at 5:40 PM kai zhu <kaizhu256 at gmail.com> wrote: >>>>> >>>>>> > Oh, and yes, I've loaded upwards of 50-100 modules in development. >>>>>> 20 >>>>>> modules is *easy* to achieve in single-page apps. >>>>>> >>>>>> was that with some combination of babel/rollup/webpack or pure-es6? >>>>>> if i want to develop a pure-es6 webapp (no babel), how would i >>>>>> transition from development-mode (20 es-module files) -> production-mode (1 >>>>>> rollup file)? >>>>>> >>>>>> >>>>>> On Fri, May 31, 2019 at 10:47 AM Isiah Meadows < >>>>>> isiahmeadows at gmail.com> wrote: >>>>>> >>>>>>> If it's bundled by Rollup or Webpack into a single bundle, it's >>>>>>> equivalent to a single `<script type="module" src="...">` pointing >>>>>>> towards the original entry point, excluding network requests.* But in >>>>>>> either case, you aren't listing 50 scripts, you're only listing the >>>>>>> entry module and importing child modules within parent modules. >>>>>>> Rollup >>>>>>> and Webpack do mostly the same thing browsers do when it comes to >>>>>>> resolving dependencies, just they generate a bundle afterwards where >>>>>>> browsers execute code afterwards. Also, it's worth noting that the >>>>>>> gap >>>>>>> between a single large request and multiple smaller requests has >>>>>>> shrunk a lot since HTTP/2 came along, since it's binary, it allows >>>>>>> requests and response data to be interleaved, it better leverages the >>>>>>> underlying TCP protocol format, and it allows servers to send data >>>>>>> pre-emptively without the client requesting it first. (Web sockets >>>>>>> are >>>>>>> built on this functionality.) It's still better to bundle in general, >>>>>>> but it's less of a problem not to. >>>>>>> >>>>>>> This is *not* the case for `<script type="module">` elements - those >>>>>>> operate more like inline scripts that happen to have the ability to >>>>>>> `import`. >>>>>>> >>>>>>> Oh, and yes, I've loaded upwards of 50-100 modules in development. 20 >>>>>>> modules is *easy* to achieve in single-page apps. >>>>>>> >>>>>>> * This is, of course, not the case if you are using pure ES6 and you >>>>>>> aren't using any plugins to, say, run the original source through >>>>>>> Babel for React + JSX or something. >>>>>>> >>>>>>> ----- >>>>>>> >>>>>>> Isiah Meadows >>>>>>> contact at isiahmeadows.com >>>>>>> www.isiahmeadows.com >>>>>>> On Sat, May 25, 2019 at 2:12 AM kai zhu <kaizhu256 at gmail.com> wrote: >>>>>>> > >>>>>>> > Asynchronous loading differs only in >>>>>>> > that it takes more code to express the same logic and you have to >>>>>>> take >>>>>>> > into account concurrent requests (and you need to cache the >>>>>>> request, >>>>>>> > not the result), but it's otherwise the same from 1km away. >>>>>>> > >>>>>>> > >>>>>>> > so async-loading 50 ```<script type="module">``` tags >>>>>>> > has equivalent side-effect >>>>>>> > as sync-loading single webpack-rollup (of same 50 modules)? >>>>>>> > >>>>>>> > i have nagging suspicion of doubts. has anyone tried native >>>>>>> async-loading large numbers (>10) of >>>>>>> > ```<script type="module">``` tags, and verify it resolves >>>>>>> identically to using a single webpack-rollup? >>>>>>> > >>>>>>> > again, i'm not that knowledgeable on es-modules, so above question >>>>>>> may be trivially true, and i'm just not aware. >>>>>>> > >>>>>>> > -kai >>>>>>> > >>>>>>> > On 24 May 2019, at 23:41, Isiah Meadows <isiahmeadows at gmail.com> >>>>>>> wrote: >>>>>>> > >>>>>>> > There's two main reasons why it scales: >>>>>>> > >>>>>>> > 1. Modules are strongly encapsulated while minimizing global >>>>>>> pollution. >>>>>>> > 2. The resolution algorithm applies the same logic no matter how >>>>>>> many >>>>>>> > modules are loaded. >>>>>>> > >>>>>>> > It's much easier for it to scale when you write the code unaware of >>>>>>> > how many modules you might be loading and unaware of how deep their >>>>>>> > dependency graph is. Fewer assumptions here is key. It's an >>>>>>> > engineering problem, but a relatively simple one. >>>>>>> > >>>>>>> > If you want a short example of how sync module resolution works, >>>>>>> you >>>>>>> > can take a look at this little utility I wrote: >>>>>>> > https://github.com/isiahmeadows/simple-require-loader. That >>>>>>> doesn't >>>>>>> > asynchronously resolve modules, but it should help explain the >>>>>>> process >>>>>>> > from a synchronous standpoint. Asynchronous loading differs only in >>>>>>> > that it takes more code to express the same logic and you have to >>>>>>> take >>>>>>> > into account concurrent requests (and you need to cache the >>>>>>> request, >>>>>>> > not the result), but it's otherwise the same from 1km away. >>>>>>> > >>>>>>> > ----- >>>>>>> > >>>>>>> > Isiah Meadows >>>>>>> > contact at isiahmeadows.com >>>>>>> > www.isiahmeadows.com >>>>>>> > >>>>>>> > On Thu, May 23, 2019 at 10:49 AM kai zhu <kaizhu256 at gmail.com> >>>>>>> wrote: >>>>>>> > >>>>>>> > >>>>>>> > actually, i admit i don't know what i'm talking about. just >>>>>>> generally confused (through ignorance) on how large-scale es-module >>>>>>> dependencies resolve when loaded/imported asynchronously. >>>>>>> > >>>>>>> > On Wed, May 22, 2019 at 10:42 PM Logan Smyth < >>>>>>> loganfsmyth at gmail.com> wrote: >>>>>>> > >>>>>>> > >>>>>>> > Can you elaborate on what loading state you need to keep track of? >>>>>>> What is the bottleneck that you run into? Also to be sure, when you say >>>>>>> async-load, do you mean `import()`? >>>>>>> > >>>>>>> > On Wed, May 22, 2019, 20:17 kai zhu <kaizhu256 at gmail.com> wrote: >>>>>>> > >>>>>>> > >>>>>>> > i don't use es-modules. >>>>>>> > but with amd/requirejs, I start having trouble with >>>>>>> module-initializations in nodejs/browser at ~5 async modules (that may or >>>>>>> may not have circular-references). 10 would be hard, and 20 would be near >>>>>>> inhuman for me. >>>>>>> > >>>>>>> > can we say its somewhat impractical for most applications to load >>>>>>> more than 50 async modules (with some of them having circular-references)? >>>>>>> and perhaps better design/spec module-loading mechanisms with this >>>>>>> usability concern in mind? >>>>>>> > >>>>>>> > p.s. its also impractical for me to async-load 5 or more modules >>>>>>> without using globalThis to keep track of each module's loading-state. >>>>>>> > _______________________________________________ >>>>>>> > es-discuss mailing list >>>>>>> > es-discuss at mozilla.org >>>>>>> > https://mail.mozilla.org/listinfo/es-discuss >>>>>>> > >>>>>>> > >>>>>>> > _______________________________________________ >>>>>>> > es-discuss mailing list >>>>>>> > es-discuss at mozilla.org >>>>>>> > https://mail.mozilla.org/listinfo/es-discuss >>>>>>> > >>>>>>> > >>>>>>> >>>>>> _______________________________________________ >>>>>> es-discuss mailing list >>>>>> es-discuss at mozilla.org >>>>>> https://mail.mozilla.org/listinfo/es-discuss >>>>>> >>>>> -------------- next part -------------- An HTML attachment was scrubbed... URL: <http://mail.mozilla.org/pipermail/es-discuss/attachments/20190601/194f0d81/attachment-0001.html>
it doesn't actually
import
1000+ es-modules inside the rollup-file. it just creates one es-module that exports a dictionary -- and assigns the dictionary 1000+ vanilla json-objects and functions.
The code provides a means to fetch N resources and export those resources within a single object at a single dynamically created file.
currently, as i'm aware, nobody uses native es-modules in production, because it cannot be rolled-up. in practice es-modules are [babel] transpiled down to es5-amd (or similar) for rollup-purposes.
if we're actually committed to native es-modules, then we either
- need to depend on embedders like loading-dev at chromium.org to create sophisticated cache-systems, or
- introduce new language-syntax to delimit es-modules for rollup-purposes, e.g.
You still have not clearly defined what you mean by "rolled-up". That language appears to be a random nickname, not any immutable principle that individuals are bound to recognize or observe (even if "rolled-up" were some form of a coding style or standard).
Nor is it clear what you mean by "production".
There is no external central committee that stamps code as "production". Even if there were no individual is obliged to submit to such a procedure nor have any concern for such an arbitrary and irrelevant presumptive review of code.
The only observable points are input and output. In general, how output is achieved is immaterial. If there are specific restrictions as to how the output can be achieved then those restrictions need to be clearly defined.
The original post asked "how many async-modules can js-app practically load?" and mentioned "circular-references". Though as yet no code has been posted which demonstrates "circular-references" or any other actual coding problem.
What issue are you trying to resolve with the current code that you are using? Are there errors thrown? What limitations does your current code have that you are trying to resolve? Is the topic about one or more coding styles?
What are you trying to do that you cannot do now?
> it doesn't actually ```import``` 1000+ es-modules inside the rollup-file. it just creates one es-module that exports a dictionary -- and assigns the dictionary 1000+ vanilla json-objects and functions. The code provides a means to fetch N resources and export those resources within a single object. > currently, as i'm aware, nobody uses native es-modules in production, because it cannot be rolled-up. > in practice es-modules are [babel] transpiled down to es5-amd (or similar) for rollup-purposes. > > if we're actually committed to native es-modules, then we either > 1) need to depend on embedders like loading-dev at chromium.org to create sophisticated cache-systems, or > 2) introduce new language-syntax to delimit es-modules for rollup-purposes, e.g. You still have not clearly defined what you mean by "rolled-up". That language appears to be a random nickname, not any immutable principle that individuals are bound to recognize or observe (even if "rolled-up" were some form of a coding style or standard). Nor is it clear what you mean by "production". There is no external central committee that stamps code as "production". Even if there were no individual is obliged to submit to such a procedure nor have any concern for such an arbitrary and irrelevant presumptive review of code. The only observable points are input and output. In general, how output is achieved is immaterial. If there are specific restrictions as to how the output can be achieved then those restrictions need to be clearly defined. The original post asked "how many async-modules can js-app practically load?" and mentioned "circular-references" (the thread appears to mainly be about one or more coding styles, not code itself) though as yet no code has been posted which demonstrates "circular-references" or any other coding problem. On Sun, Jun 2, 2019 at 1:30 AM kai zhu <kaizhu256 at gmail.com> wrote: > i played around with your code in jsfiddle [1], and understand it a little > more. > it doesn't actually ```import``` 1000+ es-modules inside the rollup-file. > it just creates one es-module that exports a dictionary > -- and assigns the dictionary 1000+ vanilla json-objects and functions. > > ```js > // the "rollup-file" is a single es-module > // that exports 1000+ vanilla dictionary-entries > const modules = {}; > > // this is not a es-module, nor is it rolled-up (external fetch) > modules.image = <await fetch json from gist.github.com> > > // this is not a [rolled-up] es-module > modules.fn = function () {...} > > // these are not [rolled-up] es-modules > Object.assign(modules, <1000 json-entries>) > > export {modules} > ``` > > currently, as i'm aware, nobody uses native es-modules in production, > because it cannot be rolled-up. > in practice es-modules are [babel] transpiled down to es5-amd (or similar) > for rollup-purposes. > > if we're actually committed to native es-modules, then we either > 1) need to depend on embedders like loading-dev at chromium.org to create > sophisticated cache-systems, or > 2) introduce new language-syntax to delimit es-modules for > rollup-purposes, e.g. > > ```js > // rollup.js with [hypothetical] # delimited es-modules > # module aa > import {bb} as bb; > export ...; > > # module bb > export ...; > ``` > > i'm generally skeptical of option 1, given how poorly npmjs.com has > handled similar problems deduplicating children in node_modules/ directory. > > [1] jsfiddle pseudo-module rollup > https://jsfiddle.net/06twrLfd/ > > On Sat, Jun 1, 2019 at 5:30 PM guest271314 <guest271314 at gmail.com> wrote: > >> > your rollup solution is interesting, >> >> What is "rollup" referring to? >> >> > but i get an error when run in chrome (i changed to n=20 to prevent >> name-collision, but it still happens). >> >> The duplicate ("collision") entry an ```try..catch``` block is included >> in the code to demonstrate given an array of module names to be exported >> and imported as identifiers 1) duplicate entries can be filtered; 2) if a >> plain object is exported duplicate identifiers ("collision") is not >> possible as a JavaScript plain object does not have duplicate property >> names ("collision"); if there is an issue with identifiers in a module the >> cause would not be the number of async-modules loaded ("how many"), but the >> naming of the identifiers within the code, using or not using ```const``` >> or ```let```. Still not sure what the actual issue is? >> >> > don't completely understand how it works, >> >> Use an ```async``` function to fetch data, check for the described >> "collision" , create a ```data URI``` to be imported, optionally, append >> addition code to be executed within the ```<script type="module">```. >> >> > but not sure of suitability for production-use, because of its dynamic >> <script> tag generation. >> >> What is the issue with dynamic ```<script>``` tag generation? >> >> There is more than one possible approach to achieve the presumptive >> requirement, that is still not clear to the exclusion of what is not the >> expected result. >> >> There were no restrictions described at the OP and following messages >> other than other than >> >> > pure-es6 application with 20 es-modules rolled-up into one >> [production] bundle? >> >> The example code uses only JavaScript implementation shipped with the >> browser without any external, third-party libraries. >> >> What standard or definition are you relying for the meaning of the term >> "production-use"? What procedure are you using to determine if code is >> "production-use" "suitable"? How is that procedure related to "how many >> async-modules can js-app practically load?"? >> >> >> >> On Sat, Jun 1, 2019 at 9:42 PM kai zhu <kaizhu256 at gmail.com> wrote: >> >>> your rollup solution is interesting, but i get an error when run in >>> chrome (i changed to n=20 to prevent name-collision, but it still >>> happens). don't completely understand how it works, but not sure of >>> suitability for production-use, because of its dynamic <script> tag >>> generation. >>> >>> ```console >>> ReferenceError: module names ["yeqjqb02mvg3yze26rc5"] are not unique >>> at >>> data:application/javascript,%0A%20%20%20%20%20%20const%20modules... >>> ``` >>> >>> On Sat, Jun 1, 2019 at 2:33 PM guest271314 <guest271314 at gmail.com> >>> wrote: >>> >>>> Re: how many async-modules can js-app practically load? >>>> >>>> An example of exporting and importing loading 1000 properties in a >>>> single module, where duplicate property names are checked for. Since >>>> JavaScript plain objects cannot have duplicate property names there should >>>> not be any "collisions"; the code can check for and modify the object to be >>>> exported, though the last duplicate property name will be exported without >>>> any errors thrown unless the code is composed to throw such an error. >>>> >>>> ``` >>>> (async() => { >>>> const oneThousandModules = encodeURIComponent( >>>> // substitute rand for a Set of module names to be exported >>>> // e.g. const moduleNames = ['moduleA', 'moduleB', ...moduleZ] >>>> ` >>>> const modules = {}; >>>> // set a function to be exported >>>> modules.fn = function() {return 'a function'}; >>>> // function to set (1000) 'random' module names to be exported >>>> const rand = (seed = 'abcdefghijklmnopqrstuvwxyz0123456789', n = >>>> 5, len = seed.length) => >>>> '.'.repeat(n).replace(/./g, _ => seed[~~(Math.random() * len)]); >>>> // use Set for unique module identifiers >>>> const moduleNames = [...Array(1000)].map(_ => rand()); >>>> const moduleIdentifiers = new Set(moduleNames); >>>> // below line will cause ReferenceError to be thrown >>>> moduleNames.push(moduleNames[0]); >>>> try { >>>> if (moduleIdentifiers.size !== moduleNames.length) { >>>> // check for duplicates >>>> const duplicates = moduleNames.filter((moduleName, index) >>>> => moduleNames.indexOf(moduleName) !== index); >>>> // notification of duplicate module names >>>> throw new ReferenceError('module names ' + >>>> JSON.stringify(duplicates) + ' are not unique'); >>>> // perform the designated task if duplicate module names >>>> are found here >>>> } >>>> } catch (e) { >>>> console.error(e); >>>> console.trace(); >>>> } >>>> // get, set (sync or async) exported module here >>>> Object.assign(modules, ...[...moduleIdentifiers].map((id, >>>> value) => ({[id]:value}))); >>>> // since JavaScript plain object cannot have duplicate property >>>> names >>>> // modules object will still be exported without duplicate >>>> property names >>>> // without collisions >>>> export {modules} >>>> `); >>>> const scriptText = `import {modules} from >>>> "data:application/javascript,${oneThousandModules};${encodeURIComponent('console.log(modules);for >>>> (const key in modules) {if (typeof modules[key] === \'function\') >>>> {console.log(modules[key]());}}')}"`; >>>> const script = document.createElement("script"); >>>> script.type = "module"; >>>> script.textContent = scriptText; >>>> document.head.appendChild(script); >>>> })(); >>>> ``` >>>> >>>> plnkr https://plnkr.co/edit/CgEhBY?p=preview >>>> >>>> On Sat, Jun 1, 2019 at 1:51 AM kai zhu <kaizhu256 at gmail.com> wrote: >>>> >>>>> > Place all of the code to be exported in 1 file? >>>>> >>>>> that obviously will not work, because of module-scope collision. can >>>>> anyone share their experience on deploying a [babel-free] pure-es6 >>>>> application with 20 es-modules rolled-up into one [production] bundle? is >>>>> it even possible? >>>>> >>>>> >>>>> On Fri, May 31, 2019 at 7:55 PM guest271314 <guest271314 at gmail.com> >>>>> wrote: >>>>> >>>>>> > how would i transition from development-mode (20 es-module files) >>>>>> -> production-mode (1 rollup file)? >>>>>> >>>>>> Place all of the code to be exported in 1 file? >>>>>> >>>>>> > with some of them having circular-references >>>>>> >>>>>> Not certain how that is possible when using ```import``` within >>>>>> ```<script type="module">```? >>>>>> >>>>>> > how many async-modules can js-app practically load? >>>>>> >>>>>> Again, how many have you tried to load? 100? 500? 1000? Either should >>>>>> be possible. >>>>>> >>>>>> What specific issue are you actually to resolve? >>>>>> >>>>>> On Fri, May 31, 2019 at 5:40 PM kai zhu <kaizhu256 at gmail.com> wrote: >>>>>> >>>>>>> > Oh, and yes, I've loaded upwards of 50-100 modules in development. >>>>>>> 20 >>>>>>> modules is *easy* to achieve in single-page apps. >>>>>>> >>>>>>> was that with some combination of babel/rollup/webpack or pure-es6? >>>>>>> if i want to develop a pure-es6 webapp (no babel), how would i >>>>>>> transition from development-mode (20 es-module files) -> production-mode (1 >>>>>>> rollup file)? >>>>>>> >>>>>>> >>>>>>> On Fri, May 31, 2019 at 10:47 AM Isiah Meadows < >>>>>>> isiahmeadows at gmail.com> wrote: >>>>>>> >>>>>>>> If it's bundled by Rollup or Webpack into a single bundle, it's >>>>>>>> equivalent to a single `<script type="module" src="...">` pointing >>>>>>>> towards the original entry point, excluding network requests.* But >>>>>>>> in >>>>>>>> either case, you aren't listing 50 scripts, you're only listing the >>>>>>>> entry module and importing child modules within parent modules. >>>>>>>> Rollup >>>>>>>> and Webpack do mostly the same thing browsers do when it comes to >>>>>>>> resolving dependencies, just they generate a bundle afterwards where >>>>>>>> browsers execute code afterwards. Also, it's worth noting that the >>>>>>>> gap >>>>>>>> between a single large request and multiple smaller requests has >>>>>>>> shrunk a lot since HTTP/2 came along, since it's binary, it allows >>>>>>>> requests and response data to be interleaved, it better leverages >>>>>>>> the >>>>>>>> underlying TCP protocol format, and it allows servers to send data >>>>>>>> pre-emptively without the client requesting it first. (Web sockets >>>>>>>> are >>>>>>>> built on this functionality.) It's still better to bundle in >>>>>>>> general, >>>>>>>> but it's less of a problem not to. >>>>>>>> >>>>>>>> This is *not* the case for `<script type="module">` elements - those >>>>>>>> operate more like inline scripts that happen to have the ability to >>>>>>>> `import`. >>>>>>>> >>>>>>>> Oh, and yes, I've loaded upwards of 50-100 modules in development. >>>>>>>> 20 >>>>>>>> modules is *easy* to achieve in single-page apps. >>>>>>>> >>>>>>>> * This is, of course, not the case if you are using pure ES6 and you >>>>>>>> aren't using any plugins to, say, run the original source through >>>>>>>> Babel for React + JSX or something. >>>>>>>> >>>>>>>> ----- >>>>>>>> >>>>>>>> Isiah Meadows >>>>>>>> contact at isiahmeadows.com >>>>>>>> www.isiahmeadows.com >>>>>>>> On Sat, May 25, 2019 at 2:12 AM kai zhu <kaizhu256 at gmail.com> >>>>>>>> wrote: >>>>>>>> > >>>>>>>> > Asynchronous loading differs only in >>>>>>>> > that it takes more code to express the same logic and you have to >>>>>>>> take >>>>>>>> > into account concurrent requests (and you need to cache the >>>>>>>> request, >>>>>>>> > not the result), but it's otherwise the same from 1km away. >>>>>>>> > >>>>>>>> > >>>>>>>> > so async-loading 50 ```<script type="module">``` tags >>>>>>>> > has equivalent side-effect >>>>>>>> > as sync-loading single webpack-rollup (of same 50 modules)? >>>>>>>> > >>>>>>>> > i have nagging suspicion of doubts. has anyone tried native >>>>>>>> async-loading large numbers (>10) of >>>>>>>> > ```<script type="module">``` tags, and verify it resolves >>>>>>>> identically to using a single webpack-rollup? >>>>>>>> > >>>>>>>> > again, i'm not that knowledgeable on es-modules, so above >>>>>>>> question may be trivially true, and i'm just not aware. >>>>>>>> > >>>>>>>> > -kai >>>>>>>> > >>>>>>>> > On 24 May 2019, at 23:41, Isiah Meadows <isiahmeadows at gmail.com> >>>>>>>> wrote: >>>>>>>> > >>>>>>>> > There's two main reasons why it scales: >>>>>>>> > >>>>>>>> > 1. Modules are strongly encapsulated while minimizing global >>>>>>>> pollution. >>>>>>>> > 2. The resolution algorithm applies the same logic no matter how >>>>>>>> many >>>>>>>> > modules are loaded. >>>>>>>> > >>>>>>>> > It's much easier for it to scale when you write the code unaware >>>>>>>> of >>>>>>>> > how many modules you might be loading and unaware of how deep >>>>>>>> their >>>>>>>> > dependency graph is. Fewer assumptions here is key. It's an >>>>>>>> > engineering problem, but a relatively simple one. >>>>>>>> > >>>>>>>> > If you want a short example of how sync module resolution works, >>>>>>>> you >>>>>>>> > can take a look at this little utility I wrote: >>>>>>>> > https://github.com/isiahmeadows/simple-require-loader. That >>>>>>>> doesn't >>>>>>>> > asynchronously resolve modules, but it should help explain the >>>>>>>> process >>>>>>>> > from a synchronous standpoint. Asynchronous loading differs only >>>>>>>> in >>>>>>>> > that it takes more code to express the same logic and you have to >>>>>>>> take >>>>>>>> > into account concurrent requests (and you need to cache the >>>>>>>> request, >>>>>>>> > not the result), but it's otherwise the same from 1km away. >>>>>>>> > >>>>>>>> > ----- >>>>>>>> > >>>>>>>> > Isiah Meadows >>>>>>>> > contact at isiahmeadows.com >>>>>>>> > www.isiahmeadows.com >>>>>>>> > >>>>>>>> > On Thu, May 23, 2019 at 10:49 AM kai zhu <kaizhu256 at gmail.com> >>>>>>>> wrote: >>>>>>>> > >>>>>>>> > >>>>>>>> > actually, i admit i don't know what i'm talking about. just >>>>>>>> generally confused (through ignorance) on how large-scale es-module >>>>>>>> dependencies resolve when loaded/imported asynchronously. >>>>>>>> > >>>>>>>> > On Wed, May 22, 2019 at 10:42 PM Logan Smyth < >>>>>>>> loganfsmyth at gmail.com> wrote: >>>>>>>> > >>>>>>>> > >>>>>>>> > Can you elaborate on what loading state you need to keep track >>>>>>>> of? What is the bottleneck that you run into? Also to be sure, when you say >>>>>>>> async-load, do you mean `import()`? >>>>>>>> > >>>>>>>> > On Wed, May 22, 2019, 20:17 kai zhu <kaizhu256 at gmail.com> wrote: >>>>>>>> > >>>>>>>> > >>>>>>>> > i don't use es-modules. >>>>>>>> > but with amd/requirejs, I start having trouble with >>>>>>>> module-initializations in nodejs/browser at ~5 async modules (that may or >>>>>>>> may not have circular-references). 10 would be hard, and 20 would be near >>>>>>>> inhuman for me. >>>>>>>> > >>>>>>>> > can we say its somewhat impractical for most applications to load >>>>>>>> more than 50 async modules (with some of them having circular-references)? >>>>>>>> and perhaps better design/spec module-loading mechanisms with this >>>>>>>> usability concern in mind? >>>>>>>> > >>>>>>>> > p.s. its also impractical for me to async-load 5 or more modules >>>>>>>> without using globalThis to keep track of each module's loading-state. >>>>>>>> > _______________________________________________ >>>>>>>> > es-discuss mailing list >>>>>>>> > es-discuss at mozilla.org >>>>>>>> > https://mail.mozilla.org/listinfo/es-discuss >>>>>>>> > >>>>>>>> > >>>>>>>> > _______________________________________________ >>>>>>>> > es-discuss mailing list >>>>>>>> > es-discuss at mozilla.org >>>>>>>> > https://mail.mozilla.org/listinfo/es-discuss >>>>>>>> > >>>>>>>> > >>>>>>>> >>>>>>> _______________________________________________ >>>>>>> es-discuss mailing list >>>>>>> es-discuss at mozilla.org >>>>>>> https://mail.mozilla.org/listinfo/es-discuss >>>>>>> >>>>>> -------------- next part -------------- An HTML attachment was scrubbed... URL: <http://mail.mozilla.org/pipermail/es-discuss/attachments/20190602/afa67299/attachment-0001.html>
i apologize for poor framing of my questions. they are still formative, but i can clarify abit as follows:
- original-question - is native es-module's async-behavior desirable?
async side-effects are difficult to manage -- i conjecture that
async-loading 20 es-modules (with dependent side-effects) is not practical
for most mortals to handle.
@frederick describes the mechanism for how to hint the brower to pre-fetch
20 es-modules. but if you pre-fetch, then is loading-behavior effectively
synchronous?
@isiah says he has experience loading 50-100 modules, but was unclear
whether they were individual [async]
<script type="module">
tags, or
some es5-transpiled rollup.
i may be wrong about everything, as i'm a bit ignorant on what async actually means in es-modules (and appreciate it, if someone can clarify that).
- the second-question about es-module rollups (which you and i are debating) stemmed from @isiah's response -- if he and everyone-else use es5-transpiled rollups (which i suspect), then shouldn't it be desirable for es-modules to natively support rollups as well? currently, there's no way to natively rollup multiple es-modules into a single bundle.
this 2nd question also has implications about es-module's async-behavior
(because rollups "load" modules in sync/blocking fashion). this could
change side-effect behaviors between development-mode (20 [async] <script type="module">
tags) and production-mode (1 rollup-bundle). again, i
may be wrong about that, as i'm ignorant about what async actually is in es-modules.
i apologize for poor framing of my questions. they are still formative, but i can clarify abit as follows: 1) original-question - is native es-module's async-behavior desirable? async side-effects are difficult to manage -- i conjecture that async-loading 20 es-modules (with dependent side-effects) is not practical for most mortals to handle. @frederick describes the mechanism for how to hint the brower to pre-fetch 20 es-modules. but if you pre-fetch, then is loading-behavior effectively synchronous? @isiah says he has experience loading 50-100 modules, but was unclear whether they were individual [async] ```<script type="module">``` tags, or some es5-transpiled rollup. i may be wrong about everything, as i'm a bit ignorant on what async actually means in es-modules (and appreciate it, if someone can clarify that). 2) the second-question about es-module rollups (which you and i are debating) stemmed from @isiah's response -- if he and everyone-else use es5-transpiled rollups (which i suspect), then shouldn't it be desirable for es-modules to natively support rollups as well? currently, there's no way to natively rollup multiple es-modules into a single bundle. this 2nd question also has implications about es-module's async-behavior (because rollups "load" modules in sync/blocking fashion). this could change side-effect behaviors between development-mode (20 [async] ```<script type="module">``` tags) and production-mode (1 rollup-bundle). again, i may be wrong about that, as i'm ignorant about what async actually is in es-modules. -kai On Sat, Jun 1, 2019 at 9:22 PM guest271314 <guest271314 at gmail.com> wrote: > > it doesn't actually ```import``` 1000+ es-modules inside the > rollup-file. it just creates one es-module that exports a dictionary -- and > assigns the dictionary 1000+ vanilla json-objects and functions. > > The code provides a means to fetch N resources and export those resources > within a single object. > > > currently, as i'm aware, nobody uses native es-modules in production, > because it cannot be rolled-up. > > in practice es-modules are [babel] transpiled down to es5-amd (or > similar) for rollup-purposes. > > > > if we're actually committed to native es-modules, then we either > > 1) need to depend on embedders like loading-dev at chromium.org to create > sophisticated cache-systems, or > > 2) introduce new language-syntax to delimit es-modules for > rollup-purposes, e.g. > > You still have not clearly defined what you mean by "rolled-up". That > language appears to be a random nickname, not any immutable principle that > individuals are bound to recognize or observe (even if "rolled-up" were > some form of a coding style or standard). > > Nor is it clear what you mean by "production". > > There is no external central committee that stamps code as "production". > Even if there were no individual is obliged to submit to such a procedure > nor have any concern for such an arbitrary and irrelevant presumptive > review of code. > > The only observable points are input and output. In general, how output is > achieved is immaterial. If there are specific restrictions as to how the > output can be achieved then those restrictions need to be clearly defined. > > > > The original post asked "how many async-modules can js-app practically > load?" and mentioned "circular-references" (the thread appears to mainly > be about one or more coding styles, not code itself) though as yet no code > has been posted which demonstrates "circular-references" or any other > coding problem. > > On Sun, Jun 2, 2019 at 1:30 AM kai zhu <kaizhu256 at gmail.com> wrote: > >> i played around with your code in jsfiddle [1], and understand it a >> little more. >> it doesn't actually ```import``` 1000+ es-modules inside the rollup-file. >> it just creates one es-module that exports a dictionary >> -- and assigns the dictionary 1000+ vanilla json-objects and functions. >> >> ```js >> // the "rollup-file" is a single es-module >> // that exports 1000+ vanilla dictionary-entries >> const modules = {}; >> >> // this is not a es-module, nor is it rolled-up (external fetch) >> modules.image = <await fetch json from gist.github.com> >> >> // this is not a [rolled-up] es-module >> modules.fn = function () {...} >> >> // these are not [rolled-up] es-modules >> Object.assign(modules, <1000 json-entries>) >> >> export {modules} >> ``` >> >> currently, as i'm aware, nobody uses native es-modules in production, >> because it cannot be rolled-up. >> in practice es-modules are [babel] transpiled down to es5-amd (or >> similar) for rollup-purposes. >> >> if we're actually committed to native es-modules, then we either >> 1) need to depend on embedders like loading-dev at chromium.org to create >> sophisticated cache-systems, or >> 2) introduce new language-syntax to delimit es-modules for >> rollup-purposes, e.g. >> >> ```js >> // rollup.js with [hypothetical] # delimited es-modules >> # module aa >> import {bb} as bb; >> export ...; >> >> # module bb >> export ...; >> ``` >> >> i'm generally skeptical of option 1, given how poorly npmjs.com has >> handled similar problems deduplicating children in node_modules/ directory. >> >> [1] jsfiddle pseudo-module rollup >> https://jsfiddle.net/06twrLfd/ >> >> On Sat, Jun 1, 2019 at 5:30 PM guest271314 <guest271314 at gmail.com> wrote: >> >>> > your rollup solution is interesting, >>> >>> What is "rollup" referring to? >>> >>> > but i get an error when run in chrome (i changed to n=20 to prevent >>> name-collision, but it still happens). >>> >>> The duplicate ("collision") entry an ```try..catch``` block is included >>> in the code to demonstrate given an array of module names to be exported >>> and imported as identifiers 1) duplicate entries can be filtered; 2) if a >>> plain object is exported duplicate identifiers ("collision") is not >>> possible as a JavaScript plain object does not have duplicate property >>> names ("collision"); if there is an issue with identifiers in a module the >>> cause would not be the number of async-modules loaded ("how many"), but the >>> naming of the identifiers within the code, using or not using ```const``` >>> or ```let```. Still not sure what the actual issue is? >>> >>> > don't completely understand how it works, >>> >>> Use an ```async``` function to fetch data, check for the described >>> "collision" , create a ```data URI``` to be imported, optionally, append >>> addition code to be executed within the ```<script type="module">```. >>> >>> > but not sure of suitability for production-use, because of its dynamic >>> <script> tag generation. >>> >>> What is the issue with dynamic ```<script>``` tag generation? >>> >>> There is more than one possible approach to achieve the presumptive >>> requirement, that is still not clear to the exclusion of what is not the >>> expected result. >>> >>> There were no restrictions described at the OP and following messages >>> other than other than >>> >>> > pure-es6 application with 20 es-modules rolled-up into one >>> [production] bundle? >>> >>> The example code uses only JavaScript implementation shipped with the >>> browser without any external, third-party libraries. >>> >>> What standard or definition are you relying for the meaning of the term >>> "production-use"? What procedure are you using to determine if code is >>> "production-use" "suitable"? How is that procedure related to "how many >>> async-modules can js-app practically load?"? >>> >>> >>> >>> On Sat, Jun 1, 2019 at 9:42 PM kai zhu <kaizhu256 at gmail.com> wrote: >>> >>>> your rollup solution is interesting, but i get an error when run in >>>> chrome (i changed to n=20 to prevent name-collision, but it still >>>> happens). don't completely understand how it works, but not sure of >>>> suitability for production-use, because of its dynamic <script> tag >>>> generation. >>>> >>>> ```console >>>> ReferenceError: module names ["yeqjqb02mvg3yze26rc5"] are not unique >>>> at >>>> data:application/javascript,%0A%20%20%20%20%20%20const%20modules... >>>> ``` >>>> >>>> On Sat, Jun 1, 2019 at 2:33 PM guest271314 <guest271314 at gmail.com> >>>> wrote: >>>> >>>>> Re: how many async-modules can js-app practically load? >>>>> >>>>> An example of exporting and importing loading 1000 properties in a >>>>> single module, where duplicate property names are checked for. Since >>>>> JavaScript plain objects cannot have duplicate property names there should >>>>> not be any "collisions"; the code can check for and modify the object to be >>>>> exported, though the last duplicate property name will be exported without >>>>> any errors thrown unless the code is composed to throw such an error. >>>>> >>>>> ``` >>>>> (async() => { >>>>> const oneThousandModules = encodeURIComponent( >>>>> // substitute rand for a Set of module names to be exported >>>>> // e.g. const moduleNames = ['moduleA', 'moduleB', ...moduleZ] >>>>> ` >>>>> const modules = {}; >>>>> // set a function to be exported >>>>> modules.fn = function() {return 'a function'}; >>>>> // function to set (1000) 'random' module names to be exported >>>>> const rand = (seed = 'abcdefghijklmnopqrstuvwxyz0123456789', n = >>>>> 5, len = seed.length) => >>>>> '.'.repeat(n).replace(/./g, _ => seed[~~(Math.random() * >>>>> len)]); >>>>> // use Set for unique module identifiers >>>>> const moduleNames = [...Array(1000)].map(_ => rand()); >>>>> const moduleIdentifiers = new Set(moduleNames); >>>>> // below line will cause ReferenceError to be thrown >>>>> moduleNames.push(moduleNames[0]); >>>>> try { >>>>> if (moduleIdentifiers.size !== moduleNames.length) { >>>>> // check for duplicates >>>>> const duplicates = moduleNames.filter((moduleName, index) >>>>> => moduleNames.indexOf(moduleName) !== index); >>>>> // notification of duplicate module names >>>>> throw new ReferenceError('module names ' + >>>>> JSON.stringify(duplicates) + ' are not unique'); >>>>> // perform the designated task if duplicate module names >>>>> are found here >>>>> } >>>>> } catch (e) { >>>>> console.error(e); >>>>> console.trace(); >>>>> } >>>>> // get, set (sync or async) exported module here >>>>> Object.assign(modules, ...[...moduleIdentifiers].map((id, >>>>> value) => ({[id]:value}))); >>>>> // since JavaScript plain object cannot have duplicate >>>>> property names >>>>> // modules object will still be exported without duplicate >>>>> property names >>>>> // without collisions >>>>> export {modules} >>>>> `); >>>>> const scriptText = `import {modules} from >>>>> "data:application/javascript,${oneThousandModules};${encodeURIComponent('console.log(modules);for >>>>> (const key in modules) {if (typeof modules[key] === \'function\') >>>>> {console.log(modules[key]());}}')}"`; >>>>> const script = document.createElement("script"); >>>>> script.type = "module"; >>>>> script.textContent = scriptText; >>>>> document.head.appendChild(script); >>>>> })(); >>>>> ``` >>>>> >>>>> plnkr https://plnkr.co/edit/CgEhBY?p=preview >>>>> >>>>> On Sat, Jun 1, 2019 at 1:51 AM kai zhu <kaizhu256 at gmail.com> wrote: >>>>> >>>>>> > Place all of the code to be exported in 1 file? >>>>>> >>>>>> that obviously will not work, because of module-scope collision. can >>>>>> anyone share their experience on deploying a [babel-free] pure-es6 >>>>>> application with 20 es-modules rolled-up into one [production] bundle? is >>>>>> it even possible? >>>>>> >>>>>> >>>>>> On Fri, May 31, 2019 at 7:55 PM guest271314 <guest271314 at gmail.com> >>>>>> wrote: >>>>>> >>>>>>> > how would i transition from development-mode (20 es-module files) >>>>>>> -> production-mode (1 rollup file)? >>>>>>> >>>>>>> Place all of the code to be exported in 1 file? >>>>>>> >>>>>>> > with some of them having circular-references >>>>>>> >>>>>>> Not certain how that is possible when using ```import``` within >>>>>>> ```<script type="module">```? >>>>>>> >>>>>>> > how many async-modules can js-app practically load? >>>>>>> >>>>>>> Again, how many have you tried to load? 100? 500? 1000? Either >>>>>>> should be possible. >>>>>>> >>>>>>> What specific issue are you actually to resolve? >>>>>>> >>>>>>> On Fri, May 31, 2019 at 5:40 PM kai zhu <kaizhu256 at gmail.com> wrote: >>>>>>> >>>>>>>> > Oh, and yes, I've loaded upwards of 50-100 modules in >>>>>>>> development. 20 >>>>>>>> modules is *easy* to achieve in single-page apps. >>>>>>>> >>>>>>>> was that with some combination of babel/rollup/webpack or pure-es6? >>>>>>>> if i want to develop a pure-es6 webapp (no babel), how would i >>>>>>>> transition from development-mode (20 es-module files) -> production-mode (1 >>>>>>>> rollup file)? >>>>>>>> >>>>>>>> >>>>>>>> On Fri, May 31, 2019 at 10:47 AM Isiah Meadows < >>>>>>>> isiahmeadows at gmail.com> wrote: >>>>>>>> >>>>>>>>> If it's bundled by Rollup or Webpack into a single bundle, it's >>>>>>>>> equivalent to a single `<script type="module" src="...">` pointing >>>>>>>>> towards the original entry point, excluding network requests.* But >>>>>>>>> in >>>>>>>>> either case, you aren't listing 50 scripts, you're only listing the >>>>>>>>> entry module and importing child modules within parent modules. >>>>>>>>> Rollup >>>>>>>>> and Webpack do mostly the same thing browsers do when it comes to >>>>>>>>> resolving dependencies, just they generate a bundle afterwards >>>>>>>>> where >>>>>>>>> browsers execute code afterwards. Also, it's worth noting that the >>>>>>>>> gap >>>>>>>>> between a single large request and multiple smaller requests has >>>>>>>>> shrunk a lot since HTTP/2 came along, since it's binary, it allows >>>>>>>>> requests and response data to be interleaved, it better leverages >>>>>>>>> the >>>>>>>>> underlying TCP protocol format, and it allows servers to send data >>>>>>>>> pre-emptively without the client requesting it first. (Web sockets >>>>>>>>> are >>>>>>>>> built on this functionality.) It's still better to bundle in >>>>>>>>> general, >>>>>>>>> but it's less of a problem not to. >>>>>>>>> >>>>>>>>> This is *not* the case for `<script type="module">` elements - >>>>>>>>> those >>>>>>>>> operate more like inline scripts that happen to have the ability to >>>>>>>>> `import`. >>>>>>>>> >>>>>>>>> Oh, and yes, I've loaded upwards of 50-100 modules in development. >>>>>>>>> 20 >>>>>>>>> modules is *easy* to achieve in single-page apps. >>>>>>>>> >>>>>>>>> * This is, of course, not the case if you are using pure ES6 and >>>>>>>>> you >>>>>>>>> aren't using any plugins to, say, run the original source through >>>>>>>>> Babel for React + JSX or something. >>>>>>>>> >>>>>>>>> ----- >>>>>>>>> >>>>>>>>> Isiah Meadows >>>>>>>>> contact at isiahmeadows.com >>>>>>>>> www.isiahmeadows.com >>>>>>>>> On Sat, May 25, 2019 at 2:12 AM kai zhu <kaizhu256 at gmail.com> >>>>>>>>> wrote: >>>>>>>>> > >>>>>>>>> > Asynchronous loading differs only in >>>>>>>>> > that it takes more code to express the same logic and you have >>>>>>>>> to take >>>>>>>>> > into account concurrent requests (and you need to cache the >>>>>>>>> request, >>>>>>>>> > not the result), but it's otherwise the same from 1km away. >>>>>>>>> > >>>>>>>>> > >>>>>>>>> > so async-loading 50 ```<script type="module">``` tags >>>>>>>>> > has equivalent side-effect >>>>>>>>> > as sync-loading single webpack-rollup (of same 50 modules)? >>>>>>>>> > >>>>>>>>> > i have nagging suspicion of doubts. has anyone tried native >>>>>>>>> async-loading large numbers (>10) of >>>>>>>>> > ```<script type="module">``` tags, and verify it resolves >>>>>>>>> identically to using a single webpack-rollup? >>>>>>>>> > >>>>>>>>> > again, i'm not that knowledgeable on es-modules, so above >>>>>>>>> question may be trivially true, and i'm just not aware. >>>>>>>>> > >>>>>>>>> > -kai >>>>>>>>> > >>>>>>>>> > On 24 May 2019, at 23:41, Isiah Meadows <isiahmeadows at gmail.com> >>>>>>>>> wrote: >>>>>>>>> > >>>>>>>>> > There's two main reasons why it scales: >>>>>>>>> > >>>>>>>>> > 1. Modules are strongly encapsulated while minimizing global >>>>>>>>> pollution. >>>>>>>>> > 2. The resolution algorithm applies the same logic no matter how >>>>>>>>> many >>>>>>>>> > modules are loaded. >>>>>>>>> > >>>>>>>>> > It's much easier for it to scale when you write the code unaware >>>>>>>>> of >>>>>>>>> > how many modules you might be loading and unaware of how deep >>>>>>>>> their >>>>>>>>> > dependency graph is. Fewer assumptions here is key. It's an >>>>>>>>> > engineering problem, but a relatively simple one. >>>>>>>>> > >>>>>>>>> > If you want a short example of how sync module resolution works, >>>>>>>>> you >>>>>>>>> > can take a look at this little utility I wrote: >>>>>>>>> > https://github.com/isiahmeadows/simple-require-loader. That >>>>>>>>> doesn't >>>>>>>>> > asynchronously resolve modules, but it should help explain the >>>>>>>>> process >>>>>>>>> > from a synchronous standpoint. Asynchronous loading differs only >>>>>>>>> in >>>>>>>>> > that it takes more code to express the same logic and you have >>>>>>>>> to take >>>>>>>>> > into account concurrent requests (and you need to cache the >>>>>>>>> request, >>>>>>>>> > not the result), but it's otherwise the same from 1km away. >>>>>>>>> > >>>>>>>>> > ----- >>>>>>>>> > >>>>>>>>> > Isiah Meadows >>>>>>>>> > contact at isiahmeadows.com >>>>>>>>> > www.isiahmeadows.com >>>>>>>>> > >>>>>>>>> > On Thu, May 23, 2019 at 10:49 AM kai zhu <kaizhu256 at gmail.com> >>>>>>>>> wrote: >>>>>>>>> > >>>>>>>>> > >>>>>>>>> > actually, i admit i don't know what i'm talking about. just >>>>>>>>> generally confused (through ignorance) on how large-scale es-module >>>>>>>>> dependencies resolve when loaded/imported asynchronously. >>>>>>>>> > >>>>>>>>> > On Wed, May 22, 2019 at 10:42 PM Logan Smyth < >>>>>>>>> loganfsmyth at gmail.com> wrote: >>>>>>>>> > >>>>>>>>> > >>>>>>>>> > Can you elaborate on what loading state you need to keep track >>>>>>>>> of? What is the bottleneck that you run into? Also to be sure, when you say >>>>>>>>> async-load, do you mean `import()`? >>>>>>>>> > >>>>>>>>> > On Wed, May 22, 2019, 20:17 kai zhu <kaizhu256 at gmail.com> wrote: >>>>>>>>> > >>>>>>>>> > >>>>>>>>> > i don't use es-modules. >>>>>>>>> > but with amd/requirejs, I start having trouble with >>>>>>>>> module-initializations in nodejs/browser at ~5 async modules (that may or >>>>>>>>> may not have circular-references). 10 would be hard, and 20 would be near >>>>>>>>> inhuman for me. >>>>>>>>> > >>>>>>>>> > can we say its somewhat impractical for most applications to >>>>>>>>> load more than 50 async modules (with some of them having >>>>>>>>> circular-references)? and perhaps better design/spec module-loading >>>>>>>>> mechanisms with this usability concern in mind? >>>>>>>>> > >>>>>>>>> > p.s. its also impractical for me to async-load 5 or more modules >>>>>>>>> without using globalThis to keep track of each module's loading-state. >>>>>>>>> > _______________________________________________ >>>>>>>>> > es-discuss mailing list >>>>>>>>> > es-discuss at mozilla.org >>>>>>>>> > https://mail.mozilla.org/listinfo/es-discuss >>>>>>>>> > >>>>>>>>> > >>>>>>>>> > _______________________________________________ >>>>>>>>> > es-discuss mailing list >>>>>>>>> > es-discuss at mozilla.org >>>>>>>>> > https://mail.mozilla.org/listinfo/es-discuss >>>>>>>>> > >>>>>>>>> > >>>>>>>>> >>>>>>>> _______________________________________________ >>>>>>>> es-discuss mailing list >>>>>>>> es-discuss at mozilla.org >>>>>>>> https://mail.mozilla.org/listinfo/es-discuss >>>>>>>> >>>>>>> -------------- next part -------------- An HTML attachment was scrubbed... URL: <http://mail.mozilla.org/pipermail/es-discuss/attachments/20190601/4da73810/attachment-0001.html>
- original-question - is native es-module's async-behavior desirable? async side-effects are difficult to manage -- i conjecture that async-loading 20 es-modules (with dependent side-effects) is not practical for most mortals to handle.
It depends on what you mean by "desirable" in a given context.
There is no difference from loading 1 module and loading 1000 modules except for time, memory and disk space usage.
Mortals can handle far more than loading 20 es-modules.
What are the specific "side-effects" that you are referring to?
describes the mechanism for how to hint the brower to pre-fetch 20 es-modules. but if you pre-fetch, then is loading-behavior effectively synchronous?
Resources can be "pre-fetched" using various means. From caching the first
request and using the cached data instead of making future requests for the
same resources; localStorage
; storing one or more entire directories in the browser
configuration folder using requestFileSystem
(Chromium/Chrome); see also Native File System API WICG/native-file-system ("Expose the file system on the user’s device, so Web apps can interoperate with the user’s native applications.").
but was unclear whether they were individual [async]
<script type="module">
tags, or some es5-transpiled rollup
There should not be any difference between the two approaches. If there is a difference then you should be able to clearly state what the difference is, and demonstrate the difference by reproduction, without speculating and not demonstrating a difference by means of reproduction.
- the second-question about es-module rollups (which you and i are debating) stemmed from @isiah's response -- if he and everyone-else use es5-transpiled rollups (which i suspect),
Do not care what "everyone-else" is supposedly doing, here. How can you possibly know what everyone-else is doing and even if you did know what third-parties are doing how does that affect what you are doing?
then shouldn't it be desirable for es-modules to natively support rollups as well? currently, there's no way to natively rollup multiple es-modules into a single bundle.
There are ways to "bundle" multiple modules into a single export "natively", as demonstrated at the previously posted code.
Are you trying to use the same pattern that browserify browserify.org ("Browserify lets you require('modules') in the browser by bundling up all of your dependencies.") does?
If by "natively rollup multiple es-modules into a single bundle" you mean fetch various resources in a single file and export those resource in a single object you can fetch()
and export N resources as a single JavaScript plain object and process the object key, value pairs after importing the single Module
object.
// sync
const o = {
a:1, b:2, c:3
};
// async
const states = fetch("https://gist.githubusercontent.com/guest271314/ffac94353ab16f42160e/raw/aaee70a3e351f6c7bc00178eabb5970a02df87e9/states.json")
.then(response => response.json())
.catch(e => {console.error(e); return "error fetching states module"});
// async
const video = fetch("https://upload.wikimedia.org/wikipedia/commons/d/d9/120-cell.ogv")
.then(response => response.blob())
.catch(e => {console.error(e); return "error fetching video module"});
// multiple "modules" exported
export {o, states, video};
at single <script type="module">
<script type="module">
import * as o from "./script.js";
(async(mods) => {
for (const [key, value] of mods) {
if (value instanceof Promise) {
console.log("async module", key, await value)
} else {
console.log("sync module", key, value);
}
}
})(Object.entries(o));
// or
// Promise.all(Object.values(o)).then(console.log).catch(console.error)
</script>
Still there is no actual problem statement. Rather, there is conjecture without a definitive issue to solve.
> > 1) original-question - is native es-module's async-behavior desirable? > async side-effects are difficult to manage -- i conjecture that > async-loading 20 es-modules (with dependent side-effects) is not practical > for most mortals to handle. It depends on what *you *mean by "desirable" in a given context. There is no difference from loading 1 module and loading 1000 modules except for network cost, memory and disk space usage. Mortals can handle far more than loading 20 es-modules. What are the specific "side-effects" that you are referring to? describes the mechanism for how to hint the brower to pre-fetch 20 > es-modules. but if you pre-fetch, then is loading-behavior effectively > synchronous? Resources can be "pre-fetched" using various means. From caching the first request and using the cached data instead of making future requests for the same resources to storing one or more entire directories in the browser configuration folder using `requestFileSystem` (Chromiom/Chrome). but was unclear whether they were individual [async] ```<script > type="module">``` tags, or some es5-transpiled rollup There should not be any difference between the two approaches. If there is a difference then you should be able to clearly state what the difference is, and demonstrate the difference by reproduction, without speculating and not demonstrating a difference by means of reproduction. 2) the second-question about es-module rollups (which you and i are > debating) stemmed from @isiah's response -- if he and everyone-else use > es5-transpiled rollups (which i suspect), Do not care what "everyone-else" is supposedly doing. How can you possibly know what everyone-else is doing and even if you did know what third-parties are doing how does that affect what you are doing? then shouldn't it be desirable for es-modules to natively support rollups > as well? currently, there's no way to natively rollup multiple es-modules > into a single bundle. There are ways to "bundle" multiple modules into a single export "natively", as demonstrated at the previously posted code. Another example approach ``` // sync const o = { a:1, b:2, c:3 }; // async const cities = fetch(" https://gist.githubusercontent.com/guest271314/ffac94353ab16f42160e/raw/aaee70a3e351f6c7bc00178eabb5970a02df87e9/states.json ") .then(response => response.json()) .catch(e => {console.error(e); return "error fetching cities module"}); // async const video = fetch(" https://upload.wikimedia.org/wikipedia/commons/d/d9/120-cell.ogv") .then(response => response.blob()) .catch(e => {console.error(e); return "error fetching video module"}); // multiple "modules" exported export {o, cities, video}; ``` at single ```<script type="module">``` ``` <script type="module"> import * as o from "./script.js"; (async(mods) => { for (const [key, value] of mods) { if (value instanceof Promise) { console.log("async module", key, await value) } else { console.log("sync module", key, value); } } })(Object.entries(o)); </script> ``` Still there is no actual problem statement. Rather, there is conjecture without a definitive issue to solve. On Sun, Jun 2, 2019 at 3:54 AM kai zhu <kaizhu256 at gmail.com> wrote: > i apologize for poor framing of my questions. they are still formative, > but i can clarify abit as follows: > > 1) original-question - is native es-module's async-behavior desirable? > async side-effects are difficult to manage -- i conjecture that > async-loading 20 es-modules (with dependent side-effects) is not practical > for most mortals to handle. > @frederick describes the mechanism for how to hint the brower to pre-fetch > 20 es-modules. but if you pre-fetch, then is loading-behavior effectively > synchronous? > @isiah says he has experience loading 50-100 modules, but was unclear > whether they were individual [async] ```<script type="module">``` tags, > or some es5-transpiled rollup. > > i may be wrong about everything, as i'm a bit ignorant on what async > actually means in es-modules (and appreciate it, if someone can clarify > that). > > > > 2) the second-question about es-module rollups (which you and i are > debating) stemmed from @isiah's response -- if he and everyone-else use > es5-transpiled rollups (which i suspect), then shouldn't it be desirable > for es-modules to natively support rollups as well? currently, there's no > way to natively rollup multiple es-modules into a single bundle. > > this 2nd question also has implications about es-module's async-behavior > (because rollups "load" modules in sync/blocking fashion). this could > change side-effect behaviors between development-mode (20 [async] ```<script > type="module">``` tags) and production-mode (1 rollup-bundle). again, i > may be wrong about that, as i'm ignorant about what async actually is in > es-modules. > > -kai > > On Sat, Jun 1, 2019 at 9:22 PM guest271314 <guest271314 at gmail.com> wrote: > >> > it doesn't actually ```import``` 1000+ es-modules inside the >> rollup-file. it just creates one es-module that exports a dictionary -- and >> assigns the dictionary 1000+ vanilla json-objects and functions. >> >> The code provides a means to fetch N resources and export those resources >> within a single object. >> >> > currently, as i'm aware, nobody uses native es-modules in production, >> because it cannot be rolled-up. >> > in practice es-modules are [babel] transpiled down to es5-amd (or >> similar) for rollup-purposes. >> > >> > if we're actually committed to native es-modules, then we either >> > 1) need to depend on embedders like loading-dev at chromium.org to create >> sophisticated cache-systems, or >> > 2) introduce new language-syntax to delimit es-modules for >> rollup-purposes, e.g. >> >> You still have not clearly defined what you mean by "rolled-up". That >> language appears to be a random nickname, not any immutable principle that >> individuals are bound to recognize or observe (even if "rolled-up" were >> some form of a coding style or standard). >> >> Nor is it clear what you mean by "production". >> >> There is no external central committee that stamps code as "production". >> Even if there were no individual is obliged to submit to such a procedure >> nor have any concern for such an arbitrary and irrelevant presumptive >> review of code. >> >> The only observable points are input and output. In general, how output >> is achieved is immaterial. If there are specific restrictions as to how the >> output can be achieved then those restrictions need to be clearly defined. >> >> >> >> The original post asked "how many async-modules can js-app practically >> load?" and mentioned "circular-references" (the thread appears to mainly >> be about one or more coding styles, not code itself) though as yet no code >> has been posted which demonstrates "circular-references" or any other >> coding problem. >> >> On Sun, Jun 2, 2019 at 1:30 AM kai zhu <kaizhu256 at gmail.com> wrote: >> >>> i played around with your code in jsfiddle [1], and understand it a >>> little more. >>> it doesn't actually ```import``` 1000+ es-modules inside the >>> rollup-file. >>> it just creates one es-module that exports a dictionary >>> -- and assigns the dictionary 1000+ vanilla json-objects and functions. >>> >>> ```js >>> // the "rollup-file" is a single es-module >>> // that exports 1000+ vanilla dictionary-entries >>> const modules = {}; >>> >>> // this is not a es-module, nor is it rolled-up (external fetch) >>> modules.image = <await fetch json from gist.github.com> >>> >>> // this is not a [rolled-up] es-module >>> modules.fn = function () {...} >>> >>> // these are not [rolled-up] es-modules >>> Object.assign(modules, <1000 json-entries>) >>> >>> export {modules} >>> ``` >>> >>> currently, as i'm aware, nobody uses native es-modules in production, >>> because it cannot be rolled-up. >>> in practice es-modules are [babel] transpiled down to es5-amd (or >>> similar) for rollup-purposes. >>> >>> if we're actually committed to native es-modules, then we either >>> 1) need to depend on embedders like loading-dev at chromium.org to create >>> sophisticated cache-systems, or >>> 2) introduce new language-syntax to delimit es-modules for >>> rollup-purposes, e.g. >>> >>> ```js >>> // rollup.js with [hypothetical] # delimited es-modules >>> # module aa >>> import {bb} as bb; >>> export ...; >>> >>> # module bb >>> export ...; >>> ``` >>> >>> i'm generally skeptical of option 1, given how poorly npmjs.com has >>> handled similar problems deduplicating children in node_modules/ directory. >>> >>> [1] jsfiddle pseudo-module rollup >>> https://jsfiddle.net/06twrLfd/ >>> >>> On Sat, Jun 1, 2019 at 5:30 PM guest271314 <guest271314 at gmail.com> >>> wrote: >>> >>>> > your rollup solution is interesting, >>>> >>>> What is "rollup" referring to? >>>> >>>> > but i get an error when run in chrome (i changed to n=20 to prevent >>>> name-collision, but it still happens). >>>> >>>> The duplicate ("collision") entry an ```try..catch``` block is included >>>> in the code to demonstrate given an array of module names to be exported >>>> and imported as identifiers 1) duplicate entries can be filtered; 2) if a >>>> plain object is exported duplicate identifiers ("collision") is not >>>> possible as a JavaScript plain object does not have duplicate property >>>> names ("collision"); if there is an issue with identifiers in a module the >>>> cause would not be the number of async-modules loaded ("how many"), but the >>>> naming of the identifiers within the code, using or not using ```const``` >>>> or ```let```. Still not sure what the actual issue is? >>>> >>>> > don't completely understand how it works, >>>> >>>> Use an ```async``` function to fetch data, check for the described >>>> "collision" , create a ```data URI``` to be imported, optionally, append >>>> addition code to be executed within the ```<script type="module">```. >>>> >>>> > but not sure of suitability for production-use, because of its >>>> dynamic <script> tag generation. >>>> >>>> What is the issue with dynamic ```<script>``` tag generation? >>>> >>>> There is more than one possible approach to achieve the presumptive >>>> requirement, that is still not clear to the exclusion of what is not the >>>> expected result. >>>> >>>> There were no restrictions described at the OP and following messages >>>> other than other than >>>> >>>> > pure-es6 application with 20 es-modules rolled-up into one >>>> [production] bundle? >>>> >>>> The example code uses only JavaScript implementation shipped with the >>>> browser without any external, third-party libraries. >>>> >>>> What standard or definition are you relying for the meaning of the term >>>> "production-use"? What procedure are you using to determine if code is >>>> "production-use" "suitable"? How is that procedure related to "how many >>>> async-modules can js-app practically load?"? >>>> >>>> >>>> >>>> On Sat, Jun 1, 2019 at 9:42 PM kai zhu <kaizhu256 at gmail.com> wrote: >>>> >>>>> your rollup solution is interesting, but i get an error when run in >>>>> chrome (i changed to n=20 to prevent name-collision, but it still >>>>> happens). don't completely understand how it works, but not sure of >>>>> suitability for production-use, because of its dynamic <script> tag >>>>> generation. >>>>> >>>>> ```console >>>>> ReferenceError: module names ["yeqjqb02mvg3yze26rc5"] are not unique >>>>> at >>>>> data:application/javascript,%0A%20%20%20%20%20%20const%20modules... >>>>> ``` >>>>> >>>>> On Sat, Jun 1, 2019 at 2:33 PM guest271314 <guest271314 at gmail.com> >>>>> wrote: >>>>> >>>>>> Re: how many async-modules can js-app practically load? >>>>>> >>>>>> An example of exporting and importing loading 1000 properties in a >>>>>> single module, where duplicate property names are checked for. Since >>>>>> JavaScript plain objects cannot have duplicate property names there should >>>>>> not be any "collisions"; the code can check for and modify the object to be >>>>>> exported, though the last duplicate property name will be exported without >>>>>> any errors thrown unless the code is composed to throw such an error. >>>>>> >>>>>> ``` >>>>>> (async() => { >>>>>> const oneThousandModules = encodeURIComponent( >>>>>> // substitute rand for a Set of module names to be exported >>>>>> // e.g. const moduleNames = ['moduleA', 'moduleB', ...moduleZ] >>>>>> ` >>>>>> const modules = {}; >>>>>> // set a function to be exported >>>>>> modules.fn = function() {return 'a function'}; >>>>>> // function to set (1000) 'random' module names to be exported >>>>>> const rand = (seed = 'abcdefghijklmnopqrstuvwxyz0123456789', n >>>>>> = 5, len = seed.length) => >>>>>> '.'.repeat(n).replace(/./g, _ => seed[~~(Math.random() * >>>>>> len)]); >>>>>> // use Set for unique module identifiers >>>>>> const moduleNames = [...Array(1000)].map(_ => rand()); >>>>>> const moduleIdentifiers = new Set(moduleNames); >>>>>> // below line will cause ReferenceError to be thrown >>>>>> moduleNames.push(moduleNames[0]); >>>>>> try { >>>>>> if (moduleIdentifiers.size !== moduleNames.length) { >>>>>> // check for duplicates >>>>>> const duplicates = moduleNames.filter((moduleName, index) >>>>>> => moduleNames.indexOf(moduleName) !== index); >>>>>> // notification of duplicate module names >>>>>> throw new ReferenceError('module names ' + >>>>>> JSON.stringify(duplicates) + ' are not unique'); >>>>>> // perform the designated task if duplicate module names >>>>>> are found here >>>>>> } >>>>>> } catch (e) { >>>>>> console.error(e); >>>>>> console.trace(); >>>>>> } >>>>>> // get, set (sync or async) exported module here >>>>>> Object.assign(modules, ...[...moduleIdentifiers].map((id, >>>>>> value) => ({[id]:value}))); >>>>>> // since JavaScript plain object cannot have duplicate >>>>>> property names >>>>>> // modules object will still be exported without duplicate >>>>>> property names >>>>>> // without collisions >>>>>> export {modules} >>>>>> `); >>>>>> const scriptText = `import {modules} from >>>>>> "data:application/javascript,${oneThousandModules};${encodeURIComponent('console.log(modules);for >>>>>> (const key in modules) {if (typeof modules[key] === \'function\') >>>>>> {console.log(modules[key]());}}')}"`; >>>>>> const script = document.createElement("script"); >>>>>> script.type = "module"; >>>>>> script.textContent = scriptText; >>>>>> document.head.appendChild(script); >>>>>> })(); >>>>>> ``` >>>>>> >>>>>> plnkr https://plnkr.co/edit/CgEhBY?p=preview >>>>>> >>>>>> On Sat, Jun 1, 2019 at 1:51 AM kai zhu <kaizhu256 at gmail.com> wrote: >>>>>> >>>>>>> > Place all of the code to be exported in 1 file? >>>>>>> >>>>>>> that obviously will not work, because of module-scope collision. >>>>>>> can anyone share their experience on deploying a [babel-free] pure-es6 >>>>>>> application with 20 es-modules rolled-up into one [production] bundle? is >>>>>>> it even possible? >>>>>>> >>>>>>> >>>>>>> On Fri, May 31, 2019 at 7:55 PM guest271314 <guest271314 at gmail.com> >>>>>>> wrote: >>>>>>> >>>>>>>> > how would i transition from development-mode (20 es-module >>>>>>>> files) -> production-mode (1 rollup file)? >>>>>>>> >>>>>>>> Place all of the code to be exported in 1 file? >>>>>>>> >>>>>>>> > with some of them having circular-references >>>>>>>> >>>>>>>> Not certain how that is possible when using ```import``` within >>>>>>>> ```<script type="module">```? >>>>>>>> >>>>>>>> > how many async-modules can js-app practically load? >>>>>>>> >>>>>>>> Again, how many have you tried to load? 100? 500? 1000? Either >>>>>>>> should be possible. >>>>>>>> >>>>>>>> What specific issue are you actually to resolve? >>>>>>>> >>>>>>>> On Fri, May 31, 2019 at 5:40 PM kai zhu <kaizhu256 at gmail.com> >>>>>>>> wrote: >>>>>>>> >>>>>>>>> > Oh, and yes, I've loaded upwards of 50-100 modules in >>>>>>>>> development. 20 >>>>>>>>> modules is *easy* to achieve in single-page apps. >>>>>>>>> >>>>>>>>> was that with some combination of babel/rollup/webpack or pure-es6? >>>>>>>>> if i want to develop a pure-es6 webapp (no babel), how would i >>>>>>>>> transition from development-mode (20 es-module files) -> production-mode (1 >>>>>>>>> rollup file)? >>>>>>>>> >>>>>>>>> >>>>>>>>> On Fri, May 31, 2019 at 10:47 AM Isiah Meadows < >>>>>>>>> isiahmeadows at gmail.com> wrote: >>>>>>>>> >>>>>>>>>> If it's bundled by Rollup or Webpack into a single bundle, it's >>>>>>>>>> equivalent to a single `<script type="module" src="...">` pointing >>>>>>>>>> towards the original entry point, excluding network requests.* >>>>>>>>>> But in >>>>>>>>>> either case, you aren't listing 50 scripts, you're only listing >>>>>>>>>> the >>>>>>>>>> entry module and importing child modules within parent modules. >>>>>>>>>> Rollup >>>>>>>>>> and Webpack do mostly the same thing browsers do when it comes to >>>>>>>>>> resolving dependencies, just they generate a bundle afterwards >>>>>>>>>> where >>>>>>>>>> browsers execute code afterwards. Also, it's worth noting that >>>>>>>>>> the gap >>>>>>>>>> between a single large request and multiple smaller requests has >>>>>>>>>> shrunk a lot since HTTP/2 came along, since it's binary, it allows >>>>>>>>>> requests and response data to be interleaved, it better leverages >>>>>>>>>> the >>>>>>>>>> underlying TCP protocol format, and it allows servers to send data >>>>>>>>>> pre-emptively without the client requesting it first. (Web >>>>>>>>>> sockets are >>>>>>>>>> built on this functionality.) It's still better to bundle in >>>>>>>>>> general, >>>>>>>>>> but it's less of a problem not to. >>>>>>>>>> >>>>>>>>>> This is *not* the case for `<script type="module">` elements - >>>>>>>>>> those >>>>>>>>>> operate more like inline scripts that happen to have the ability >>>>>>>>>> to >>>>>>>>>> `import`. >>>>>>>>>> >>>>>>>>>> Oh, and yes, I've loaded upwards of 50-100 modules in >>>>>>>>>> development. 20 >>>>>>>>>> modules is *easy* to achieve in single-page apps. >>>>>>>>>> >>>>>>>>>> * This is, of course, not the case if you are using pure ES6 and >>>>>>>>>> you >>>>>>>>>> aren't using any plugins to, say, run the original source through >>>>>>>>>> Babel for React + JSX or something. >>>>>>>>>> >>>>>>>>>> ----- >>>>>>>>>> >>>>>>>>>> Isiah Meadows >>>>>>>>>> contact at isiahmeadows.com >>>>>>>>>> www.isiahmeadows.com >>>>>>>>>> On Sat, May 25, 2019 at 2:12 AM kai zhu <kaizhu256 at gmail.com> >>>>>>>>>> wrote: >>>>>>>>>> > >>>>>>>>>> > Asynchronous loading differs only in >>>>>>>>>> > that it takes more code to express the same logic and you have >>>>>>>>>> to take >>>>>>>>>> > into account concurrent requests (and you need to cache the >>>>>>>>>> request, >>>>>>>>>> > not the result), but it's otherwise the same from 1km away. >>>>>>>>>> > >>>>>>>>>> > >>>>>>>>>> > so async-loading 50 ```<script type="module">``` tags >>>>>>>>>> > has equivalent side-effect >>>>>>>>>> > as sync-loading single webpack-rollup (of same 50 modules)? >>>>>>>>>> > >>>>>>>>>> > i have nagging suspicion of doubts. has anyone tried native >>>>>>>>>> async-loading large numbers (>10) of >>>>>>>>>> > ```<script type="module">``` tags, and verify it resolves >>>>>>>>>> identically to using a single webpack-rollup? >>>>>>>>>> > >>>>>>>>>> > again, i'm not that knowledgeable on es-modules, so above >>>>>>>>>> question may be trivially true, and i'm just not aware. >>>>>>>>>> > >>>>>>>>>> > -kai >>>>>>>>>> > >>>>>>>>>> > On 24 May 2019, at 23:41, Isiah Meadows <isiahmeadows at gmail.com> >>>>>>>>>> wrote: >>>>>>>>>> > >>>>>>>>>> > There's two main reasons why it scales: >>>>>>>>>> > >>>>>>>>>> > 1. Modules are strongly encapsulated while minimizing global >>>>>>>>>> pollution. >>>>>>>>>> > 2. The resolution algorithm applies the same logic no matter >>>>>>>>>> how many >>>>>>>>>> > modules are loaded. >>>>>>>>>> > >>>>>>>>>> > It's much easier for it to scale when you write the code >>>>>>>>>> unaware of >>>>>>>>>> > how many modules you might be loading and unaware of how deep >>>>>>>>>> their >>>>>>>>>> > dependency graph is. Fewer assumptions here is key. It's an >>>>>>>>>> > engineering problem, but a relatively simple one. >>>>>>>>>> > >>>>>>>>>> > If you want a short example of how sync module resolution >>>>>>>>>> works, you >>>>>>>>>> > can take a look at this little utility I wrote: >>>>>>>>>> > https://github.com/isiahmeadows/simple-require-loader. That >>>>>>>>>> doesn't >>>>>>>>>> > asynchronously resolve modules, but it should help explain the >>>>>>>>>> process >>>>>>>>>> > from a synchronous standpoint. Asynchronous loading differs >>>>>>>>>> only in >>>>>>>>>> > that it takes more code to express the same logic and you have >>>>>>>>>> to take >>>>>>>>>> > into account concurrent requests (and you need to cache the >>>>>>>>>> request, >>>>>>>>>> > not the result), but it's otherwise the same from 1km away. >>>>>>>>>> > >>>>>>>>>> > ----- >>>>>>>>>> > >>>>>>>>>> > Isiah Meadows >>>>>>>>>> > contact at isiahmeadows.com >>>>>>>>>> > www.isiahmeadows.com >>>>>>>>>> > >>>>>>>>>> > On Thu, May 23, 2019 at 10:49 AM kai zhu <kaizhu256 at gmail.com> >>>>>>>>>> wrote: >>>>>>>>>> > >>>>>>>>>> > >>>>>>>>>> > actually, i admit i don't know what i'm talking about. just >>>>>>>>>> generally confused (through ignorance) on how large-scale es-module >>>>>>>>>> dependencies resolve when loaded/imported asynchronously. >>>>>>>>>> > >>>>>>>>>> > On Wed, May 22, 2019 at 10:42 PM Logan Smyth < >>>>>>>>>> loganfsmyth at gmail.com> wrote: >>>>>>>>>> > >>>>>>>>>> > >>>>>>>>>> > Can you elaborate on what loading state you need to keep track >>>>>>>>>> of? What is the bottleneck that you run into? Also to be sure, when you say >>>>>>>>>> async-load, do you mean `import()`? >>>>>>>>>> > >>>>>>>>>> > On Wed, May 22, 2019, 20:17 kai zhu <kaizhu256 at gmail.com> >>>>>>>>>> wrote: >>>>>>>>>> > >>>>>>>>>> > >>>>>>>>>> > i don't use es-modules. >>>>>>>>>> > but with amd/requirejs, I start having trouble with >>>>>>>>>> module-initializations in nodejs/browser at ~5 async modules (that may or >>>>>>>>>> may not have circular-references). 10 would be hard, and 20 would be near >>>>>>>>>> inhuman for me. >>>>>>>>>> > >>>>>>>>>> > can we say its somewhat impractical for most applications to >>>>>>>>>> load more than 50 async modules (with some of them having >>>>>>>>>> circular-references)? and perhaps better design/spec module-loading >>>>>>>>>> mechanisms with this usability concern in mind? >>>>>>>>>> > >>>>>>>>>> > p.s. its also impractical for me to async-load 5 or more >>>>>>>>>> modules without using globalThis to keep track of each module's >>>>>>>>>> loading-state. >>>>>>>>>> > _______________________________________________ >>>>>>>>>> > es-discuss mailing list >>>>>>>>>> > es-discuss at mozilla.org >>>>>>>>>> > https://mail.mozilla.org/listinfo/es-discuss >>>>>>>>>> > >>>>>>>>>> > >>>>>>>>>> > _______________________________________________ >>>>>>>>>> > es-discuss mailing list >>>>>>>>>> > es-discuss at mozilla.org >>>>>>>>>> > https://mail.mozilla.org/listinfo/es-discuss >>>>>>>>>> > >>>>>>>>>> > >>>>>>>>>> >>>>>>>>> _______________________________________________ >>>>>>>>> es-discuss mailing list >>>>>>>>> es-discuss at mozilla.org >>>>>>>>> https://mail.mozilla.org/listinfo/es-discuss >>>>>>>>> >>>>>>>> -------------- next part -------------- An HTML attachment was scrubbed... URL: <http://mail.mozilla.org/pipermail/es-discuss/attachments/20190602/3f0e899d/attachment-0001.html>
@guest271314 <guest271314 at gmail.com>, your example again is not a [native]
bundle of two or more inlined es-modules. its just a single es-module that that fetches json data.
i'm asking if its desirable to inline multiple es-modules into a single file natively, e.g.:
/*
* es-module.rollup.js
* this [hypothetical] rollup-file contains multiple inlined es-modules
* to improve load-performance in production-deployment.
*/
// 1. inlined es-module ./main.js
import { foo } from "./counter.js"
import { bar } from "./display.js"
foo(bar);
// 2. inlined es-module ./counter.js
var foo;
foo = function (bar) {
bar();
};
export { foo }
// 3. inlined es-module ./display.js
var bar;
bar = function () {
console.log("hello world");
};
export { bar }
this native es-module inline-capability may not be desirable to you, which is fine. it would be a datapoint against this feature (and rely instead on pre-emptive import-maps and http2-push, as explained by @frederick and @isiah).
@guest271314 <guest271314 at gmail.com>, your example again is not a [native] bundle of two or more inlined es-modules. its just a single es-module that that fetches json data. i'm asking if its desirable to inline multiple es-modules into a single file natively, e.g.: ``` /* * es-module.rollup.js * this [hypothetical] rollup-file contains multiple inlined es-modules * to improve load-performance in production-deployment. */ // 1. inlined es-module ./main.js import { foo } from "./counter.js" import { bar } from "./display.js" foo(bar); // 2. inlined es-module ./counter.js var foo; foo = function (bar) { bar(); }; export { foo } // 3. inlined es-module ./display.js var bar; bar = function () { console.log("hello world"); }; export { bar } ``` this native es-module inline-capability may not be desirable to you, which is fine. it would be a datapoint against this feature (and rely instead on pre-emptive import-maps and http2-push, as explained by @frederick and @isiah). On Sun, Jun 2, 2019 at 11:22 AM guest271314 <guest271314 at gmail.com> wrote: > 1) original-question - is native es-module's async-behavior desirable? >> async side-effects are difficult to manage -- i conjecture that >> async-loading 20 es-modules (with dependent side-effects) is not practical >> for most mortals to handle. > > > It depends on what *you *mean by "desirable" in a given context. > > There is no difference from loading 1 module and loading 1000 modules > except for network cost, memory and disk space usage. > > Mortals can handle far more than loading 20 es-modules. > > What are the specific "side-effects" that you are referring to? > > describes the mechanism for how to hint the brower to pre-fetch 20 >> es-modules. but if you pre-fetch, then is loading-behavior effectively >> synchronous? > > > Resources can be "pre-fetched" using various means. From caching the first > request and using the cached data instead of making future requests for the > same resources to storing one or more entire directories in the browser > configuration folder using `requestFileSystem` (Chromiom/Chrome). > > but was unclear whether they were individual [async] ```<script >> type="module">``` tags, or some es5-transpiled rollup > > > There should not be any difference between the two approaches. If there is > a difference then you should be able to clearly state what the difference > is, and demonstrate the difference by reproduction, without speculating and > not demonstrating a difference by means of reproduction. > > 2) the second-question about es-module rollups (which you and i are >> debating) stemmed from @isiah's response -- if he and everyone-else use >> es5-transpiled rollups (which i suspect), > > > Do not care what "everyone-else" is supposedly doing. How can you possibly > know what everyone-else is doing and even if you did know what > third-parties are doing how does that affect what you are doing? > > then shouldn't it be desirable for es-modules to natively support rollups >> as well? currently, there's no way to natively rollup multiple es-modules >> into a single bundle. > > > There are ways to "bundle" multiple modules into a single export > "natively", as demonstrated at the previously posted code. > > Another example approach > > ``` > // sync > const o = { > a:1, b:2, c:3 > }; > // async > const cities = fetch(" > https://gist.githubusercontent.com/guest271314/ffac94353ab16f42160e/raw/aaee70a3e351f6c7bc00178eabb5970a02df87e9/states.json > ") > .then(response => response.json()) > .catch(e => {console.error(e); return "error fetching > cities module"}); > // async > const video = fetch(" > https://upload.wikimedia.org/wikipedia/commons/d/d9/120-cell.ogv") > .then(response => response.blob()) > .catch(e => {console.error(e); return "error fetching video > module"}); > // multiple "modules" exported > export {o, cities, video}; > ``` > > at single ```<script type="module">``` > > ``` > <script type="module"> > import * as o from "./script.js"; > (async(mods) => { > for (const [key, value] of mods) { > if (value instanceof Promise) { > console.log("async module", key, await value) > } else { > console.log("sync module", key, value); > } > } > })(Object.entries(o)); > </script> > ``` > > Still there is no actual problem statement. Rather, there is conjecture > without a definitive issue to solve. > > > > > On Sun, Jun 2, 2019 at 3:54 AM kai zhu <kaizhu256 at gmail.com> wrote: > >> i apologize for poor framing of my questions. they are still formative, >> but i can clarify abit as follows: >> >> 1) original-question - is native es-module's async-behavior desirable? >> async side-effects are difficult to manage -- i conjecture that >> async-loading 20 es-modules (with dependent side-effects) is not practical >> for most mortals to handle. >> @frederick describes the mechanism for how to hint the brower to >> pre-fetch 20 es-modules. but if you pre-fetch, then is loading-behavior >> effectively synchronous? >> @isiah says he has experience loading 50-100 modules, but was unclear >> whether they were individual [async] ```<script type="module">``` tags, >> or some es5-transpiled rollup. >> >> i may be wrong about everything, as i'm a bit ignorant on what async >> actually means in es-modules (and appreciate it, if someone can clarify >> that). >> >> >> >> 2) the second-question about es-module rollups (which you and i are >> debating) stemmed from @isiah's response -- if he and everyone-else use >> es5-transpiled rollups (which i suspect), then shouldn't it be desirable >> for es-modules to natively support rollups as well? currently, there's no >> way to natively rollup multiple es-modules into a single bundle. >> >> this 2nd question also has implications about es-module's async-behavior >> (because rollups "load" modules in sync/blocking fashion). this could >> change side-effect behaviors between development-mode (20 [async] ```<script >> type="module">``` tags) and production-mode (1 rollup-bundle). again, i >> may be wrong about that, as i'm ignorant about what async actually is in >> es-modules. >> >> -kai >> >> On Sat, Jun 1, 2019 at 9:22 PM guest271314 <guest271314 at gmail.com> wrote: >> >>> > it doesn't actually ```import``` 1000+ es-modules inside the >>> rollup-file. it just creates one es-module that exports a dictionary -- and >>> assigns the dictionary 1000+ vanilla json-objects and functions. >>> >>> The code provides a means to fetch N resources and export those >>> resources within a single object. >>> >>> > currently, as i'm aware, nobody uses native es-modules in production, >>> because it cannot be rolled-up. >>> > in practice es-modules are [babel] transpiled down to es5-amd (or >>> similar) for rollup-purposes. >>> > >>> > if we're actually committed to native es-modules, then we either >>> > 1) need to depend on embedders like loading-dev at chromium.org to >>> create sophisticated cache-systems, or >>> > 2) introduce new language-syntax to delimit es-modules for >>> rollup-purposes, e.g. >>> >>> You still have not clearly defined what you mean by "rolled-up". That >>> language appears to be a random nickname, not any immutable principle that >>> individuals are bound to recognize or observe (even if "rolled-up" were >>> some form of a coding style or standard). >>> >>> Nor is it clear what you mean by "production". >>> >>> There is no external central committee that stamps code as "production". >>> Even if there were no individual is obliged to submit to such a procedure >>> nor have any concern for such an arbitrary and irrelevant presumptive >>> review of code. >>> >>> The only observable points are input and output. In general, how output >>> is achieved is immaterial. If there are specific restrictions as to how the >>> output can be achieved then those restrictions need to be clearly defined. >>> >>> >>> >>> The original post asked "how many async-modules can js-app practically >>> load?" and mentioned "circular-references" (the thread appears to >>> mainly be about one or more coding styles, not code itself) though as yet >>> no code has been posted which demonstrates "circular-references" or any >>> other coding problem. >>> >>> On Sun, Jun 2, 2019 at 1:30 AM kai zhu <kaizhu256 at gmail.com> wrote: >>> >>>> i played around with your code in jsfiddle [1], and understand it a >>>> little more. >>>> it doesn't actually ```import``` 1000+ es-modules inside the >>>> rollup-file. >>>> it just creates one es-module that exports a dictionary >>>> -- and assigns the dictionary 1000+ vanilla json-objects and functions. >>>> >>>> ```js >>>> // the "rollup-file" is a single es-module >>>> // that exports 1000+ vanilla dictionary-entries >>>> const modules = {}; >>>> >>>> // this is not a es-module, nor is it rolled-up (external fetch) >>>> modules.image = <await fetch json from gist.github.com> >>>> >>>> // this is not a [rolled-up] es-module >>>> modules.fn = function () {...} >>>> >>>> // these are not [rolled-up] es-modules >>>> Object.assign(modules, <1000 json-entries>) >>>> >>>> export {modules} >>>> ``` >>>> >>>> currently, as i'm aware, nobody uses native es-modules in production, >>>> because it cannot be rolled-up. >>>> in practice es-modules are [babel] transpiled down to es5-amd (or >>>> similar) for rollup-purposes. >>>> >>>> if we're actually committed to native es-modules, then we either >>>> 1) need to depend on embedders like loading-dev at chromium.org to create >>>> sophisticated cache-systems, or >>>> 2) introduce new language-syntax to delimit es-modules for >>>> rollup-purposes, e.g. >>>> >>>> ```js >>>> // rollup.js with [hypothetical] # delimited es-modules >>>> # module aa >>>> import {bb} as bb; >>>> export ...; >>>> >>>> # module bb >>>> export ...; >>>> ``` >>>> >>>> i'm generally skeptical of option 1, given how poorly npmjs.com has >>>> handled similar problems deduplicating children in node_modules/ directory. >>>> >>>> [1] jsfiddle pseudo-module rollup >>>> https://jsfiddle.net/06twrLfd/ >>>> >>>> On Sat, Jun 1, 2019 at 5:30 PM guest271314 <guest271314 at gmail.com> >>>> wrote: >>>> >>>>> > your rollup solution is interesting, >>>>> >>>>> What is "rollup" referring to? >>>>> >>>>> > but i get an error when run in chrome (i changed to n=20 to prevent >>>>> name-collision, but it still happens). >>>>> >>>>> The duplicate ("collision") entry an ```try..catch``` block is >>>>> included in the code to demonstrate given an array of module names to be >>>>> exported and imported as identifiers 1) duplicate entries can be filtered; >>>>> 2) if a plain object is exported duplicate identifiers ("collision") is not >>>>> possible as a JavaScript plain object does not have duplicate property >>>>> names ("collision"); if there is an issue with identifiers in a module the >>>>> cause would not be the number of async-modules loaded ("how many"), but the >>>>> naming of the identifiers within the code, using or not using ```const``` >>>>> or ```let```. Still not sure what the actual issue is? >>>>> >>>>> > don't completely understand how it works, >>>>> >>>>> Use an ```async``` function to fetch data, check for the described >>>>> "collision" , create a ```data URI``` to be imported, optionally, append >>>>> addition code to be executed within the ```<script type="module">```. >>>>> >>>>> > but not sure of suitability for production-use, because of its >>>>> dynamic <script> tag generation. >>>>> >>>>> What is the issue with dynamic ```<script>``` tag generation? >>>>> >>>>> There is more than one possible approach to achieve the presumptive >>>>> requirement, that is still not clear to the exclusion of what is not the >>>>> expected result. >>>>> >>>>> There were no restrictions described at the OP and following messages >>>>> other than other than >>>>> >>>>> > pure-es6 application with 20 es-modules rolled-up into one >>>>> [production] bundle? >>>>> >>>>> The example code uses only JavaScript implementation shipped with the >>>>> browser without any external, third-party libraries. >>>>> >>>>> What standard or definition are you relying for the meaning of the >>>>> term "production-use"? What procedure are you using to determine if code is >>>>> "production-use" "suitable"? How is that procedure related to "how many >>>>> async-modules can js-app practically load?"? >>>>> >>>>> >>>>> >>>>> On Sat, Jun 1, 2019 at 9:42 PM kai zhu <kaizhu256 at gmail.com> wrote: >>>>> >>>>>> your rollup solution is interesting, but i get an error when run in >>>>>> chrome (i changed to n=20 to prevent name-collision, but it still >>>>>> happens). don't completely understand how it works, but not sure of >>>>>> suitability for production-use, because of its dynamic <script> tag >>>>>> generation. >>>>>> >>>>>> ```console >>>>>> ReferenceError: module names ["yeqjqb02mvg3yze26rc5"] are not unique >>>>>> at >>>>>> data:application/javascript,%0A%20%20%20%20%20%20const%20modules... >>>>>> ``` >>>>>> >>>>>> On Sat, Jun 1, 2019 at 2:33 PM guest271314 <guest271314 at gmail.com> >>>>>> wrote: >>>>>> >>>>>>> Re: how many async-modules can js-app practically load? >>>>>>> >>>>>>> An example of exporting and importing loading 1000 properties in a >>>>>>> single module, where duplicate property names are checked for. Since >>>>>>> JavaScript plain objects cannot have duplicate property names there should >>>>>>> not be any "collisions"; the code can check for and modify the object to be >>>>>>> exported, though the last duplicate property name will be exported without >>>>>>> any errors thrown unless the code is composed to throw such an error. >>>>>>> >>>>>>> ``` >>>>>>> (async() => { >>>>>>> const oneThousandModules = encodeURIComponent( >>>>>>> // substitute rand for a Set of module names to be exported >>>>>>> // e.g. const moduleNames = ['moduleA', 'moduleB', ...moduleZ] >>>>>>> ` >>>>>>> const modules = {}; >>>>>>> // set a function to be exported >>>>>>> modules.fn = function() {return 'a function'}; >>>>>>> // function to set (1000) 'random' module names to be exported >>>>>>> const rand = (seed = 'abcdefghijklmnopqrstuvwxyz0123456789', n >>>>>>> = 5, len = seed.length) => >>>>>>> '.'.repeat(n).replace(/./g, _ => seed[~~(Math.random() * >>>>>>> len)]); >>>>>>> // use Set for unique module identifiers >>>>>>> const moduleNames = [...Array(1000)].map(_ => rand()); >>>>>>> const moduleIdentifiers = new Set(moduleNames); >>>>>>> // below line will cause ReferenceError to be thrown >>>>>>> moduleNames.push(moduleNames[0]); >>>>>>> try { >>>>>>> if (moduleIdentifiers.size !== moduleNames.length) { >>>>>>> // check for duplicates >>>>>>> const duplicates = moduleNames.filter((moduleName, >>>>>>> index) => moduleNames.indexOf(moduleName) !== index); >>>>>>> // notification of duplicate module names >>>>>>> throw new ReferenceError('module names ' + >>>>>>> JSON.stringify(duplicates) + ' are not unique'); >>>>>>> // perform the designated task if duplicate module names >>>>>>> are found here >>>>>>> } >>>>>>> } catch (e) { >>>>>>> console.error(e); >>>>>>> console.trace(); >>>>>>> } >>>>>>> // get, set (sync or async) exported module here >>>>>>> Object.assign(modules, ...[...moduleIdentifiers].map((id, >>>>>>> value) => ({[id]:value}))); >>>>>>> // since JavaScript plain object cannot have duplicate >>>>>>> property names >>>>>>> // modules object will still be exported without duplicate >>>>>>> property names >>>>>>> // without collisions >>>>>>> export {modules} >>>>>>> `); >>>>>>> const scriptText = `import {modules} from >>>>>>> "data:application/javascript,${oneThousandModules};${encodeURIComponent('console.log(modules);for >>>>>>> (const key in modules) {if (typeof modules[key] === \'function\') >>>>>>> {console.log(modules[key]());}}')}"`; >>>>>>> const script = document.createElement("script"); >>>>>>> script.type = "module"; >>>>>>> script.textContent = scriptText; >>>>>>> document.head.appendChild(script); >>>>>>> })(); >>>>>>> ``` >>>>>>> >>>>>>> plnkr https://plnkr.co/edit/CgEhBY?p=preview >>>>>>> >>>>>>> On Sat, Jun 1, 2019 at 1:51 AM kai zhu <kaizhu256 at gmail.com> wrote: >>>>>>> >>>>>>>> > Place all of the code to be exported in 1 file? >>>>>>>> >>>>>>>> that obviously will not work, because of module-scope collision. >>>>>>>> can anyone share their experience on deploying a [babel-free] pure-es6 >>>>>>>> application with 20 es-modules rolled-up into one [production] bundle? is >>>>>>>> it even possible? >>>>>>>> >>>>>>>> >>>>>>>> On Fri, May 31, 2019 at 7:55 PM guest271314 <guest271314 at gmail.com> >>>>>>>> wrote: >>>>>>>> >>>>>>>>> > how would i transition from development-mode (20 es-module >>>>>>>>> files) -> production-mode (1 rollup file)? >>>>>>>>> >>>>>>>>> Place all of the code to be exported in 1 file? >>>>>>>>> >>>>>>>>> > with some of them having circular-references >>>>>>>>> >>>>>>>>> Not certain how that is possible when using ```import``` within >>>>>>>>> ```<script type="module">```? >>>>>>>>> >>>>>>>>> > how many async-modules can js-app practically load? >>>>>>>>> >>>>>>>>> Again, how many have you tried to load? 100? 500? 1000? Either >>>>>>>>> should be possible. >>>>>>>>> >>>>>>>>> What specific issue are you actually to resolve? >>>>>>>>> >>>>>>>>> On Fri, May 31, 2019 at 5:40 PM kai zhu <kaizhu256 at gmail.com> >>>>>>>>> wrote: >>>>>>>>> >>>>>>>>>> > Oh, and yes, I've loaded upwards of 50-100 modules in >>>>>>>>>> development. 20 >>>>>>>>>> modules is *easy* to achieve in single-page apps. >>>>>>>>>> >>>>>>>>>> was that with some combination of babel/rollup/webpack or >>>>>>>>>> pure-es6? >>>>>>>>>> if i want to develop a pure-es6 webapp (no babel), how would i >>>>>>>>>> transition from development-mode (20 es-module files) -> production-mode (1 >>>>>>>>>> rollup file)? >>>>>>>>>> >>>>>>>>>> >>>>>>>>>> On Fri, May 31, 2019 at 10:47 AM Isiah Meadows < >>>>>>>>>> isiahmeadows at gmail.com> wrote: >>>>>>>>>> >>>>>>>>>>> If it's bundled by Rollup or Webpack into a single bundle, it's >>>>>>>>>>> equivalent to a single `<script type="module" src="...">` >>>>>>>>>>> pointing >>>>>>>>>>> towards the original entry point, excluding network requests.* >>>>>>>>>>> But in >>>>>>>>>>> either case, you aren't listing 50 scripts, you're only listing >>>>>>>>>>> the >>>>>>>>>>> entry module and importing child modules within parent modules. >>>>>>>>>>> Rollup >>>>>>>>>>> and Webpack do mostly the same thing browsers do when it comes to >>>>>>>>>>> resolving dependencies, just they generate a bundle afterwards >>>>>>>>>>> where >>>>>>>>>>> browsers execute code afterwards. Also, it's worth noting that >>>>>>>>>>> the gap >>>>>>>>>>> between a single large request and multiple smaller requests has >>>>>>>>>>> shrunk a lot since HTTP/2 came along, since it's binary, it >>>>>>>>>>> allows >>>>>>>>>>> requests and response data to be interleaved, it better >>>>>>>>>>> leverages the >>>>>>>>>>> underlying TCP protocol format, and it allows servers to send >>>>>>>>>>> data >>>>>>>>>>> pre-emptively without the client requesting it first. (Web >>>>>>>>>>> sockets are >>>>>>>>>>> built on this functionality.) It's still better to bundle in >>>>>>>>>>> general, >>>>>>>>>>> but it's less of a problem not to. >>>>>>>>>>> >>>>>>>>>>> This is *not* the case for `<script type="module">` elements - >>>>>>>>>>> those >>>>>>>>>>> operate more like inline scripts that happen to have the ability >>>>>>>>>>> to >>>>>>>>>>> `import`. >>>>>>>>>>> >>>>>>>>>>> Oh, and yes, I've loaded upwards of 50-100 modules in >>>>>>>>>>> development. 20 >>>>>>>>>>> modules is *easy* to achieve in single-page apps. >>>>>>>>>>> >>>>>>>>>>> * This is, of course, not the case if you are using pure ES6 and >>>>>>>>>>> you >>>>>>>>>>> aren't using any plugins to, say, run the original source through >>>>>>>>>>> Babel for React + JSX or something. >>>>>>>>>>> >>>>>>>>>>> ----- >>>>>>>>>>> >>>>>>>>>>> Isiah Meadows >>>>>>>>>>> contact at isiahmeadows.com >>>>>>>>>>> www.isiahmeadows.com >>>>>>>>>>> On Sat, May 25, 2019 at 2:12 AM kai zhu <kaizhu256 at gmail.com> >>>>>>>>>>> wrote: >>>>>>>>>>> > >>>>>>>>>>> > Asynchronous loading differs only in >>>>>>>>>>> > that it takes more code to express the same logic and you have >>>>>>>>>>> to take >>>>>>>>>>> > into account concurrent requests (and you need to cache the >>>>>>>>>>> request, >>>>>>>>>>> > not the result), but it's otherwise the same from 1km away. >>>>>>>>>>> > >>>>>>>>>>> > >>>>>>>>>>> > so async-loading 50 ```<script type="module">``` tags >>>>>>>>>>> > has equivalent side-effect >>>>>>>>>>> > as sync-loading single webpack-rollup (of same 50 modules)? >>>>>>>>>>> > >>>>>>>>>>> > i have nagging suspicion of doubts. has anyone tried native >>>>>>>>>>> async-loading large numbers (>10) of >>>>>>>>>>> > ```<script type="module">``` tags, and verify it resolves >>>>>>>>>>> identically to using a single webpack-rollup? >>>>>>>>>>> > >>>>>>>>>>> > again, i'm not that knowledgeable on es-modules, so above >>>>>>>>>>> question may be trivially true, and i'm just not aware. >>>>>>>>>>> > >>>>>>>>>>> > -kai >>>>>>>>>>> > >>>>>>>>>>> > On 24 May 2019, at 23:41, Isiah Meadows < >>>>>>>>>>> isiahmeadows at gmail.com> wrote: >>>>>>>>>>> > >>>>>>>>>>> > There's two main reasons why it scales: >>>>>>>>>>> > >>>>>>>>>>> > 1. Modules are strongly encapsulated while minimizing global >>>>>>>>>>> pollution. >>>>>>>>>>> > 2. The resolution algorithm applies the same logic no matter >>>>>>>>>>> how many >>>>>>>>>>> > modules are loaded. >>>>>>>>>>> > >>>>>>>>>>> > It's much easier for it to scale when you write the code >>>>>>>>>>> unaware of >>>>>>>>>>> > how many modules you might be loading and unaware of how deep >>>>>>>>>>> their >>>>>>>>>>> > dependency graph is. Fewer assumptions here is key. It's an >>>>>>>>>>> > engineering problem, but a relatively simple one. >>>>>>>>>>> > >>>>>>>>>>> > If you want a short example of how sync module resolution >>>>>>>>>>> works, you >>>>>>>>>>> > can take a look at this little utility I wrote: >>>>>>>>>>> > https://github.com/isiahmeadows/simple-require-loader. That >>>>>>>>>>> doesn't >>>>>>>>>>> > asynchronously resolve modules, but it should help explain the >>>>>>>>>>> process >>>>>>>>>>> > from a synchronous standpoint. Asynchronous loading differs >>>>>>>>>>> only in >>>>>>>>>>> > that it takes more code to express the same logic and you have >>>>>>>>>>> to take >>>>>>>>>>> > into account concurrent requests (and you need to cache the >>>>>>>>>>> request, >>>>>>>>>>> > not the result), but it's otherwise the same from 1km away. >>>>>>>>>>> > >>>>>>>>>>> > ----- >>>>>>>>>>> > >>>>>>>>>>> > Isiah Meadows >>>>>>>>>>> > contact at isiahmeadows.com >>>>>>>>>>> > www.isiahmeadows.com >>>>>>>>>>> > >>>>>>>>>>> > On Thu, May 23, 2019 at 10:49 AM kai zhu <kaizhu256 at gmail.com> >>>>>>>>>>> wrote: >>>>>>>>>>> > >>>>>>>>>>> > >>>>>>>>>>> > actually, i admit i don't know what i'm talking about. just >>>>>>>>>>> generally confused (through ignorance) on how large-scale es-module >>>>>>>>>>> dependencies resolve when loaded/imported asynchronously. >>>>>>>>>>> > >>>>>>>>>>> > On Wed, May 22, 2019 at 10:42 PM Logan Smyth < >>>>>>>>>>> loganfsmyth at gmail.com> wrote: >>>>>>>>>>> > >>>>>>>>>>> > >>>>>>>>>>> > Can you elaborate on what loading state you need to keep track >>>>>>>>>>> of? What is the bottleneck that you run into? Also to be sure, when you say >>>>>>>>>>> async-load, do you mean `import()`? >>>>>>>>>>> > >>>>>>>>>>> > On Wed, May 22, 2019, 20:17 kai zhu <kaizhu256 at gmail.com> >>>>>>>>>>> wrote: >>>>>>>>>>> > >>>>>>>>>>> > >>>>>>>>>>> > i don't use es-modules. >>>>>>>>>>> > but with amd/requirejs, I start having trouble with >>>>>>>>>>> module-initializations in nodejs/browser at ~5 async modules (that may or >>>>>>>>>>> may not have circular-references). 10 would be hard, and 20 would be near >>>>>>>>>>> inhuman for me. >>>>>>>>>>> > >>>>>>>>>>> > can we say its somewhat impractical for most applications to >>>>>>>>>>> load more than 50 async modules (with some of them having >>>>>>>>>>> circular-references)? and perhaps better design/spec module-loading >>>>>>>>>>> mechanisms with this usability concern in mind? >>>>>>>>>>> > >>>>>>>>>>> > p.s. its also impractical for me to async-load 5 or more >>>>>>>>>>> modules without using globalThis to keep track of each module's >>>>>>>>>>> loading-state. >>>>>>>>>>> > _______________________________________________ >>>>>>>>>>> > es-discuss mailing list >>>>>>>>>>> > es-discuss at mozilla.org >>>>>>>>>>> > https://mail.mozilla.org/listinfo/es-discuss >>>>>>>>>>> > >>>>>>>>>>> > >>>>>>>>>>> > _______________________________________________ >>>>>>>>>>> > es-discuss mailing list >>>>>>>>>>> > es-discuss at mozilla.org >>>>>>>>>>> > https://mail.mozilla.org/listinfo/es-discuss >>>>>>>>>>> > >>>>>>>>>>> > >>>>>>>>>>> >>>>>>>>>> _______________________________________________ >>>>>>>>>> es-discuss mailing list >>>>>>>>>> es-discuss at mozilla.org >>>>>>>>>> https://mail.mozilla.org/listinfo/es-discuss >>>>>>>>>> >>>>>>>>> -------------- next part -------------- An HTML attachment was scrubbed... URL: <http://mail.mozilla.org/pipermail/es-discuss/attachments/20190602/b9df6ad1/attachment-0001.html>
Multiple imports are already possible
import {inline} from "./inline.js";
import {nextInline} from "./nextInline.js";
const o = {
a:1, b:2, c:3
};
const z = {f: 5};
// ...
export {o, cities, video, inline, nextInline};
Are you proposing multiple export
s
export {o, cities, video, inline, nextInline};
o.c = 7;
z.c = o.c;
export {z};
which is also currently possible?
Re
having circular-references
Is the issue at the example code use of var
instead of const
and exporting the same identifier twice?
Uncaught SyntaxError: Duplicate export of 'o'
?
Multiple imports are already possible ``` import {inline} from "./inline.js"; import {nextInline} from "./nextInline.js"; const o = { a:1, b:2, c:3 }; // ... export {o, cities, video, inline, nextInline}; ``` Are you proposing multiple ```export```s? ``` export {o, cities, video, inline, nextInline}; o.c = 7; export {o}; ``` On Sun, Jun 2, 2019 at 6:19 PM kai zhu <kaizhu256 at gmail.com> wrote: > @guest271314 <guest271314 at gmail.com>, your example again is not a > [native] bundle of two or more inlined es-modules. its just a single > es-module that that fetches json data. > > i'm asking if its desirable to inline multiple es-modules into a single > file natively, e.g.: > > ``` > /* > * es-module.rollup.js > * this [hypothetical] rollup-file contains multiple inlined es-modules > * to improve load-performance in production-deployment. > */ > > // 1. inlined es-module ./main.js > import { foo } from "./counter.js" > import { bar } from "./display.js" > foo(bar); > > // 2. inlined es-module ./counter.js > var foo; > foo = function (bar) { > bar(); > }; > export { foo } > > // 3. inlined es-module ./display.js > var bar; > bar = function () { > console.log("hello world"); > }; > export { bar } > ``` > > this native es-module inline-capability may not be desirable to you, which > is fine. it would be a datapoint against this feature (and rely instead on > pre-emptive import-maps and http2-push, as explained by @frederick and > @isiah). > > > On Sun, Jun 2, 2019 at 11:22 AM guest271314 <guest271314 at gmail.com> wrote: > >> 1) original-question - is native es-module's async-behavior desirable? >>> async side-effects are difficult to manage -- i conjecture that >>> async-loading 20 es-modules (with dependent side-effects) is not practical >>> for most mortals to handle. >> >> >> It depends on what *you *mean by "desirable" in a given context. >> >> There is no difference from loading 1 module and loading 1000 modules >> except for network cost, memory and disk space usage. >> >> Mortals can handle far more than loading 20 es-modules. >> >> What are the specific "side-effects" that you are referring to? >> >> describes the mechanism for how to hint the brower to pre-fetch 20 >>> es-modules. but if you pre-fetch, then is loading-behavior effectively >>> synchronous? >> >> >> Resources can be "pre-fetched" using various means. From caching the >> first request and using the cached data instead of making future requests >> for the same resources to storing one or more entire directories in the >> browser configuration folder using `requestFileSystem` (Chromiom/Chrome). >> >> but was unclear whether they were individual [async] ```<script >>> type="module">``` tags, or some es5-transpiled rollup >> >> >> There should not be any difference between the two approaches. If there >> is a difference then you should be able to clearly state what the >> difference is, and demonstrate the difference by reproduction, without >> speculating and not demonstrating a difference by means of reproduction. >> >> 2) the second-question about es-module rollups (which you and i are >>> debating) stemmed from @isiah's response -- if he and everyone-else use >>> es5-transpiled rollups (which i suspect), >> >> >> Do not care what "everyone-else" is supposedly doing. How can you >> possibly know what everyone-else is doing and even if you did know what >> third-parties are doing how does that affect what you are doing? >> >> then shouldn't it be desirable for es-modules to natively support rollups >>> as well? currently, there's no way to natively rollup multiple es-modules >>> into a single bundle. >> >> >> There are ways to "bundle" multiple modules into a single export >> "natively", as demonstrated at the previously posted code. >> >> Another example approach >> >> ``` >> // sync >> const o = { >> a:1, b:2, c:3 >> }; >> // async >> const cities = fetch(" >> https://gist.githubusercontent.com/guest271314/ffac94353ab16f42160e/raw/aaee70a3e351f6c7bc00178eabb5970a02df87e9/states.json >> ") >> .then(response => response.json()) >> .catch(e => {console.error(e); return "error fetching >> cities module"}); >> // async >> const video = fetch(" >> https://upload.wikimedia.org/wikipedia/commons/d/d9/120-cell.ogv") >> .then(response => response.blob()) >> .catch(e => {console.error(e); return "error fetching video >> module"}); >> // multiple "modules" exported >> export {o, cities, video}; >> ``` >> >> at single ```<script type="module">``` >> >> ``` >> <script type="module"> >> import * as o from "./script.js"; >> (async(mods) => { >> for (const [key, value] of mods) { >> if (value instanceof Promise) { >> console.log("async module", key, await value) >> } else { >> console.log("sync module", key, value); >> } >> } >> })(Object.entries(o)); >> </script> >> ``` >> >> Still there is no actual problem statement. Rather, there is conjecture >> without a definitive issue to solve. >> >> >> >> >> On Sun, Jun 2, 2019 at 3:54 AM kai zhu <kaizhu256 at gmail.com> wrote: >> >>> i apologize for poor framing of my questions. they are still formative, >>> but i can clarify abit as follows: >>> >>> 1) original-question - is native es-module's async-behavior desirable? >>> async side-effects are difficult to manage -- i conjecture that >>> async-loading 20 es-modules (with dependent side-effects) is not practical >>> for most mortals to handle. >>> @frederick describes the mechanism for how to hint the brower to >>> pre-fetch 20 es-modules. but if you pre-fetch, then is loading-behavior >>> effectively synchronous? >>> @isiah says he has experience loading 50-100 modules, but was unclear >>> whether they were individual [async] ```<script type="module">``` tags, >>> or some es5-transpiled rollup. >>> >>> i may be wrong about everything, as i'm a bit ignorant on what async >>> actually means in es-modules (and appreciate it, if someone can clarify >>> that). >>> >>> >>> >>> 2) the second-question about es-module rollups (which you and i are >>> debating) stemmed from @isiah's response -- if he and everyone-else use >>> es5-transpiled rollups (which i suspect), then shouldn't it be desirable >>> for es-modules to natively support rollups as well? currently, there's no >>> way to natively rollup multiple es-modules into a single bundle. >>> >>> this 2nd question also has implications about es-module's async-behavior >>> (because rollups "load" modules in sync/blocking fashion). this could >>> change side-effect behaviors between development-mode (20 [async] ```<script >>> type="module">``` tags) and production-mode (1 rollup-bundle). again, >>> i may be wrong about that, as i'm ignorant about what async actually is in >>> es-modules. >>> >>> -kai >>> >>> On Sat, Jun 1, 2019 at 9:22 PM guest271314 <guest271314 at gmail.com> >>> wrote: >>> >>>> > it doesn't actually ```import``` 1000+ es-modules inside the >>>> rollup-file. it just creates one es-module that exports a dictionary -- and >>>> assigns the dictionary 1000+ vanilla json-objects and functions. >>>> >>>> The code provides a means to fetch N resources and export those >>>> resources within a single object. >>>> >>>> > currently, as i'm aware, nobody uses native es-modules in production, >>>> because it cannot be rolled-up. >>>> > in practice es-modules are [babel] transpiled down to es5-amd (or >>>> similar) for rollup-purposes. >>>> > >>>> > if we're actually committed to native es-modules, then we either >>>> > 1) need to depend on embedders like loading-dev at chromium.org to >>>> create sophisticated cache-systems, or >>>> > 2) introduce new language-syntax to delimit es-modules for >>>> rollup-purposes, e.g. >>>> >>>> You still have not clearly defined what you mean by "rolled-up". That >>>> language appears to be a random nickname, not any immutable principle that >>>> individuals are bound to recognize or observe (even if "rolled-up" were >>>> some form of a coding style or standard). >>>> >>>> Nor is it clear what you mean by "production". >>>> >>>> There is no external central committee that stamps code as >>>> "production". Even if there were no individual is obliged to submit to such >>>> a procedure nor have any concern for such an arbitrary and irrelevant >>>> presumptive review of code. >>>> >>>> The only observable points are input and output. In general, how output >>>> is achieved is immaterial. If there are specific restrictions as to how the >>>> output can be achieved then those restrictions need to be clearly defined. >>>> >>>> >>>> >>>> The original post asked "how many async-modules can js-app practically >>>> load?" and mentioned "circular-references" (the thread appears to >>>> mainly be about one or more coding styles, not code itself) though as yet >>>> no code has been posted which demonstrates "circular-references" or any >>>> other coding problem. >>>> >>>> On Sun, Jun 2, 2019 at 1:30 AM kai zhu <kaizhu256 at gmail.com> wrote: >>>> >>>>> i played around with your code in jsfiddle [1], and understand it a >>>>> little more. >>>>> it doesn't actually ```import``` 1000+ es-modules inside the >>>>> rollup-file. >>>>> it just creates one es-module that exports a dictionary >>>>> -- and assigns the dictionary 1000+ vanilla json-objects and >>>>> functions. >>>>> >>>>> ```js >>>>> // the "rollup-file" is a single es-module >>>>> // that exports 1000+ vanilla dictionary-entries >>>>> const modules = {}; >>>>> >>>>> // this is not a es-module, nor is it rolled-up (external fetch) >>>>> modules.image = <await fetch json from gist.github.com> >>>>> >>>>> // this is not a [rolled-up] es-module >>>>> modules.fn = function () {...} >>>>> >>>>> // these are not [rolled-up] es-modules >>>>> Object.assign(modules, <1000 json-entries>) >>>>> >>>>> export {modules} >>>>> ``` >>>>> >>>>> currently, as i'm aware, nobody uses native es-modules in production, >>>>> because it cannot be rolled-up. >>>>> in practice es-modules are [babel] transpiled down to es5-amd (or >>>>> similar) for rollup-purposes. >>>>> >>>>> if we're actually committed to native es-modules, then we either >>>>> 1) need to depend on embedders like loading-dev at chromium.org to >>>>> create sophisticated cache-systems, or >>>>> 2) introduce new language-syntax to delimit es-modules for >>>>> rollup-purposes, e.g. >>>>> >>>>> ```js >>>>> // rollup.js with [hypothetical] # delimited es-modules >>>>> # module aa >>>>> import {bb} as bb; >>>>> export ...; >>>>> >>>>> # module bb >>>>> export ...; >>>>> ``` >>>>> >>>>> i'm generally skeptical of option 1, given how poorly npmjs.com has >>>>> handled similar problems deduplicating children in node_modules/ directory. >>>>> >>>>> [1] jsfiddle pseudo-module rollup >>>>> https://jsfiddle.net/06twrLfd/ >>>>> >>>>> On Sat, Jun 1, 2019 at 5:30 PM guest271314 <guest271314 at gmail.com> >>>>> wrote: >>>>> >>>>>> > your rollup solution is interesting, >>>>>> >>>>>> What is "rollup" referring to? >>>>>> >>>>>> > but i get an error when run in chrome (i changed to n=20 to prevent >>>>>> name-collision, but it still happens). >>>>>> >>>>>> The duplicate ("collision") entry an ```try..catch``` block is >>>>>> included in the code to demonstrate given an array of module names to be >>>>>> exported and imported as identifiers 1) duplicate entries can be filtered; >>>>>> 2) if a plain object is exported duplicate identifiers ("collision") is not >>>>>> possible as a JavaScript plain object does not have duplicate property >>>>>> names ("collision"); if there is an issue with identifiers in a module the >>>>>> cause would not be the number of async-modules loaded ("how many"), but the >>>>>> naming of the identifiers within the code, using or not using ```const``` >>>>>> or ```let```. Still not sure what the actual issue is? >>>>>> >>>>>> > don't completely understand how it works, >>>>>> >>>>>> Use an ```async``` function to fetch data, check for the described >>>>>> "collision" , create a ```data URI``` to be imported, optionally, append >>>>>> addition code to be executed within the ```<script type="module">```. >>>>>> >>>>>> > but not sure of suitability for production-use, because of its >>>>>> dynamic <script> tag generation. >>>>>> >>>>>> What is the issue with dynamic ```<script>``` tag generation? >>>>>> >>>>>> There is more than one possible approach to achieve the presumptive >>>>>> requirement, that is still not clear to the exclusion of what is not the >>>>>> expected result. >>>>>> >>>>>> There were no restrictions described at the OP and following messages >>>>>> other than other than >>>>>> >>>>>> > pure-es6 application with 20 es-modules rolled-up into one >>>>>> [production] bundle? >>>>>> >>>>>> The example code uses only JavaScript implementation shipped with the >>>>>> browser without any external, third-party libraries. >>>>>> >>>>>> What standard or definition are you relying for the meaning of the >>>>>> term "production-use"? What procedure are you using to determine if code is >>>>>> "production-use" "suitable"? How is that procedure related to "how many >>>>>> async-modules can js-app practically load?"? >>>>>> >>>>>> >>>>>> >>>>>> On Sat, Jun 1, 2019 at 9:42 PM kai zhu <kaizhu256 at gmail.com> wrote: >>>>>> >>>>>>> your rollup solution is interesting, but i get an error when run in >>>>>>> chrome (i changed to n=20 to prevent name-collision, but it still >>>>>>> happens). don't completely understand how it works, but not sure of >>>>>>> suitability for production-use, because of its dynamic <script> tag >>>>>>> generation. >>>>>>> >>>>>>> ```console >>>>>>> ReferenceError: module names ["yeqjqb02mvg3yze26rc5"] are not unique >>>>>>> at >>>>>>> data:application/javascript,%0A%20%20%20%20%20%20const%20modules... >>>>>>> ``` >>>>>>> >>>>>>> On Sat, Jun 1, 2019 at 2:33 PM guest271314 <guest271314 at gmail.com> >>>>>>> wrote: >>>>>>> >>>>>>>> Re: how many async-modules can js-app practically load? >>>>>>>> >>>>>>>> An example of exporting and importing loading 1000 properties in a >>>>>>>> single module, where duplicate property names are checked for. Since >>>>>>>> JavaScript plain objects cannot have duplicate property names there should >>>>>>>> not be any "collisions"; the code can check for and modify the object to be >>>>>>>> exported, though the last duplicate property name will be exported without >>>>>>>> any errors thrown unless the code is composed to throw such an error. >>>>>>>> >>>>>>>> ``` >>>>>>>> (async() => { >>>>>>>> const oneThousandModules = encodeURIComponent( >>>>>>>> // substitute rand for a Set of module names to be exported >>>>>>>> // e.g. const moduleNames = ['moduleA', 'moduleB', ...moduleZ] >>>>>>>> ` >>>>>>>> const modules = {}; >>>>>>>> // set a function to be exported >>>>>>>> modules.fn = function() {return 'a function'}; >>>>>>>> // function to set (1000) 'random' module names to be exported >>>>>>>> const rand = (seed = 'abcdefghijklmnopqrstuvwxyz0123456789', >>>>>>>> n = 5, len = seed.length) => >>>>>>>> '.'.repeat(n).replace(/./g, _ => seed[~~(Math.random() * >>>>>>>> len)]); >>>>>>>> // use Set for unique module identifiers >>>>>>>> const moduleNames = [...Array(1000)].map(_ => rand()); >>>>>>>> const moduleIdentifiers = new Set(moduleNames); >>>>>>>> // below line will cause ReferenceError to be thrown >>>>>>>> moduleNames.push(moduleNames[0]); >>>>>>>> try { >>>>>>>> if (moduleIdentifiers.size !== moduleNames.length) { >>>>>>>> // check for duplicates >>>>>>>> const duplicates = moduleNames.filter((moduleName, >>>>>>>> index) => moduleNames.indexOf(moduleName) !== index); >>>>>>>> // notification of duplicate module names >>>>>>>> throw new ReferenceError('module names ' + >>>>>>>> JSON.stringify(duplicates) + ' are not unique'); >>>>>>>> // perform the designated task if duplicate module >>>>>>>> names are found here >>>>>>>> } >>>>>>>> } catch (e) { >>>>>>>> console.error(e); >>>>>>>> console.trace(); >>>>>>>> } >>>>>>>> // get, set (sync or async) exported module here >>>>>>>> Object.assign(modules, ...[...moduleIdentifiers].map((id, >>>>>>>> value) => ({[id]:value}))); >>>>>>>> // since JavaScript plain object cannot have duplicate >>>>>>>> property names >>>>>>>> // modules object will still be exported without duplicate >>>>>>>> property names >>>>>>>> // without collisions >>>>>>>> export {modules} >>>>>>>> `); >>>>>>>> const scriptText = `import {modules} from >>>>>>>> "data:application/javascript,${oneThousandModules};${encodeURIComponent('console.log(modules);for >>>>>>>> (const key in modules) {if (typeof modules[key] === \'function\') >>>>>>>> {console.log(modules[key]());}}')}"`; >>>>>>>> const script = document.createElement("script"); >>>>>>>> script.type = "module"; >>>>>>>> script.textContent = scriptText; >>>>>>>> document.head.appendChild(script); >>>>>>>> })(); >>>>>>>> ``` >>>>>>>> >>>>>>>> plnkr https://plnkr.co/edit/CgEhBY?p=preview >>>>>>>> >>>>>>>> On Sat, Jun 1, 2019 at 1:51 AM kai zhu <kaizhu256 at gmail.com> wrote: >>>>>>>> >>>>>>>>> > Place all of the code to be exported in 1 file? >>>>>>>>> >>>>>>>>> that obviously will not work, because of module-scope collision. >>>>>>>>> can anyone share their experience on deploying a [babel-free] pure-es6 >>>>>>>>> application with 20 es-modules rolled-up into one [production] bundle? is >>>>>>>>> it even possible? >>>>>>>>> >>>>>>>>> >>>>>>>>> On Fri, May 31, 2019 at 7:55 PM guest271314 <guest271314 at gmail.com> >>>>>>>>> wrote: >>>>>>>>> >>>>>>>>>> > how would i transition from development-mode (20 es-module >>>>>>>>>> files) -> production-mode (1 rollup file)? >>>>>>>>>> >>>>>>>>>> Place all of the code to be exported in 1 file? >>>>>>>>>> >>>>>>>>>> > with some of them having circular-references >>>>>>>>>> >>>>>>>>>> Not certain how that is possible when using ```import``` within >>>>>>>>>> ```<script type="module">```? >>>>>>>>>> >>>>>>>>>> > how many async-modules can js-app practically load? >>>>>>>>>> >>>>>>>>>> Again, how many have you tried to load? 100? 500? 1000? Either >>>>>>>>>> should be possible. >>>>>>>>>> >>>>>>>>>> What specific issue are you actually to resolve? >>>>>>>>>> >>>>>>>>>> On Fri, May 31, 2019 at 5:40 PM kai zhu <kaizhu256 at gmail.com> >>>>>>>>>> wrote: >>>>>>>>>> >>>>>>>>>>> > Oh, and yes, I've loaded upwards of 50-100 modules in >>>>>>>>>>> development. 20 >>>>>>>>>>> modules is *easy* to achieve in single-page apps. >>>>>>>>>>> >>>>>>>>>>> was that with some combination of babel/rollup/webpack or >>>>>>>>>>> pure-es6? >>>>>>>>>>> if i want to develop a pure-es6 webapp (no babel), how would i >>>>>>>>>>> transition from development-mode (20 es-module files) -> production-mode (1 >>>>>>>>>>> rollup file)? >>>>>>>>>>> >>>>>>>>>>> >>>>>>>>>>> On Fri, May 31, 2019 at 10:47 AM Isiah Meadows < >>>>>>>>>>> isiahmeadows at gmail.com> wrote: >>>>>>>>>>> >>>>>>>>>>>> If it's bundled by Rollup or Webpack into a single bundle, it's >>>>>>>>>>>> equivalent to a single `<script type="module" src="...">` >>>>>>>>>>>> pointing >>>>>>>>>>>> towards the original entry point, excluding network requests.* >>>>>>>>>>>> But in >>>>>>>>>>>> either case, you aren't listing 50 scripts, you're only listing >>>>>>>>>>>> the >>>>>>>>>>>> entry module and importing child modules within parent modules. >>>>>>>>>>>> Rollup >>>>>>>>>>>> and Webpack do mostly the same thing browsers do when it comes >>>>>>>>>>>> to >>>>>>>>>>>> resolving dependencies, just they generate a bundle afterwards >>>>>>>>>>>> where >>>>>>>>>>>> browsers execute code afterwards. Also, it's worth noting that >>>>>>>>>>>> the gap >>>>>>>>>>>> between a single large request and multiple smaller requests has >>>>>>>>>>>> shrunk a lot since HTTP/2 came along, since it's binary, it >>>>>>>>>>>> allows >>>>>>>>>>>> requests and response data to be interleaved, it better >>>>>>>>>>>> leverages the >>>>>>>>>>>> underlying TCP protocol format, and it allows servers to send >>>>>>>>>>>> data >>>>>>>>>>>> pre-emptively without the client requesting it first. (Web >>>>>>>>>>>> sockets are >>>>>>>>>>>> built on this functionality.) It's still better to bundle in >>>>>>>>>>>> general, >>>>>>>>>>>> but it's less of a problem not to. >>>>>>>>>>>> >>>>>>>>>>>> This is *not* the case for `<script type="module">` elements - >>>>>>>>>>>> those >>>>>>>>>>>> operate more like inline scripts that happen to have the >>>>>>>>>>>> ability to >>>>>>>>>>>> `import`. >>>>>>>>>>>> >>>>>>>>>>>> Oh, and yes, I've loaded upwards of 50-100 modules in >>>>>>>>>>>> development. 20 >>>>>>>>>>>> modules is *easy* to achieve in single-page apps. >>>>>>>>>>>> >>>>>>>>>>>> * This is, of course, not the case if you are using pure ES6 >>>>>>>>>>>> and you >>>>>>>>>>>> aren't using any plugins to, say, run the original source >>>>>>>>>>>> through >>>>>>>>>>>> Babel for React + JSX or something. >>>>>>>>>>>> >>>>>>>>>>>> ----- >>>>>>>>>>>> >>>>>>>>>>>> Isiah Meadows >>>>>>>>>>>> contact at isiahmeadows.com >>>>>>>>>>>> www.isiahmeadows.com >>>>>>>>>>>> On Sat, May 25, 2019 at 2:12 AM kai zhu <kaizhu256 at gmail.com> >>>>>>>>>>>> wrote: >>>>>>>>>>>> > >>>>>>>>>>>> > Asynchronous loading differs only in >>>>>>>>>>>> > that it takes more code to express the same logic and you >>>>>>>>>>>> have to take >>>>>>>>>>>> > into account concurrent requests (and you need to cache the >>>>>>>>>>>> request, >>>>>>>>>>>> > not the result), but it's otherwise the same from 1km away. >>>>>>>>>>>> > >>>>>>>>>>>> > >>>>>>>>>>>> > so async-loading 50 ```<script type="module">``` tags >>>>>>>>>>>> > has equivalent side-effect >>>>>>>>>>>> > as sync-loading single webpack-rollup (of same 50 modules)? >>>>>>>>>>>> > >>>>>>>>>>>> > i have nagging suspicion of doubts. has anyone tried native >>>>>>>>>>>> async-loading large numbers (>10) of >>>>>>>>>>>> > ```<script type="module">``` tags, and verify it resolves >>>>>>>>>>>> identically to using a single webpack-rollup? >>>>>>>>>>>> > >>>>>>>>>>>> > again, i'm not that knowledgeable on es-modules, so above >>>>>>>>>>>> question may be trivially true, and i'm just not aware. >>>>>>>>>>>> > >>>>>>>>>>>> > -kai >>>>>>>>>>>> > >>>>>>>>>>>> > On 24 May 2019, at 23:41, Isiah Meadows < >>>>>>>>>>>> isiahmeadows at gmail.com> wrote: >>>>>>>>>>>> > >>>>>>>>>>>> > There's two main reasons why it scales: >>>>>>>>>>>> > >>>>>>>>>>>> > 1. Modules are strongly encapsulated while minimizing global >>>>>>>>>>>> pollution. >>>>>>>>>>>> > 2. The resolution algorithm applies the same logic no matter >>>>>>>>>>>> how many >>>>>>>>>>>> > modules are loaded. >>>>>>>>>>>> > >>>>>>>>>>>> > It's much easier for it to scale when you write the code >>>>>>>>>>>> unaware of >>>>>>>>>>>> > how many modules you might be loading and unaware of how deep >>>>>>>>>>>> their >>>>>>>>>>>> > dependency graph is. Fewer assumptions here is key. It's an >>>>>>>>>>>> > engineering problem, but a relatively simple one. >>>>>>>>>>>> > >>>>>>>>>>>> > If you want a short example of how sync module resolution >>>>>>>>>>>> works, you >>>>>>>>>>>> > can take a look at this little utility I wrote: >>>>>>>>>>>> > https://github.com/isiahmeadows/simple-require-loader. That >>>>>>>>>>>> doesn't >>>>>>>>>>>> > asynchronously resolve modules, but it should help explain >>>>>>>>>>>> the process >>>>>>>>>>>> > from a synchronous standpoint. Asynchronous loading differs >>>>>>>>>>>> only in >>>>>>>>>>>> > that it takes more code to express the same logic and you >>>>>>>>>>>> have to take >>>>>>>>>>>> > into account concurrent requests (and you need to cache the >>>>>>>>>>>> request, >>>>>>>>>>>> > not the result), but it's otherwise the same from 1km away. >>>>>>>>>>>> > >>>>>>>>>>>> > ----- >>>>>>>>>>>> > >>>>>>>>>>>> > Isiah Meadows >>>>>>>>>>>> > contact at isiahmeadows.com >>>>>>>>>>>> > www.isiahmeadows.com >>>>>>>>>>>> > >>>>>>>>>>>> > On Thu, May 23, 2019 at 10:49 AM kai zhu <kaizhu256 at gmail.com> >>>>>>>>>>>> wrote: >>>>>>>>>>>> > >>>>>>>>>>>> > >>>>>>>>>>>> > actually, i admit i don't know what i'm talking about. just >>>>>>>>>>>> generally confused (through ignorance) on how large-scale es-module >>>>>>>>>>>> dependencies resolve when loaded/imported asynchronously. >>>>>>>>>>>> > >>>>>>>>>>>> > On Wed, May 22, 2019 at 10:42 PM Logan Smyth < >>>>>>>>>>>> loganfsmyth at gmail.com> wrote: >>>>>>>>>>>> > >>>>>>>>>>>> > >>>>>>>>>>>> > Can you elaborate on what loading state you need to keep >>>>>>>>>>>> track of? What is the bottleneck that you run into? Also to be sure, when >>>>>>>>>>>> you say async-load, do you mean `import()`? >>>>>>>>>>>> > >>>>>>>>>>>> > On Wed, May 22, 2019, 20:17 kai zhu <kaizhu256 at gmail.com> >>>>>>>>>>>> wrote: >>>>>>>>>>>> > >>>>>>>>>>>> > >>>>>>>>>>>> > i don't use es-modules. >>>>>>>>>>>> > but with amd/requirejs, I start having trouble with >>>>>>>>>>>> module-initializations in nodejs/browser at ~5 async modules (that may or >>>>>>>>>>>> may not have circular-references). 10 would be hard, and 20 would be near >>>>>>>>>>>> inhuman for me. >>>>>>>>>>>> > >>>>>>>>>>>> > can we say its somewhat impractical for most applications to >>>>>>>>>>>> load more than 50 async modules (with some of them having >>>>>>>>>>>> circular-references)? and perhaps better design/spec module-loading >>>>>>>>>>>> mechanisms with this usability concern in mind? >>>>>>>>>>>> > >>>>>>>>>>>> > p.s. its also impractical for me to async-load 5 or more >>>>>>>>>>>> modules without using globalThis to keep track of each module's >>>>>>>>>>>> loading-state. >>>>>>>>>>>> > _______________________________________________ >>>>>>>>>>>> > es-discuss mailing list >>>>>>>>>>>> > es-discuss at mozilla.org >>>>>>>>>>>> > https://mail.mozilla.org/listinfo/es-discuss >>>>>>>>>>>> > >>>>>>>>>>>> > >>>>>>>>>>>> > _______________________________________________ >>>>>>>>>>>> > es-discuss mailing list >>>>>>>>>>>> > es-discuss at mozilla.org >>>>>>>>>>>> > https://mail.mozilla.org/listinfo/es-discuss >>>>>>>>>>>> > >>>>>>>>>>>> > >>>>>>>>>>>> >>>>>>>>>>> _______________________________________________ >>>>>>>>>>> es-discuss mailing list >>>>>>>>>>> es-discuss at mozilla.org >>>>>>>>>>> https://mail.mozilla.org/listinfo/es-discuss >>>>>>>>>>> >>>>>>>>>> -------------- next part -------------- An HTML attachment was scrubbed... URL: <http://mail.mozilla.org/pipermail/es-discuss/attachments/20190602/43def27d/attachment-0001.html>
not inline multiple export
's, but inline multiple module-scopes.
/*
* how do you inline the two es-modules below
* with colliding `foo` and `bar` variables?
*
* you can't unless you introduce new language-syntax
* to somehow delimit their scopes
*/
// [hypothethical] es-module-scope delimiter
# es-module-scope "./inline.js"
// module ./inline.js
import { foo } from "./aa.js"
const bar = { baz: foo };
export { bar };
// [hypothethical] es-module-scope delimiter
# es-module-scope ./nextinline.js
// module ./nextinline.js
import { foo } from "./bb.js"
const bar = { baz: foo };
export { bar };
not inline multiple ```export```'s, but inline multiple module-scopes. ```js /* * how do you inline the two es-modules below * with colliding `foo` and `bar` variables? * * you can't unless you introduce new language-syntax * to somehow delimit their scopes */ // [hypothethical] es-module-scope delimiter # es-module-scope "./inline.js" // module ./inline.js import { foo } from "./aa.js" const bar = { baz: foo }; export { bar }; // [hypothethical] es-module-scope delimiter # es-module-scope ./nextinline.js // module ./nextinline.js import { foo } from "./bb.js" const bar = { baz: foo }; export { bar }; ``` On Sun, Jun 2, 2019 at 2:54 PM guest271314 <guest271314 at gmail.com> wrote: > Multiple imports are already possible > > ``` > import {inline} from "./inline.js"; > import {nextInline} from "./nextInline.js"; > > const o = { > a:1, b:2, c:3 > }; > > // ... > > export {o, cities, video, inline, nextInline}; > ``` > > Are you proposing multiple ```export```s? > > ``` > export {o, cities, video, inline, nextInline}; > o.c = 7; > export {o}; > ``` > > > > On Sun, Jun 2, 2019 at 6:19 PM kai zhu <kaizhu256 at gmail.com> wrote: > >> @guest271314 <guest271314 at gmail.com>, your example again is not a >> [native] bundle of two or more inlined es-modules. its just a single >> es-module that that fetches json data. >> >> i'm asking if its desirable to inline multiple es-modules into a single >> file natively, e.g.: >> >> ``` >> /* >> * es-module.rollup.js >> * this [hypothetical] rollup-file contains multiple inlined es-modules >> * to improve load-performance in production-deployment. >> */ >> >> // 1. inlined es-module ./main.js >> import { foo } from "./counter.js" >> import { bar } from "./display.js" >> foo(bar); >> >> // 2. inlined es-module ./counter.js >> var foo; >> foo = function (bar) { >> bar(); >> }; >> export { foo } >> >> // 3. inlined es-module ./display.js >> var bar; >> bar = function () { >> console.log("hello world"); >> }; >> export { bar } >> ``` >> >> this native es-module inline-capability may not be desirable to you, >> which is fine. it would be a datapoint against this feature (and rely >> instead on pre-emptive import-maps and http2-push, as explained by >> @frederick and @isiah). >> >> >> On Sun, Jun 2, 2019 at 11:22 AM guest271314 <guest271314 at gmail.com> >> wrote: >> >>> 1) original-question - is native es-module's async-behavior desirable? >>>> async side-effects are difficult to manage -- i conjecture that >>>> async-loading 20 es-modules (with dependent side-effects) is not practical >>>> for most mortals to handle. >>> >>> >>> It depends on what *you *mean by "desirable" in a given context. >>> >>> There is no difference from loading 1 module and loading 1000 modules >>> except for network cost, memory and disk space usage. >>> >>> Mortals can handle far more than loading 20 es-modules. >>> >>> What are the specific "side-effects" that you are referring to? >>> >>> describes the mechanism for how to hint the brower to pre-fetch 20 >>>> es-modules. but if you pre-fetch, then is loading-behavior effectively >>>> synchronous? >>> >>> >>> Resources can be "pre-fetched" using various means. From caching the >>> first request and using the cached data instead of making future requests >>> for the same resources to storing one or more entire directories in the >>> browser configuration folder using `requestFileSystem` (Chromiom/Chrome). >>> >>> but was unclear whether they were individual [async] ```<script >>>> type="module">``` tags, or some es5-transpiled rollup >>> >>> >>> There should not be any difference between the two approaches. If there >>> is a difference then you should be able to clearly state what the >>> difference is, and demonstrate the difference by reproduction, without >>> speculating and not demonstrating a difference by means of reproduction. >>> >>> 2) the second-question about es-module rollups (which you and i are >>>> debating) stemmed from @isiah's response -- if he and everyone-else use >>>> es5-transpiled rollups (which i suspect), >>> >>> >>> Do not care what "everyone-else" is supposedly doing. How can you >>> possibly know what everyone-else is doing and even if you did know what >>> third-parties are doing how does that affect what you are doing? >>> >>> then shouldn't it be desirable for es-modules to natively support >>>> rollups as well? currently, there's no way to natively rollup multiple >>>> es-modules into a single bundle. >>> >>> >>> There are ways to "bundle" multiple modules into a single export >>> "natively", as demonstrated at the previously posted code. >>> >>> Another example approach >>> >>> ``` >>> // sync >>> const o = { >>> a:1, b:2, c:3 >>> }; >>> // async >>> const cities = fetch(" >>> https://gist.githubusercontent.com/guest271314/ffac94353ab16f42160e/raw/aaee70a3e351f6c7bc00178eabb5970a02df87e9/states.json >>> ") >>> .then(response => response.json()) >>> .catch(e => {console.error(e); return "error fetching >>> cities module"}); >>> // async >>> const video = fetch(" >>> https://upload.wikimedia.org/wikipedia/commons/d/d9/120-cell.ogv") >>> .then(response => response.blob()) >>> .catch(e => {console.error(e); return "error fetching >>> video module"}); >>> // multiple "modules" exported >>> export {o, cities, video}; >>> ``` >>> >>> at single ```<script type="module">``` >>> >>> ``` >>> <script type="module"> >>> import * as o from "./script.js"; >>> (async(mods) => { >>> for (const [key, value] of mods) { >>> if (value instanceof Promise) { >>> console.log("async module", key, await value) >>> } else { >>> console.log("sync module", key, value); >>> } >>> } >>> })(Object.entries(o)); >>> </script> >>> ``` >>> >>> Still there is no actual problem statement. Rather, there is conjecture >>> without a definitive issue to solve. >>> >>> >>> >>> >>> On Sun, Jun 2, 2019 at 3:54 AM kai zhu <kaizhu256 at gmail.com> wrote: >>> >>>> i apologize for poor framing of my questions. they are still >>>> formative, but i can clarify abit as follows: >>>> >>>> 1) original-question - is native es-module's async-behavior desirable? >>>> async side-effects are difficult to manage -- i conjecture that >>>> async-loading 20 es-modules (with dependent side-effects) is not practical >>>> for most mortals to handle. >>>> @frederick describes the mechanism for how to hint the brower to >>>> pre-fetch 20 es-modules. but if you pre-fetch, then is loading-behavior >>>> effectively synchronous? >>>> @isiah says he has experience loading 50-100 modules, but was unclear >>>> whether they were individual [async] ```<script type="module">``` >>>> tags, or some es5-transpiled rollup. >>>> >>>> i may be wrong about everything, as i'm a bit ignorant on what async >>>> actually means in es-modules (and appreciate it, if someone can clarify >>>> that). >>>> >>>> >>>> >>>> 2) the second-question about es-module rollups (which you and i are >>>> debating) stemmed from @isiah's response -- if he and everyone-else use >>>> es5-transpiled rollups (which i suspect), then shouldn't it be desirable >>>> for es-modules to natively support rollups as well? currently, there's no >>>> way to natively rollup multiple es-modules into a single bundle. >>>> >>>> this 2nd question also has implications about es-module's >>>> async-behavior (because rollups "load" modules in sync/blocking fashion). >>>> this could change side-effect behaviors between development-mode (20 >>>> [async] ```<script type="module">``` tags) and production-mode (1 >>>> rollup-bundle). again, i may be wrong about that, as i'm ignorant about >>>> what async actually is in es-modules. >>>> >>>> -kai >>>> >>>> On Sat, Jun 1, 2019 at 9:22 PM guest271314 <guest271314 at gmail.com> >>>> wrote: >>>> >>>>> > it doesn't actually ```import``` 1000+ es-modules inside the >>>>> rollup-file. it just creates one es-module that exports a dictionary -- and >>>>> assigns the dictionary 1000+ vanilla json-objects and functions. >>>>> >>>>> The code provides a means to fetch N resources and export those >>>>> resources within a single object. >>>>> >>>>> > currently, as i'm aware, nobody uses native es-modules in >>>>> production, because it cannot be rolled-up. >>>>> > in practice es-modules are [babel] transpiled down to es5-amd (or >>>>> similar) for rollup-purposes. >>>>> > >>>>> > if we're actually committed to native es-modules, then we either >>>>> > 1) need to depend on embedders like loading-dev at chromium.org to >>>>> create sophisticated cache-systems, or >>>>> > 2) introduce new language-syntax to delimit es-modules for >>>>> rollup-purposes, e.g. >>>>> >>>>> You still have not clearly defined what you mean by "rolled-up". That >>>>> language appears to be a random nickname, not any immutable principle that >>>>> individuals are bound to recognize or observe (even if "rolled-up" were >>>>> some form of a coding style or standard). >>>>> >>>>> Nor is it clear what you mean by "production". >>>>> >>>>> There is no external central committee that stamps code as >>>>> "production". Even if there were no individual is obliged to submit to such >>>>> a procedure nor have any concern for such an arbitrary and irrelevant >>>>> presumptive review of code. >>>>> >>>>> The only observable points are input and output. In general, how >>>>> output is achieved is immaterial. If there are specific restrictions as to >>>>> how the output can be achieved then those restrictions need to be clearly >>>>> defined. >>>>> >>>>> >>>>> >>>>> The original post asked "how many async-modules can js-app practically >>>>> load?" and mentioned "circular-references" (the thread appears to >>>>> mainly be about one or more coding styles, not code itself) though as yet >>>>> no code has been posted which demonstrates "circular-references" or any >>>>> other coding problem. >>>>> >>>>> On Sun, Jun 2, 2019 at 1:30 AM kai zhu <kaizhu256 at gmail.com> wrote: >>>>> >>>>>> i played around with your code in jsfiddle [1], and understand it a >>>>>> little more. >>>>>> it doesn't actually ```import``` 1000+ es-modules inside the >>>>>> rollup-file. >>>>>> it just creates one es-module that exports a dictionary >>>>>> -- and assigns the dictionary 1000+ vanilla json-objects and >>>>>> functions. >>>>>> >>>>>> ```js >>>>>> // the "rollup-file" is a single es-module >>>>>> // that exports 1000+ vanilla dictionary-entries >>>>>> const modules = {}; >>>>>> >>>>>> // this is not a es-module, nor is it rolled-up (external fetch) >>>>>> modules.image = <await fetch json from gist.github.com> >>>>>> >>>>>> // this is not a [rolled-up] es-module >>>>>> modules.fn = function () {...} >>>>>> >>>>>> // these are not [rolled-up] es-modules >>>>>> Object.assign(modules, <1000 json-entries>) >>>>>> >>>>>> export {modules} >>>>>> ``` >>>>>> >>>>>> currently, as i'm aware, nobody uses native es-modules in production, >>>>>> because it cannot be rolled-up. >>>>>> in practice es-modules are [babel] transpiled down to es5-amd (or >>>>>> similar) for rollup-purposes. >>>>>> >>>>>> if we're actually committed to native es-modules, then we either >>>>>> 1) need to depend on embedders like loading-dev at chromium.org to >>>>>> create sophisticated cache-systems, or >>>>>> 2) introduce new language-syntax to delimit es-modules for >>>>>> rollup-purposes, e.g. >>>>>> >>>>>> ```js >>>>>> // rollup.js with [hypothetical] # delimited es-modules >>>>>> # module aa >>>>>> import {bb} as bb; >>>>>> export ...; >>>>>> >>>>>> # module bb >>>>>> export ...; >>>>>> ``` >>>>>> >>>>>> i'm generally skeptical of option 1, given how poorly npmjs.com has >>>>>> handled similar problems deduplicating children in node_modules/ directory. >>>>>> >>>>>> [1] jsfiddle pseudo-module rollup >>>>>> https://jsfiddle.net/06twrLfd/ >>>>>> >>>>>> On Sat, Jun 1, 2019 at 5:30 PM guest271314 <guest271314 at gmail.com> >>>>>> wrote: >>>>>> >>>>>>> > your rollup solution is interesting, >>>>>>> >>>>>>> What is "rollup" referring to? >>>>>>> >>>>>>> > but i get an error when run in chrome (i changed to n=20 to >>>>>>> prevent name-collision, but it still happens). >>>>>>> >>>>>>> The duplicate ("collision") entry an ```try..catch``` block is >>>>>>> included in the code to demonstrate given an array of module names to be >>>>>>> exported and imported as identifiers 1) duplicate entries can be filtered; >>>>>>> 2) if a plain object is exported duplicate identifiers ("collision") is not >>>>>>> possible as a JavaScript plain object does not have duplicate property >>>>>>> names ("collision"); if there is an issue with identifiers in a module the >>>>>>> cause would not be the number of async-modules loaded ("how many"), but the >>>>>>> naming of the identifiers within the code, using or not using ```const``` >>>>>>> or ```let```. Still not sure what the actual issue is? >>>>>>> >>>>>>> > don't completely understand how it works, >>>>>>> >>>>>>> Use an ```async``` function to fetch data, check for the described >>>>>>> "collision" , create a ```data URI``` to be imported, optionally, append >>>>>>> addition code to be executed within the ```<script type="module">```. >>>>>>> >>>>>>> > but not sure of suitability for production-use, because of its >>>>>>> dynamic <script> tag generation. >>>>>>> >>>>>>> What is the issue with dynamic ```<script>``` tag generation? >>>>>>> >>>>>>> There is more than one possible approach to achieve the presumptive >>>>>>> requirement, that is still not clear to the exclusion of what is not the >>>>>>> expected result. >>>>>>> >>>>>>> There were no restrictions described at the OP and following >>>>>>> messages other than other than >>>>>>> >>>>>>> > pure-es6 application with 20 es-modules rolled-up into one >>>>>>> [production] bundle? >>>>>>> >>>>>>> The example code uses only JavaScript implementation shipped with >>>>>>> the browser without any external, third-party libraries. >>>>>>> >>>>>>> What standard or definition are you relying for the meaning of the >>>>>>> term "production-use"? What procedure are you using to determine if code is >>>>>>> "production-use" "suitable"? How is that procedure related to "how many >>>>>>> async-modules can js-app practically load?"? >>>>>>> >>>>>>> >>>>>>> >>>>>>> On Sat, Jun 1, 2019 at 9:42 PM kai zhu <kaizhu256 at gmail.com> wrote: >>>>>>> >>>>>>>> your rollup solution is interesting, but i get an error when run in >>>>>>>> chrome (i changed to n=20 to prevent name-collision, but it still >>>>>>>> happens). don't completely understand how it works, but not sure of >>>>>>>> suitability for production-use, because of its dynamic <script> tag >>>>>>>> generation. >>>>>>>> >>>>>>>> ```console >>>>>>>> ReferenceError: module names ["yeqjqb02mvg3yze26rc5"] are not unique >>>>>>>> at >>>>>>>> data:application/javascript,%0A%20%20%20%20%20%20const%20modules... >>>>>>>> ``` >>>>>>>> >>>>>>>> On Sat, Jun 1, 2019 at 2:33 PM guest271314 <guest271314 at gmail.com> >>>>>>>> wrote: >>>>>>>> >>>>>>>>> Re: how many async-modules can js-app practically load? >>>>>>>>> >>>>>>>>> An example of exporting and importing loading 1000 properties in a >>>>>>>>> single module, where duplicate property names are checked for. Since >>>>>>>>> JavaScript plain objects cannot have duplicate property names there should >>>>>>>>> not be any "collisions"; the code can check for and modify the object to be >>>>>>>>> exported, though the last duplicate property name will be exported without >>>>>>>>> any errors thrown unless the code is composed to throw such an error. >>>>>>>>> >>>>>>>>> ``` >>>>>>>>> (async() => { >>>>>>>>> const oneThousandModules = encodeURIComponent( >>>>>>>>> // substitute rand for a Set of module names to be exported >>>>>>>>> // e.g. const moduleNames = ['moduleA', 'moduleB', >>>>>>>>> ...moduleZ] >>>>>>>>> ` >>>>>>>>> const modules = {}; >>>>>>>>> // set a function to be exported >>>>>>>>> modules.fn = function() {return 'a function'}; >>>>>>>>> // function to set (1000) 'random' module names to be >>>>>>>>> exported >>>>>>>>> const rand = (seed = 'abcdefghijklmnopqrstuvwxyz0123456789', >>>>>>>>> n = 5, len = seed.length) => >>>>>>>>> '.'.repeat(n).replace(/./g, _ => seed[~~(Math.random() * >>>>>>>>> len)]); >>>>>>>>> // use Set for unique module identifiers >>>>>>>>> const moduleNames = [...Array(1000)].map(_ => rand()); >>>>>>>>> const moduleIdentifiers = new Set(moduleNames); >>>>>>>>> // below line will cause ReferenceError to be thrown >>>>>>>>> moduleNames.push(moduleNames[0]); >>>>>>>>> try { >>>>>>>>> if (moduleIdentifiers.size !== moduleNames.length) { >>>>>>>>> // check for duplicates >>>>>>>>> const duplicates = moduleNames.filter((moduleName, >>>>>>>>> index) => moduleNames.indexOf(moduleName) !== index); >>>>>>>>> // notification of duplicate module names >>>>>>>>> throw new ReferenceError('module names ' + >>>>>>>>> JSON.stringify(duplicates) + ' are not unique'); >>>>>>>>> // perform the designated task if duplicate module >>>>>>>>> names are found here >>>>>>>>> } >>>>>>>>> } catch (e) { >>>>>>>>> console.error(e); >>>>>>>>> console.trace(); >>>>>>>>> } >>>>>>>>> // get, set (sync or async) exported module here >>>>>>>>> Object.assign(modules, ...[...moduleIdentifiers].map((id, >>>>>>>>> value) => ({[id]:value}))); >>>>>>>>> // since JavaScript plain object cannot have duplicate >>>>>>>>> property names >>>>>>>>> // modules object will still be exported without duplicate >>>>>>>>> property names >>>>>>>>> // without collisions >>>>>>>>> export {modules} >>>>>>>>> `); >>>>>>>>> const scriptText = `import {modules} from >>>>>>>>> "data:application/javascript,${oneThousandModules};${encodeURIComponent('console.log(modules);for >>>>>>>>> (const key in modules) {if (typeof modules[key] === \'function\') >>>>>>>>> {console.log(modules[key]());}}')}"`; >>>>>>>>> const script = document.createElement("script"); >>>>>>>>> script.type = "module"; >>>>>>>>> script.textContent = scriptText; >>>>>>>>> document.head.appendChild(script); >>>>>>>>> })(); >>>>>>>>> ``` >>>>>>>>> >>>>>>>>> plnkr https://plnkr.co/edit/CgEhBY?p=preview >>>>>>>>> >>>>>>>>> On Sat, Jun 1, 2019 at 1:51 AM kai zhu <kaizhu256 at gmail.com> >>>>>>>>> wrote: >>>>>>>>> >>>>>>>>>> > Place all of the code to be exported in 1 file? >>>>>>>>>> >>>>>>>>>> that obviously will not work, because of module-scope collision. >>>>>>>>>> can anyone share their experience on deploying a [babel-free] pure-es6 >>>>>>>>>> application with 20 es-modules rolled-up into one [production] bundle? is >>>>>>>>>> it even possible? >>>>>>>>>> >>>>>>>>>> >>>>>>>>>> On Fri, May 31, 2019 at 7:55 PM guest271314 < >>>>>>>>>> guest271314 at gmail.com> wrote: >>>>>>>>>> >>>>>>>>>>> > how would i transition from development-mode (20 es-module >>>>>>>>>>> files) -> production-mode (1 rollup file)? >>>>>>>>>>> >>>>>>>>>>> Place all of the code to be exported in 1 file? >>>>>>>>>>> >>>>>>>>>>> > with some of them having circular-references >>>>>>>>>>> >>>>>>>>>>> Not certain how that is possible when using ```import``` within >>>>>>>>>>> ```<script type="module">```? >>>>>>>>>>> >>>>>>>>>>> > how many async-modules can js-app practically load? >>>>>>>>>>> >>>>>>>>>>> Again, how many have you tried to load? 100? 500? 1000? Either >>>>>>>>>>> should be possible. >>>>>>>>>>> >>>>>>>>>>> What specific issue are you actually to resolve? >>>>>>>>>>> >>>>>>>>>>> On Fri, May 31, 2019 at 5:40 PM kai zhu <kaizhu256 at gmail.com> >>>>>>>>>>> wrote: >>>>>>>>>>> >>>>>>>>>>>> > Oh, and yes, I've loaded upwards of 50-100 modules in >>>>>>>>>>>> development. 20 >>>>>>>>>>>> modules is *easy* to achieve in single-page apps. >>>>>>>>>>>> >>>>>>>>>>>> was that with some combination of babel/rollup/webpack or >>>>>>>>>>>> pure-es6? >>>>>>>>>>>> if i want to develop a pure-es6 webapp (no babel), how would i >>>>>>>>>>>> transition from development-mode (20 es-module files) -> production-mode (1 >>>>>>>>>>>> rollup file)? >>>>>>>>>>>> >>>>>>>>>>>> >>>>>>>>>>>> On Fri, May 31, 2019 at 10:47 AM Isiah Meadows < >>>>>>>>>>>> isiahmeadows at gmail.com> wrote: >>>>>>>>>>>> >>>>>>>>>>>>> If it's bundled by Rollup or Webpack into a single bundle, it's >>>>>>>>>>>>> equivalent to a single `<script type="module" src="...">` >>>>>>>>>>>>> pointing >>>>>>>>>>>>> towards the original entry point, excluding network requests.* >>>>>>>>>>>>> But in >>>>>>>>>>>>> either case, you aren't listing 50 scripts, you're only >>>>>>>>>>>>> listing the >>>>>>>>>>>>> entry module and importing child modules within parent >>>>>>>>>>>>> modules. Rollup >>>>>>>>>>>>> and Webpack do mostly the same thing browsers do when it comes >>>>>>>>>>>>> to >>>>>>>>>>>>> resolving dependencies, just they generate a bundle afterwards >>>>>>>>>>>>> where >>>>>>>>>>>>> browsers execute code afterwards. Also, it's worth noting that >>>>>>>>>>>>> the gap >>>>>>>>>>>>> between a single large request and multiple smaller requests >>>>>>>>>>>>> has >>>>>>>>>>>>> shrunk a lot since HTTP/2 came along, since it's binary, it >>>>>>>>>>>>> allows >>>>>>>>>>>>> requests and response data to be interleaved, it better >>>>>>>>>>>>> leverages the >>>>>>>>>>>>> underlying TCP protocol format, and it allows servers to send >>>>>>>>>>>>> data >>>>>>>>>>>>> pre-emptively without the client requesting it first. (Web >>>>>>>>>>>>> sockets are >>>>>>>>>>>>> built on this functionality.) It's still better to bundle in >>>>>>>>>>>>> general, >>>>>>>>>>>>> but it's less of a problem not to. >>>>>>>>>>>>> >>>>>>>>>>>>> This is *not* the case for `<script type="module">` elements - >>>>>>>>>>>>> those >>>>>>>>>>>>> operate more like inline scripts that happen to have the >>>>>>>>>>>>> ability to >>>>>>>>>>>>> `import`. >>>>>>>>>>>>> >>>>>>>>>>>>> Oh, and yes, I've loaded upwards of 50-100 modules in >>>>>>>>>>>>> development. 20 >>>>>>>>>>>>> modules is *easy* to achieve in single-page apps. >>>>>>>>>>>>> >>>>>>>>>>>>> * This is, of course, not the case if you are using pure ES6 >>>>>>>>>>>>> and you >>>>>>>>>>>>> aren't using any plugins to, say, run the original source >>>>>>>>>>>>> through >>>>>>>>>>>>> Babel for React + JSX or something. >>>>>>>>>>>>> >>>>>>>>>>>>> ----- >>>>>>>>>>>>> >>>>>>>>>>>>> Isiah Meadows >>>>>>>>>>>>> contact at isiahmeadows.com >>>>>>>>>>>>> www.isiahmeadows.com >>>>>>>>>>>>> On Sat, May 25, 2019 at 2:12 AM kai zhu <kaizhu256 at gmail.com> >>>>>>>>>>>>> wrote: >>>>>>>>>>>>> > >>>>>>>>>>>>> > Asynchronous loading differs only in >>>>>>>>>>>>> > that it takes more code to express the same logic and you >>>>>>>>>>>>> have to take >>>>>>>>>>>>> > into account concurrent requests (and you need to cache the >>>>>>>>>>>>> request, >>>>>>>>>>>>> > not the result), but it's otherwise the same from 1km away. >>>>>>>>>>>>> > >>>>>>>>>>>>> > >>>>>>>>>>>>> > so async-loading 50 ```<script type="module">``` tags >>>>>>>>>>>>> > has equivalent side-effect >>>>>>>>>>>>> > as sync-loading single webpack-rollup (of same 50 modules)? >>>>>>>>>>>>> > >>>>>>>>>>>>> > i have nagging suspicion of doubts. has anyone tried native >>>>>>>>>>>>> async-loading large numbers (>10) of >>>>>>>>>>>>> > ```<script type="module">``` tags, and verify it resolves >>>>>>>>>>>>> identically to using a single webpack-rollup? >>>>>>>>>>>>> > >>>>>>>>>>>>> > again, i'm not that knowledgeable on es-modules, so above >>>>>>>>>>>>> question may be trivially true, and i'm just not aware. >>>>>>>>>>>>> > >>>>>>>>>>>>> > -kai >>>>>>>>>>>>> > >>>>>>>>>>>>> > On 24 May 2019, at 23:41, Isiah Meadows < >>>>>>>>>>>>> isiahmeadows at gmail.com> wrote: >>>>>>>>>>>>> > >>>>>>>>>>>>> > There's two main reasons why it scales: >>>>>>>>>>>>> > >>>>>>>>>>>>> > 1. Modules are strongly encapsulated while minimizing global >>>>>>>>>>>>> pollution. >>>>>>>>>>>>> > 2. The resolution algorithm applies the same logic no matter >>>>>>>>>>>>> how many >>>>>>>>>>>>> > modules are loaded. >>>>>>>>>>>>> > >>>>>>>>>>>>> > It's much easier for it to scale when you write the code >>>>>>>>>>>>> unaware of >>>>>>>>>>>>> > how many modules you might be loading and unaware of how >>>>>>>>>>>>> deep their >>>>>>>>>>>>> > dependency graph is. Fewer assumptions here is key. It's an >>>>>>>>>>>>> > engineering problem, but a relatively simple one. >>>>>>>>>>>>> > >>>>>>>>>>>>> > If you want a short example of how sync module resolution >>>>>>>>>>>>> works, you >>>>>>>>>>>>> > can take a look at this little utility I wrote: >>>>>>>>>>>>> > https://github.com/isiahmeadows/simple-require-loader. That >>>>>>>>>>>>> doesn't >>>>>>>>>>>>> > asynchronously resolve modules, but it should help explain >>>>>>>>>>>>> the process >>>>>>>>>>>>> > from a synchronous standpoint. Asynchronous loading differs >>>>>>>>>>>>> only in >>>>>>>>>>>>> > that it takes more code to express the same logic and you >>>>>>>>>>>>> have to take >>>>>>>>>>>>> > into account concurrent requests (and you need to cache the >>>>>>>>>>>>> request, >>>>>>>>>>>>> > not the result), but it's otherwise the same from 1km away. >>>>>>>>>>>>> > >>>>>>>>>>>>> > ----- >>>>>>>>>>>>> > >>>>>>>>>>>>> > Isiah Meadows >>>>>>>>>>>>> > contact at isiahmeadows.com >>>>>>>>>>>>> > www.isiahmeadows.com >>>>>>>>>>>>> > >>>>>>>>>>>>> > On Thu, May 23, 2019 at 10:49 AM kai zhu < >>>>>>>>>>>>> kaizhu256 at gmail.com> wrote: >>>>>>>>>>>>> > >>>>>>>>>>>>> > >>>>>>>>>>>>> > actually, i admit i don't know what i'm talking about. just >>>>>>>>>>>>> generally confused (through ignorance) on how large-scale es-module >>>>>>>>>>>>> dependencies resolve when loaded/imported asynchronously. >>>>>>>>>>>>> > >>>>>>>>>>>>> > On Wed, May 22, 2019 at 10:42 PM Logan Smyth < >>>>>>>>>>>>> loganfsmyth at gmail.com> wrote: >>>>>>>>>>>>> > >>>>>>>>>>>>> > >>>>>>>>>>>>> > Can you elaborate on what loading state you need to keep >>>>>>>>>>>>> track of? What is the bottleneck that you run into? Also to be sure, when >>>>>>>>>>>>> you say async-load, do you mean `import()`? >>>>>>>>>>>>> > >>>>>>>>>>>>> > On Wed, May 22, 2019, 20:17 kai zhu <kaizhu256 at gmail.com> >>>>>>>>>>>>> wrote: >>>>>>>>>>>>> > >>>>>>>>>>>>> > >>>>>>>>>>>>> > i don't use es-modules. >>>>>>>>>>>>> > but with amd/requirejs, I start having trouble with >>>>>>>>>>>>> module-initializations in nodejs/browser at ~5 async modules (that may or >>>>>>>>>>>>> may not have circular-references). 10 would be hard, and 20 would be near >>>>>>>>>>>>> inhuman for me. >>>>>>>>>>>>> > >>>>>>>>>>>>> > can we say its somewhat impractical for most applications to >>>>>>>>>>>>> load more than 50 async modules (with some of them having >>>>>>>>>>>>> circular-references)? and perhaps better design/spec module-loading >>>>>>>>>>>>> mechanisms with this usability concern in mind? >>>>>>>>>>>>> > >>>>>>>>>>>>> > p.s. its also impractical for me to async-load 5 or more >>>>>>>>>>>>> modules without using globalThis to keep track of each module's >>>>>>>>>>>>> loading-state. >>>>>>>>>>>>> > _______________________________________________ >>>>>>>>>>>>> > es-discuss mailing list >>>>>>>>>>>>> > es-discuss at mozilla.org >>>>>>>>>>>>> > https://mail.mozilla.org/listinfo/es-discuss >>>>>>>>>>>>> > >>>>>>>>>>>>> > >>>>>>>>>>>>> > _______________________________________________ >>>>>>>>>>>>> > es-discuss mailing list >>>>>>>>>>>>> > es-discuss at mozilla.org >>>>>>>>>>>>> > https://mail.mozilla.org/listinfo/es-discuss >>>>>>>>>>>>> > >>>>>>>>>>>>> > >>>>>>>>>>>>> >>>>>>>>>>>> _______________________________________________ >>>>>>>>>>>> es-discuss mailing list >>>>>>>>>>>> es-discuss at mozilla.org >>>>>>>>>>>> https://mail.mozilla.org/listinfo/es-discuss >>>>>>>>>>>> >>>>>>>>>>> -------------- next part -------------- An HTML attachment was scrubbed... URL: <http://mail.mozilla.org/pipermail/es-discuss/attachments/20190602/f08cddbd/attachment-0001.html>
One option would be to utilize shortName
developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Statements/import#Import_an_export_with_a_more_convenient_alias
import { foo as foo1 } from "./aa.js";
const bar1 = { baz: foo1 };
export { bar1 };
import { foo as foo2 } from "./bb.js";
const bar2 = { baz: foo2 };
export { bar2 };
(async() => {
const {...bars} = await import("./inline.js");
console.log(bars);
})();
One option is to utilize ```shortName``` https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Statements/import#Import_an_export_with_a_more_convenient_alias ``` import {foo as foo1} from "./aa.js"; let bar1 = { baz: foo1 }; export { bar1 }; import {foo as foo2} from "./bb.js"; const bar2 = { baz: foo2 }; export { bar2 }; ``` On Sun, Jun 2, 2019 at 11:05 PM kai zhu <kaizhu256 at gmail.com> wrote: > not inline multiple ```export```'s, but inline multiple module-scopes. > > ```js > /* > * how do you inline the two es-modules below > * with colliding `foo` and `bar` variables? > * > * you can't unless you introduce new language-syntax > * to somehow delimit their scopes > */ > > // [hypothethical] es-module-scope delimiter > # es-module-scope "./inline.js" > > // module ./inline.js > import { foo } from "./aa.js" > const bar = { baz: foo }; > export { bar }; > > > > // [hypothethical] es-module-scope delimiter > # es-module-scope ./nextinline.js > > // module ./nextinline.js > import { foo } from "./bb.js" > const bar = { baz: foo }; > export { bar }; > ``` > > On Sun, Jun 2, 2019 at 2:54 PM guest271314 <guest271314 at gmail.com> wrote: > >> Multiple imports are already possible >> >> ``` >> import {inline} from "./inline.js"; >> import {nextInline} from "./nextInline.js"; >> >> const o = { >> a:1, b:2, c:3 >> }; >> >> // ... >> >> export {o, cities, video, inline, nextInline}; >> ``` >> >> Are you proposing multiple ```export```s? >> >> ``` >> export {o, cities, video, inline, nextInline}; >> o.c = 7; >> export {o}; >> ``` >> >> >> >> On Sun, Jun 2, 2019 at 6:19 PM kai zhu <kaizhu256 at gmail.com> wrote: >> >>> @guest271314 <guest271314 at gmail.com>, your example again is not a >>> [native] bundle of two or more inlined es-modules. its just a single >>> es-module that that fetches json data. >>> >>> i'm asking if its desirable to inline multiple es-modules into a single >>> file natively, e.g.: >>> >>> ``` >>> /* >>> * es-module.rollup.js >>> * this [hypothetical] rollup-file contains multiple inlined es-modules >>> * to improve load-performance in production-deployment. >>> */ >>> >>> // 1. inlined es-module ./main.js >>> import { foo } from "./counter.js" >>> import { bar } from "./display.js" >>> foo(bar); >>> >>> // 2. inlined es-module ./counter.js >>> var foo; >>> foo = function (bar) { >>> bar(); >>> }; >>> export { foo } >>> >>> // 3. inlined es-module ./display.js >>> var bar; >>> bar = function () { >>> console.log("hello world"); >>> }; >>> export { bar } >>> ``` >>> >>> this native es-module inline-capability may not be desirable to you, >>> which is fine. it would be a datapoint against this feature (and rely >>> instead on pre-emptive import-maps and http2-push, as explained by >>> @frederick and @isiah). >>> >>> >>> On Sun, Jun 2, 2019 at 11:22 AM guest271314 <guest271314 at gmail.com> >>> wrote: >>> >>>> 1) original-question - is native es-module's async-behavior desirable? >>>>> async side-effects are difficult to manage -- i conjecture that >>>>> async-loading 20 es-modules (with dependent side-effects) is not practical >>>>> for most mortals to handle. >>>> >>>> >>>> It depends on what *you *mean by "desirable" in a given context. >>>> >>>> There is no difference from loading 1 module and loading 1000 modules >>>> except for network cost, memory and disk space usage. >>>> >>>> Mortals can handle far more than loading 20 es-modules. >>>> >>>> What are the specific "side-effects" that you are referring to? >>>> >>>> describes the mechanism for how to hint the brower to pre-fetch 20 >>>>> es-modules. but if you pre-fetch, then is loading-behavior effectively >>>>> synchronous? >>>> >>>> >>>> Resources can be "pre-fetched" using various means. From caching the >>>> first request and using the cached data instead of making future requests >>>> for the same resources to storing one or more entire directories in the >>>> browser configuration folder using `requestFileSystem` (Chromiom/Chrome). >>>> >>>> but was unclear whether they were individual [async] ```<script >>>>> type="module">``` tags, or some es5-transpiled rollup >>>> >>>> >>>> There should not be any difference between the two approaches. If there >>>> is a difference then you should be able to clearly state what the >>>> difference is, and demonstrate the difference by reproduction, without >>>> speculating and not demonstrating a difference by means of reproduction. >>>> >>>> 2) the second-question about es-module rollups (which you and i are >>>>> debating) stemmed from @isiah's response -- if he and everyone-else use >>>>> es5-transpiled rollups (which i suspect), >>>> >>>> >>>> Do not care what "everyone-else" is supposedly doing. How can you >>>> possibly know what everyone-else is doing and even if you did know what >>>> third-parties are doing how does that affect what you are doing? >>>> >>>> then shouldn't it be desirable for es-modules to natively support >>>>> rollups as well? currently, there's no way to natively rollup multiple >>>>> es-modules into a single bundle. >>>> >>>> >>>> There are ways to "bundle" multiple modules into a single export >>>> "natively", as demonstrated at the previously posted code. >>>> >>>> Another example approach >>>> >>>> ``` >>>> // sync >>>> const o = { >>>> a:1, b:2, c:3 >>>> }; >>>> // async >>>> const cities = fetch(" >>>> https://gist.githubusercontent.com/guest271314/ffac94353ab16f42160e/raw/aaee70a3e351f6c7bc00178eabb5970a02df87e9/states.json >>>> ") >>>> .then(response => response.json()) >>>> .catch(e => {console.error(e); return "error fetching >>>> cities module"}); >>>> // async >>>> const video = fetch(" >>>> https://upload.wikimedia.org/wikipedia/commons/d/d9/120-cell.ogv") >>>> .then(response => response.blob()) >>>> .catch(e => {console.error(e); return "error fetching >>>> video module"}); >>>> // multiple "modules" exported >>>> export {o, cities, video}; >>>> ``` >>>> >>>> at single ```<script type="module">``` >>>> >>>> ``` >>>> <script type="module"> >>>> import * as o from "./script.js"; >>>> (async(mods) => { >>>> for (const [key, value] of mods) { >>>> if (value instanceof Promise) { >>>> console.log("async module", key, await value) >>>> } else { >>>> console.log("sync module", key, value); >>>> } >>>> } >>>> })(Object.entries(o)); >>>> </script> >>>> ``` >>>> >>>> Still there is no actual problem statement. Rather, there is conjecture >>>> without a definitive issue to solve. >>>> >>>> >>>> >>>> >>>> On Sun, Jun 2, 2019 at 3:54 AM kai zhu <kaizhu256 at gmail.com> wrote: >>>> >>>>> i apologize for poor framing of my questions. they are still >>>>> formative, but i can clarify abit as follows: >>>>> >>>>> 1) original-question - is native es-module's async-behavior >>>>> desirable? async side-effects are difficult to manage -- i conjecture that >>>>> async-loading 20 es-modules (with dependent side-effects) is not practical >>>>> for most mortals to handle. >>>>> @frederick describes the mechanism for how to hint the brower to >>>>> pre-fetch 20 es-modules. but if you pre-fetch, then is loading-behavior >>>>> effectively synchronous? >>>>> @isiah says he has experience loading 50-100 modules, but was unclear >>>>> whether they were individual [async] ```<script type="module">``` >>>>> tags, or some es5-transpiled rollup. >>>>> >>>>> i may be wrong about everything, as i'm a bit ignorant on what async >>>>> actually means in es-modules (and appreciate it, if someone can clarify >>>>> that). >>>>> >>>>> >>>>> >>>>> 2) the second-question about es-module rollups (which you and i are >>>>> debating) stemmed from @isiah's response -- if he and everyone-else use >>>>> es5-transpiled rollups (which i suspect), then shouldn't it be desirable >>>>> for es-modules to natively support rollups as well? currently, there's no >>>>> way to natively rollup multiple es-modules into a single bundle. >>>>> >>>>> this 2nd question also has implications about es-module's >>>>> async-behavior (because rollups "load" modules in sync/blocking fashion). >>>>> this could change side-effect behaviors between development-mode (20 >>>>> [async] ```<script type="module">``` tags) and production-mode (1 >>>>> rollup-bundle). again, i may be wrong about that, as i'm ignorant about >>>>> what async actually is in es-modules. >>>>> >>>>> -kai >>>>> >>>>> On Sat, Jun 1, 2019 at 9:22 PM guest271314 <guest271314 at gmail.com> >>>>> wrote: >>>>> >>>>>> > it doesn't actually ```import``` 1000+ es-modules inside the >>>>>> rollup-file. it just creates one es-module that exports a dictionary -- and >>>>>> assigns the dictionary 1000+ vanilla json-objects and functions. >>>>>> >>>>>> The code provides a means to fetch N resources and export those >>>>>> resources within a single object. >>>>>> >>>>>> > currently, as i'm aware, nobody uses native es-modules in >>>>>> production, because it cannot be rolled-up. >>>>>> > in practice es-modules are [babel] transpiled down to es5-amd (or >>>>>> similar) for rollup-purposes. >>>>>> > >>>>>> > if we're actually committed to native es-modules, then we either >>>>>> > 1) need to depend on embedders like loading-dev at chromium.org to >>>>>> create sophisticated cache-systems, or >>>>>> > 2) introduce new language-syntax to delimit es-modules for >>>>>> rollup-purposes, e.g. >>>>>> >>>>>> You still have not clearly defined what you mean by "rolled-up". That >>>>>> language appears to be a random nickname, not any immutable principle that >>>>>> individuals are bound to recognize or observe (even if "rolled-up" were >>>>>> some form of a coding style or standard). >>>>>> >>>>>> Nor is it clear what you mean by "production". >>>>>> >>>>>> There is no external central committee that stamps code as >>>>>> "production". Even if there were no individual is obliged to submit to such >>>>>> a procedure nor have any concern for such an arbitrary and irrelevant >>>>>> presumptive review of code. >>>>>> >>>>>> The only observable points are input and output. In general, how >>>>>> output is achieved is immaterial. If there are specific restrictions as to >>>>>> how the output can be achieved then those restrictions need to be clearly >>>>>> defined. >>>>>> >>>>>> >>>>>> >>>>>> The original post asked "how many async-modules can js-app >>>>>> practically load?" and mentioned "circular-references" (the thread >>>>>> appears to mainly be about one or more coding styles, not code itself) >>>>>> though as yet no code has been posted which demonstrates >>>>>> "circular-references" or any other coding problem. >>>>>> >>>>>> On Sun, Jun 2, 2019 at 1:30 AM kai zhu <kaizhu256 at gmail.com> wrote: >>>>>> >>>>>>> i played around with your code in jsfiddle [1], and understand it a >>>>>>> little more. >>>>>>> it doesn't actually ```import``` 1000+ es-modules inside the >>>>>>> rollup-file. >>>>>>> it just creates one es-module that exports a dictionary >>>>>>> -- and assigns the dictionary 1000+ vanilla json-objects and >>>>>>> functions. >>>>>>> >>>>>>> ```js >>>>>>> // the "rollup-file" is a single es-module >>>>>>> // that exports 1000+ vanilla dictionary-entries >>>>>>> const modules = {}; >>>>>>> >>>>>>> // this is not a es-module, nor is it rolled-up (external fetch) >>>>>>> modules.image = <await fetch json from gist.github.com> >>>>>>> >>>>>>> // this is not a [rolled-up] es-module >>>>>>> modules.fn = function () {...} >>>>>>> >>>>>>> // these are not [rolled-up] es-modules >>>>>>> Object.assign(modules, <1000 json-entries>) >>>>>>> >>>>>>> export {modules} >>>>>>> ``` >>>>>>> >>>>>>> currently, as i'm aware, nobody uses native es-modules in >>>>>>> production, because it cannot be rolled-up. >>>>>>> in practice es-modules are [babel] transpiled down to es5-amd (or >>>>>>> similar) for rollup-purposes. >>>>>>> >>>>>>> if we're actually committed to native es-modules, then we either >>>>>>> 1) need to depend on embedders like loading-dev at chromium.org to >>>>>>> create sophisticated cache-systems, or >>>>>>> 2) introduce new language-syntax to delimit es-modules for >>>>>>> rollup-purposes, e.g. >>>>>>> >>>>>>> ```js >>>>>>> // rollup.js with [hypothetical] # delimited es-modules >>>>>>> # module aa >>>>>>> import {bb} as bb; >>>>>>> export ...; >>>>>>> >>>>>>> # module bb >>>>>>> export ...; >>>>>>> ``` >>>>>>> >>>>>>> i'm generally skeptical of option 1, given how poorly npmjs.com has >>>>>>> handled similar problems deduplicating children in node_modules/ directory. >>>>>>> >>>>>>> [1] jsfiddle pseudo-module rollup >>>>>>> https://jsfiddle.net/06twrLfd/ >>>>>>> >>>>>>> On Sat, Jun 1, 2019 at 5:30 PM guest271314 <guest271314 at gmail.com> >>>>>>> wrote: >>>>>>> >>>>>>>> > your rollup solution is interesting, >>>>>>>> >>>>>>>> What is "rollup" referring to? >>>>>>>> >>>>>>>> > but i get an error when run in chrome (i changed to n=20 to >>>>>>>> prevent name-collision, but it still happens). >>>>>>>> >>>>>>>> The duplicate ("collision") entry an ```try..catch``` block is >>>>>>>> included in the code to demonstrate given an array of module names to be >>>>>>>> exported and imported as identifiers 1) duplicate entries can be filtered; >>>>>>>> 2) if a plain object is exported duplicate identifiers ("collision") is not >>>>>>>> possible as a JavaScript plain object does not have duplicate property >>>>>>>> names ("collision"); if there is an issue with identifiers in a module the >>>>>>>> cause would not be the number of async-modules loaded ("how many"), but the >>>>>>>> naming of the identifiers within the code, using or not using ```const``` >>>>>>>> or ```let```. Still not sure what the actual issue is? >>>>>>>> >>>>>>>> > don't completely understand how it works, >>>>>>>> >>>>>>>> Use an ```async``` function to fetch data, check for the described >>>>>>>> "collision" , create a ```data URI``` to be imported, optionally, append >>>>>>>> addition code to be executed within the ```<script type="module">```. >>>>>>>> >>>>>>>> > but not sure of suitability for production-use, because of its >>>>>>>> dynamic <script> tag generation. >>>>>>>> >>>>>>>> What is the issue with dynamic ```<script>``` tag generation? >>>>>>>> >>>>>>>> There is more than one possible approach to achieve the presumptive >>>>>>>> requirement, that is still not clear to the exclusion of what is not the >>>>>>>> expected result. >>>>>>>> >>>>>>>> There were no restrictions described at the OP and following >>>>>>>> messages other than other than >>>>>>>> >>>>>>>> > pure-es6 application with 20 es-modules rolled-up into one >>>>>>>> [production] bundle? >>>>>>>> >>>>>>>> The example code uses only JavaScript implementation shipped with >>>>>>>> the browser without any external, third-party libraries. >>>>>>>> >>>>>>>> What standard or definition are you relying for the meaning of the >>>>>>>> term "production-use"? What procedure are you using to determine if code is >>>>>>>> "production-use" "suitable"? How is that procedure related to "how many >>>>>>>> async-modules can js-app practically load?"? >>>>>>>> >>>>>>>> >>>>>>>> >>>>>>>> On Sat, Jun 1, 2019 at 9:42 PM kai zhu <kaizhu256 at gmail.com> wrote: >>>>>>>> >>>>>>>>> your rollup solution is interesting, but i get an error when run >>>>>>>>> in chrome (i changed to n=20 to prevent name-collision, but it still >>>>>>>>> happens). don't completely understand how it works, but not sure of >>>>>>>>> suitability for production-use, because of its dynamic <script> tag >>>>>>>>> generation. >>>>>>>>> >>>>>>>>> ```console >>>>>>>>> ReferenceError: module names ["yeqjqb02mvg3yze26rc5"] are not >>>>>>>>> unique >>>>>>>>> at >>>>>>>>> data:application/javascript,%0A%20%20%20%20%20%20const%20modules... >>>>>>>>> ``` >>>>>>>>> >>>>>>>>> On Sat, Jun 1, 2019 at 2:33 PM guest271314 <guest271314 at gmail.com> >>>>>>>>> wrote: >>>>>>>>> >>>>>>>>>> Re: how many async-modules can js-app practically load? >>>>>>>>>> >>>>>>>>>> An example of exporting and importing loading 1000 properties in >>>>>>>>>> a single module, where duplicate property names are checked for. Since >>>>>>>>>> JavaScript plain objects cannot have duplicate property names there should >>>>>>>>>> not be any "collisions"; the code can check for and modify the object to be >>>>>>>>>> exported, though the last duplicate property name will be exported without >>>>>>>>>> any errors thrown unless the code is composed to throw such an error. >>>>>>>>>> >>>>>>>>>> ``` >>>>>>>>>> (async() => { >>>>>>>>>> const oneThousandModules = encodeURIComponent( >>>>>>>>>> // substitute rand for a Set of module names to be exported >>>>>>>>>> // e.g. const moduleNames = ['moduleA', 'moduleB', >>>>>>>>>> ...moduleZ] >>>>>>>>>> ` >>>>>>>>>> const modules = {}; >>>>>>>>>> // set a function to be exported >>>>>>>>>> modules.fn = function() {return 'a function'}; >>>>>>>>>> // function to set (1000) 'random' module names to be >>>>>>>>>> exported >>>>>>>>>> const rand = (seed = >>>>>>>>>> 'abcdefghijklmnopqrstuvwxyz0123456789', n = 5, len = seed.length) => >>>>>>>>>> '.'.repeat(n).replace(/./g, _ => seed[~~(Math.random() * >>>>>>>>>> len)]); >>>>>>>>>> // use Set for unique module identifiers >>>>>>>>>> const moduleNames = [...Array(1000)].map(_ => rand()); >>>>>>>>>> const moduleIdentifiers = new Set(moduleNames); >>>>>>>>>> // below line will cause ReferenceError to be thrown >>>>>>>>>> moduleNames.push(moduleNames[0]); >>>>>>>>>> try { >>>>>>>>>> if (moduleIdentifiers.size !== moduleNames.length) { >>>>>>>>>> // check for duplicates >>>>>>>>>> const duplicates = moduleNames.filter((moduleName, >>>>>>>>>> index) => moduleNames.indexOf(moduleName) !== index); >>>>>>>>>> // notification of duplicate module names >>>>>>>>>> throw new ReferenceError('module names ' + >>>>>>>>>> JSON.stringify(duplicates) + ' are not unique'); >>>>>>>>>> // perform the designated task if duplicate module >>>>>>>>>> names are found here >>>>>>>>>> } >>>>>>>>>> } catch (e) { >>>>>>>>>> console.error(e); >>>>>>>>>> console.trace(); >>>>>>>>>> } >>>>>>>>>> // get, set (sync or async) exported module here >>>>>>>>>> Object.assign(modules, ...[...moduleIdentifiers].map((id, >>>>>>>>>> value) => ({[id]:value}))); >>>>>>>>>> // since JavaScript plain object cannot have duplicate >>>>>>>>>> property names >>>>>>>>>> // modules object will still be exported without >>>>>>>>>> duplicate property names >>>>>>>>>> // without collisions >>>>>>>>>> export {modules} >>>>>>>>>> `); >>>>>>>>>> const scriptText = `import {modules} from >>>>>>>>>> "data:application/javascript,${oneThousandModules};${encodeURIComponent('console.log(modules);for >>>>>>>>>> (const key in modules) {if (typeof modules[key] === \'function\') >>>>>>>>>> {console.log(modules[key]());}}')}"`; >>>>>>>>>> const script = document.createElement("script"); >>>>>>>>>> script.type = "module"; >>>>>>>>>> script.textContent = scriptText; >>>>>>>>>> document.head.appendChild(script); >>>>>>>>>> })(); >>>>>>>>>> ``` >>>>>>>>>> >>>>>>>>>> plnkr https://plnkr.co/edit/CgEhBY?p=preview >>>>>>>>>> >>>>>>>>>> On Sat, Jun 1, 2019 at 1:51 AM kai zhu <kaizhu256 at gmail.com> >>>>>>>>>> wrote: >>>>>>>>>> >>>>>>>>>>> > Place all of the code to be exported in 1 file? >>>>>>>>>>> >>>>>>>>>>> that obviously will not work, because of module-scope >>>>>>>>>>> collision. can anyone share their experience on deploying a [babel-free] >>>>>>>>>>> pure-es6 application with 20 es-modules rolled-up into one [production] >>>>>>>>>>> bundle? is it even possible? >>>>>>>>>>> >>>>>>>>>>> >>>>>>>>>>> On Fri, May 31, 2019 at 7:55 PM guest271314 < >>>>>>>>>>> guest271314 at gmail.com> wrote: >>>>>>>>>>> >>>>>>>>>>>> > how would i transition from development-mode (20 es-module >>>>>>>>>>>> files) -> production-mode (1 rollup file)? >>>>>>>>>>>> >>>>>>>>>>>> Place all of the code to be exported in 1 file? >>>>>>>>>>>> >>>>>>>>>>>> > with some of them having circular-references >>>>>>>>>>>> >>>>>>>>>>>> Not certain how that is possible when using ```import``` within >>>>>>>>>>>> ```<script type="module">```? >>>>>>>>>>>> >>>>>>>>>>>> > how many async-modules can js-app practically load? >>>>>>>>>>>> >>>>>>>>>>>> Again, how many have you tried to load? 100? 500? 1000? Either >>>>>>>>>>>> should be possible. >>>>>>>>>>>> >>>>>>>>>>>> What specific issue are you actually to resolve? >>>>>>>>>>>> >>>>>>>>>>>> On Fri, May 31, 2019 at 5:40 PM kai zhu <kaizhu256 at gmail.com> >>>>>>>>>>>> wrote: >>>>>>>>>>>> >>>>>>>>>>>>> > Oh, and yes, I've loaded upwards of 50-100 modules in >>>>>>>>>>>>> development. 20 >>>>>>>>>>>>> modules is *easy* to achieve in single-page apps. >>>>>>>>>>>>> >>>>>>>>>>>>> was that with some combination of babel/rollup/webpack or >>>>>>>>>>>>> pure-es6? >>>>>>>>>>>>> if i want to develop a pure-es6 webapp (no babel), how would i >>>>>>>>>>>>> transition from development-mode (20 es-module files) -> production-mode (1 >>>>>>>>>>>>> rollup file)? >>>>>>>>>>>>> >>>>>>>>>>>>> >>>>>>>>>>>>> On Fri, May 31, 2019 at 10:47 AM Isiah Meadows < >>>>>>>>>>>>> isiahmeadows at gmail.com> wrote: >>>>>>>>>>>>> >>>>>>>>>>>>>> If it's bundled by Rollup or Webpack into a single bundle, >>>>>>>>>>>>>> it's >>>>>>>>>>>>>> equivalent to a single `<script type="module" src="...">` >>>>>>>>>>>>>> pointing >>>>>>>>>>>>>> towards the original entry point, excluding network >>>>>>>>>>>>>> requests.* But in >>>>>>>>>>>>>> either case, you aren't listing 50 scripts, you're only >>>>>>>>>>>>>> listing the >>>>>>>>>>>>>> entry module and importing child modules within parent >>>>>>>>>>>>>> modules. Rollup >>>>>>>>>>>>>> and Webpack do mostly the same thing browsers do when it >>>>>>>>>>>>>> comes to >>>>>>>>>>>>>> resolving dependencies, just they generate a bundle >>>>>>>>>>>>>> afterwards where >>>>>>>>>>>>>> browsers execute code afterwards. Also, it's worth noting >>>>>>>>>>>>>> that the gap >>>>>>>>>>>>>> between a single large request and multiple smaller requests >>>>>>>>>>>>>> has >>>>>>>>>>>>>> shrunk a lot since HTTP/2 came along, since it's binary, it >>>>>>>>>>>>>> allows >>>>>>>>>>>>>> requests and response data to be interleaved, it better >>>>>>>>>>>>>> leverages the >>>>>>>>>>>>>> underlying TCP protocol format, and it allows servers to send >>>>>>>>>>>>>> data >>>>>>>>>>>>>> pre-emptively without the client requesting it first. (Web >>>>>>>>>>>>>> sockets are >>>>>>>>>>>>>> built on this functionality.) It's still better to bundle in >>>>>>>>>>>>>> general, >>>>>>>>>>>>>> but it's less of a problem not to. >>>>>>>>>>>>>> >>>>>>>>>>>>>> This is *not* the case for `<script type="module">` elements >>>>>>>>>>>>>> - those >>>>>>>>>>>>>> operate more like inline scripts that happen to have the >>>>>>>>>>>>>> ability to >>>>>>>>>>>>>> `import`. >>>>>>>>>>>>>> >>>>>>>>>>>>>> Oh, and yes, I've loaded upwards of 50-100 modules in >>>>>>>>>>>>>> development. 20 >>>>>>>>>>>>>> modules is *easy* to achieve in single-page apps. >>>>>>>>>>>>>> >>>>>>>>>>>>>> * This is, of course, not the case if you are using pure ES6 >>>>>>>>>>>>>> and you >>>>>>>>>>>>>> aren't using any plugins to, say, run the original source >>>>>>>>>>>>>> through >>>>>>>>>>>>>> Babel for React + JSX or something. >>>>>>>>>>>>>> >>>>>>>>>>>>>> ----- >>>>>>>>>>>>>> >>>>>>>>>>>>>> Isiah Meadows >>>>>>>>>>>>>> contact at isiahmeadows.com >>>>>>>>>>>>>> www.isiahmeadows.com >>>>>>>>>>>>>> On Sat, May 25, 2019 at 2:12 AM kai zhu <kaizhu256 at gmail.com> >>>>>>>>>>>>>> wrote: >>>>>>>>>>>>>> > >>>>>>>>>>>>>> > Asynchronous loading differs only in >>>>>>>>>>>>>> > that it takes more code to express the same logic and you >>>>>>>>>>>>>> have to take >>>>>>>>>>>>>> > into account concurrent requests (and you need to cache the >>>>>>>>>>>>>> request, >>>>>>>>>>>>>> > not the result), but it's otherwise the same from 1km away. >>>>>>>>>>>>>> > >>>>>>>>>>>>>> > >>>>>>>>>>>>>> > so async-loading 50 ```<script type="module">``` tags >>>>>>>>>>>>>> > has equivalent side-effect >>>>>>>>>>>>>> > as sync-loading single webpack-rollup (of same 50 modules)? >>>>>>>>>>>>>> > >>>>>>>>>>>>>> > i have nagging suspicion of doubts. has anyone tried >>>>>>>>>>>>>> native async-loading large numbers (>10) of >>>>>>>>>>>>>> > ```<script type="module">``` tags, and verify it resolves >>>>>>>>>>>>>> identically to using a single webpack-rollup? >>>>>>>>>>>>>> > >>>>>>>>>>>>>> > again, i'm not that knowledgeable on es-modules, so above >>>>>>>>>>>>>> question may be trivially true, and i'm just not aware. >>>>>>>>>>>>>> > >>>>>>>>>>>>>> > -kai >>>>>>>>>>>>>> > >>>>>>>>>>>>>> > On 24 May 2019, at 23:41, Isiah Meadows < >>>>>>>>>>>>>> isiahmeadows at gmail.com> wrote: >>>>>>>>>>>>>> > >>>>>>>>>>>>>> > There's two main reasons why it scales: >>>>>>>>>>>>>> > >>>>>>>>>>>>>> > 1. Modules are strongly encapsulated while minimizing >>>>>>>>>>>>>> global pollution. >>>>>>>>>>>>>> > 2. The resolution algorithm applies the same logic no >>>>>>>>>>>>>> matter how many >>>>>>>>>>>>>> > modules are loaded. >>>>>>>>>>>>>> > >>>>>>>>>>>>>> > It's much easier for it to scale when you write the code >>>>>>>>>>>>>> unaware of >>>>>>>>>>>>>> > how many modules you might be loading and unaware of how >>>>>>>>>>>>>> deep their >>>>>>>>>>>>>> > dependency graph is. Fewer assumptions here is key. It's an >>>>>>>>>>>>>> > engineering problem, but a relatively simple one. >>>>>>>>>>>>>> > >>>>>>>>>>>>>> > If you want a short example of how sync module resolution >>>>>>>>>>>>>> works, you >>>>>>>>>>>>>> > can take a look at this little utility I wrote: >>>>>>>>>>>>>> > https://github.com/isiahmeadows/simple-require-loader. >>>>>>>>>>>>>> That doesn't >>>>>>>>>>>>>> > asynchronously resolve modules, but it should help explain >>>>>>>>>>>>>> the process >>>>>>>>>>>>>> > from a synchronous standpoint. Asynchronous loading differs >>>>>>>>>>>>>> only in >>>>>>>>>>>>>> > that it takes more code to express the same logic and you >>>>>>>>>>>>>> have to take >>>>>>>>>>>>>> > into account concurrent requests (and you need to cache the >>>>>>>>>>>>>> request, >>>>>>>>>>>>>> > not the result), but it's otherwise the same from 1km away. >>>>>>>>>>>>>> > >>>>>>>>>>>>>> > ----- >>>>>>>>>>>>>> > >>>>>>>>>>>>>> > Isiah Meadows >>>>>>>>>>>>>> > contact at isiahmeadows.com >>>>>>>>>>>>>> > www.isiahmeadows.com >>>>>>>>>>>>>> > >>>>>>>>>>>>>> > On Thu, May 23, 2019 at 10:49 AM kai zhu < >>>>>>>>>>>>>> kaizhu256 at gmail.com> wrote: >>>>>>>>>>>>>> > >>>>>>>>>>>>>> > >>>>>>>>>>>>>> > actually, i admit i don't know what i'm talking about. >>>>>>>>>>>>>> just generally confused (through ignorance) on how large-scale es-module >>>>>>>>>>>>>> dependencies resolve when loaded/imported asynchronously. >>>>>>>>>>>>>> > >>>>>>>>>>>>>> > On Wed, May 22, 2019 at 10:42 PM Logan Smyth < >>>>>>>>>>>>>> loganfsmyth at gmail.com> wrote: >>>>>>>>>>>>>> > >>>>>>>>>>>>>> > >>>>>>>>>>>>>> > Can you elaborate on what loading state you need to keep >>>>>>>>>>>>>> track of? What is the bottleneck that you run into? Also to be sure, when >>>>>>>>>>>>>> you say async-load, do you mean `import()`? >>>>>>>>>>>>>> > >>>>>>>>>>>>>> > On Wed, May 22, 2019, 20:17 kai zhu <kaizhu256 at gmail.com> >>>>>>>>>>>>>> wrote: >>>>>>>>>>>>>> > >>>>>>>>>>>>>> > >>>>>>>>>>>>>> > i don't use es-modules. >>>>>>>>>>>>>> > but with amd/requirejs, I start having trouble with >>>>>>>>>>>>>> module-initializations in nodejs/browser at ~5 async modules (that may or >>>>>>>>>>>>>> may not have circular-references). 10 would be hard, and 20 would be near >>>>>>>>>>>>>> inhuman for me. >>>>>>>>>>>>>> > >>>>>>>>>>>>>> > can we say its somewhat impractical for most applications >>>>>>>>>>>>>> to load more than 50 async modules (with some of them having >>>>>>>>>>>>>> circular-references)? and perhaps better design/spec module-loading >>>>>>>>>>>>>> mechanisms with this usability concern in mind? >>>>>>>>>>>>>> > >>>>>>>>>>>>>> > p.s. its also impractical for me to async-load 5 or more >>>>>>>>>>>>>> modules without using globalThis to keep track of each module's >>>>>>>>>>>>>> loading-state. >>>>>>>>>>>>>> > _______________________________________________ >>>>>>>>>>>>>> > es-discuss mailing list >>>>>>>>>>>>>> > es-discuss at mozilla.org >>>>>>>>>>>>>> > https://mail.mozilla.org/listinfo/es-discuss >>>>>>>>>>>>>> > >>>>>>>>>>>>>> > >>>>>>>>>>>>>> > _______________________________________________ >>>>>>>>>>>>>> > es-discuss mailing list >>>>>>>>>>>>>> > es-discuss at mozilla.org >>>>>>>>>>>>>> > https://mail.mozilla.org/listinfo/es-discuss >>>>>>>>>>>>>> > >>>>>>>>>>>>>> > >>>>>>>>>>>>>> >>>>>>>>>>>>> _______________________________________________ >>>>>>>>>>>>> es-discuss mailing list >>>>>>>>>>>>> es-discuss at mozilla.org >>>>>>>>>>>>> https://mail.mozilla.org/listinfo/es-discuss >>>>>>>>>>>>> >>>>>>>>>>>> -------------- next part -------------- An HTML attachment was scrubbed... URL: <http://mail.mozilla.org/pipermail/es-discuss/attachments/20190603/f6113d23/attachment-0001.html>
but that requires coordination among modules, which is not always possible. the idea is to inline/rollup es-modules that may not have come from same developers (and whom are unaware their es-modules collide w/ others when rolled-up).
you should be able to natively transition from development-env (individual es-modules) -> production-env (rolled-up es-modules), w/o down-transpiling
to es5-amdjs.
but that requires coordination among modules, which is not always possible. the idea is to inline/rollup es-modules that may not have come from same developers (and whom are unaware their es-modules collide w/ others when rolled-up). you should be able to natively transition from development-env (individual es-modules) -> production-env (rolled-up es-modules), w/o down-transpiling to es5-amdjs. On Sun, Jun 2, 2019 at 8:29 PM guest271314 <guest271314 at gmail.com> wrote: > One option is to utilize ```shortName``` > https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Statements/import#Import_an_export_with_a_more_convenient_alias > > ``` > import {foo as foo1} from "./aa.js"; > let bar1 = { baz: foo1 }; > export { bar1 }; > > import {foo as foo2} from "./bb.js"; > const bar2 = { baz: foo2 }; > export { bar2 }; > ``` > > On Sun, Jun 2, 2019 at 11:05 PM kai zhu <kaizhu256 at gmail.com> wrote: > >> not inline multiple ```export```'s, but inline multiple module-scopes. >> >> ```js >> /* >> * how do you inline the two es-modules below >> * with colliding `foo` and `bar` variables? >> * >> * you can't unless you introduce new language-syntax >> * to somehow delimit their scopes >> */ >> >> // [hypothethical] es-module-scope delimiter >> # es-module-scope "./inline.js" >> >> // module ./inline.js >> import { foo } from "./aa.js" >> const bar = { baz: foo }; >> export { bar }; >> >> >> >> // [hypothethical] es-module-scope delimiter >> # es-module-scope ./nextinline.js >> >> // module ./nextinline.js >> import { foo } from "./bb.js" >> const bar = { baz: foo }; >> export { bar }; >> ``` >> >> On Sun, Jun 2, 2019 at 2:54 PM guest271314 <guest271314 at gmail.com> wrote: >> >>> Multiple imports are already possible >>> >>> ``` >>> import {inline} from "./inline.js"; >>> import {nextInline} from "./nextInline.js"; >>> >>> const o = { >>> a:1, b:2, c:3 >>> }; >>> >>> // ... >>> >>> export {o, cities, video, inline, nextInline}; >>> ``` >>> >>> Are you proposing multiple ```export```s? >>> >>> ``` >>> export {o, cities, video, inline, nextInline}; >>> o.c = 7; >>> export {o}; >>> ``` >>> >>> >>> >>> On Sun, Jun 2, 2019 at 6:19 PM kai zhu <kaizhu256 at gmail.com> wrote: >>> >>>> @guest271314 <guest271314 at gmail.com>, your example again is not a >>>> [native] bundle of two or more inlined es-modules. its just a single >>>> es-module that that fetches json data. >>>> >>>> i'm asking if its desirable to inline multiple es-modules into a single >>>> file natively, e.g.: >>>> >>>> ``` >>>> /* >>>> * es-module.rollup.js >>>> * this [hypothetical] rollup-file contains multiple inlined es-modules >>>> * to improve load-performance in production-deployment. >>>> */ >>>> >>>> // 1. inlined es-module ./main.js >>>> import { foo } from "./counter.js" >>>> import { bar } from "./display.js" >>>> foo(bar); >>>> >>>> // 2. inlined es-module ./counter.js >>>> var foo; >>>> foo = function (bar) { >>>> bar(); >>>> }; >>>> export { foo } >>>> >>>> // 3. inlined es-module ./display.js >>>> var bar; >>>> bar = function () { >>>> console.log("hello world"); >>>> }; >>>> export { bar } >>>> ``` >>>> >>>> this native es-module inline-capability may not be desirable to you, >>>> which is fine. it would be a datapoint against this feature (and rely >>>> instead on pre-emptive import-maps and http2-push, as explained by >>>> @frederick and @isiah). >>>> >>>> >>>> On Sun, Jun 2, 2019 at 11:22 AM guest271314 <guest271314 at gmail.com> >>>> wrote: >>>> >>>>> 1) original-question - is native es-module's async-behavior >>>>>> desirable? async side-effects are difficult to manage -- i conjecture that >>>>>> async-loading 20 es-modules (with dependent side-effects) is not practical >>>>>> for most mortals to handle. >>>>> >>>>> >>>>> It depends on what *you *mean by "desirable" in a given context. >>>>> >>>>> There is no difference from loading 1 module and loading 1000 modules >>>>> except for network cost, memory and disk space usage. >>>>> >>>>> Mortals can handle far more than loading 20 es-modules. >>>>> >>>>> What are the specific "side-effects" that you are referring to? >>>>> >>>>> describes the mechanism for how to hint the brower to pre-fetch 20 >>>>>> es-modules. but if you pre-fetch, then is loading-behavior effectively >>>>>> synchronous? >>>>> >>>>> >>>>> Resources can be "pre-fetched" using various means. From caching the >>>>> first request and using the cached data instead of making future requests >>>>> for the same resources to storing one or more entire directories in the >>>>> browser configuration folder using `requestFileSystem` (Chromiom/Chrome). >>>>> >>>>> but was unclear whether they were individual [async] ```<script >>>>>> type="module">``` tags, or some es5-transpiled rollup >>>>> >>>>> >>>>> There should not be any difference between the two approaches. If >>>>> there is a difference then you should be able to clearly state what the >>>>> difference is, and demonstrate the difference by reproduction, without >>>>> speculating and not demonstrating a difference by means of reproduction. >>>>> >>>>> 2) the second-question about es-module rollups (which you and i are >>>>>> debating) stemmed from @isiah's response -- if he and everyone-else use >>>>>> es5-transpiled rollups (which i suspect), >>>>> >>>>> >>>>> Do not care what "everyone-else" is supposedly doing. How can you >>>>> possibly know what everyone-else is doing and even if you did know what >>>>> third-parties are doing how does that affect what you are doing? >>>>> >>>>> then shouldn't it be desirable for es-modules to natively support >>>>>> rollups as well? currently, there's no way to natively rollup multiple >>>>>> es-modules into a single bundle. >>>>> >>>>> >>>>> There are ways to "bundle" multiple modules into a single export >>>>> "natively", as demonstrated at the previously posted code. >>>>> >>>>> Another example approach >>>>> >>>>> ``` >>>>> // sync >>>>> const o = { >>>>> a:1, b:2, c:3 >>>>> }; >>>>> // async >>>>> const cities = fetch(" >>>>> https://gist.githubusercontent.com/guest271314/ffac94353ab16f42160e/raw/aaee70a3e351f6c7bc00178eabb5970a02df87e9/states.json >>>>> ") >>>>> .then(response => response.json()) >>>>> .catch(e => {console.error(e); return "error fetching >>>>> cities module"}); >>>>> // async >>>>> const video = fetch(" >>>>> https://upload.wikimedia.org/wikipedia/commons/d/d9/120-cell.ogv") >>>>> .then(response => response.blob()) >>>>> .catch(e => {console.error(e); return "error fetching >>>>> video module"}); >>>>> // multiple "modules" exported >>>>> export {o, cities, video}; >>>>> ``` >>>>> >>>>> at single ```<script type="module">``` >>>>> >>>>> ``` >>>>> <script type="module"> >>>>> import * as o from "./script.js"; >>>>> (async(mods) => { >>>>> for (const [key, value] of mods) { >>>>> if (value instanceof Promise) { >>>>> console.log("async module", key, await value) >>>>> } else { >>>>> console.log("sync module", key, value); >>>>> } >>>>> } >>>>> })(Object.entries(o)); >>>>> </script> >>>>> ``` >>>>> >>>>> Still there is no actual problem statement. Rather, there is >>>>> conjecture without a definitive issue to solve. >>>>> >>>>> >>>>> >>>>> >>>>> On Sun, Jun 2, 2019 at 3:54 AM kai zhu <kaizhu256 at gmail.com> wrote: >>>>> >>>>>> i apologize for poor framing of my questions. they are still >>>>>> formative, but i can clarify abit as follows: >>>>>> >>>>>> 1) original-question - is native es-module's async-behavior >>>>>> desirable? async side-effects are difficult to manage -- i conjecture that >>>>>> async-loading 20 es-modules (with dependent side-effects) is not practical >>>>>> for most mortals to handle. >>>>>> @frederick describes the mechanism for how to hint the brower to >>>>>> pre-fetch 20 es-modules. but if you pre-fetch, then is loading-behavior >>>>>> effectively synchronous? >>>>>> @isiah says he has experience loading 50-100 modules, but was unclear >>>>>> whether they were individual [async] ```<script type="module">``` >>>>>> tags, or some es5-transpiled rollup. >>>>>> >>>>>> i may be wrong about everything, as i'm a bit ignorant on what async >>>>>> actually means in es-modules (and appreciate it, if someone can clarify >>>>>> that). >>>>>> >>>>>> >>>>>> >>>>>> 2) the second-question about es-module rollups (which you and i are >>>>>> debating) stemmed from @isiah's response -- if he and everyone-else use >>>>>> es5-transpiled rollups (which i suspect), then shouldn't it be desirable >>>>>> for es-modules to natively support rollups as well? currently, there's no >>>>>> way to natively rollup multiple es-modules into a single bundle. >>>>>> >>>>>> this 2nd question also has implications about es-module's >>>>>> async-behavior (because rollups "load" modules in sync/blocking fashion). >>>>>> this could change side-effect behaviors between development-mode (20 >>>>>> [async] ```<script type="module">``` tags) and production-mode (1 >>>>>> rollup-bundle). again, i may be wrong about that, as i'm ignorant about >>>>>> what async actually is in es-modules. >>>>>> >>>>>> -kai >>>>>> >>>>>> On Sat, Jun 1, 2019 at 9:22 PM guest271314 <guest271314 at gmail.com> >>>>>> wrote: >>>>>> >>>>>>> > it doesn't actually ```import``` 1000+ es-modules inside the >>>>>>> rollup-file. it just creates one es-module that exports a dictionary -- and >>>>>>> assigns the dictionary 1000+ vanilla json-objects and functions. >>>>>>> >>>>>>> The code provides a means to fetch N resources and export those >>>>>>> resources within a single object. >>>>>>> >>>>>>> > currently, as i'm aware, nobody uses native es-modules in >>>>>>> production, because it cannot be rolled-up. >>>>>>> > in practice es-modules are [babel] transpiled down to es5-amd (or >>>>>>> similar) for rollup-purposes. >>>>>>> > >>>>>>> > if we're actually committed to native es-modules, then we either >>>>>>> > 1) need to depend on embedders like loading-dev at chromium.org to >>>>>>> create sophisticated cache-systems, or >>>>>>> > 2) introduce new language-syntax to delimit es-modules for >>>>>>> rollup-purposes, e.g. >>>>>>> >>>>>>> You still have not clearly defined what you mean by "rolled-up". >>>>>>> That language appears to be a random nickname, not any immutable principle >>>>>>> that individuals are bound to recognize or observe (even if "rolled-up" >>>>>>> were some form of a coding style or standard). >>>>>>> >>>>>>> Nor is it clear what you mean by "production". >>>>>>> >>>>>>> There is no external central committee that stamps code as >>>>>>> "production". Even if there were no individual is obliged to submit to such >>>>>>> a procedure nor have any concern for such an arbitrary and irrelevant >>>>>>> presumptive review of code. >>>>>>> >>>>>>> The only observable points are input and output. In general, how >>>>>>> output is achieved is immaterial. If there are specific restrictions as to >>>>>>> how the output can be achieved then those restrictions need to be clearly >>>>>>> defined. >>>>>>> >>>>>>> >>>>>>> >>>>>>> The original post asked "how many async-modules can js-app >>>>>>> practically load?" and mentioned "circular-references" (the thread >>>>>>> appears to mainly be about one or more coding styles, not code itself) >>>>>>> though as yet no code has been posted which demonstrates >>>>>>> "circular-references" or any other coding problem. >>>>>>> >>>>>>> On Sun, Jun 2, 2019 at 1:30 AM kai zhu <kaizhu256 at gmail.com> wrote: >>>>>>> >>>>>>>> i played around with your code in jsfiddle [1], and understand it a >>>>>>>> little more. >>>>>>>> it doesn't actually ```import``` 1000+ es-modules inside the >>>>>>>> rollup-file. >>>>>>>> it just creates one es-module that exports a dictionary >>>>>>>> -- and assigns the dictionary 1000+ vanilla json-objects and >>>>>>>> functions. >>>>>>>> >>>>>>>> ```js >>>>>>>> // the "rollup-file" is a single es-module >>>>>>>> // that exports 1000+ vanilla dictionary-entries >>>>>>>> const modules = {}; >>>>>>>> >>>>>>>> // this is not a es-module, nor is it rolled-up (external fetch) >>>>>>>> modules.image = <await fetch json from gist.github.com> >>>>>>>> >>>>>>>> // this is not a [rolled-up] es-module >>>>>>>> modules.fn = function () {...} >>>>>>>> >>>>>>>> // these are not [rolled-up] es-modules >>>>>>>> Object.assign(modules, <1000 json-entries>) >>>>>>>> >>>>>>>> export {modules} >>>>>>>> ``` >>>>>>>> >>>>>>>> currently, as i'm aware, nobody uses native es-modules in >>>>>>>> production, because it cannot be rolled-up. >>>>>>>> in practice es-modules are [babel] transpiled down to es5-amd (or >>>>>>>> similar) for rollup-purposes. >>>>>>>> >>>>>>>> if we're actually committed to native es-modules, then we either >>>>>>>> 1) need to depend on embedders like loading-dev at chromium.org to >>>>>>>> create sophisticated cache-systems, or >>>>>>>> 2) introduce new language-syntax to delimit es-modules for >>>>>>>> rollup-purposes, e.g. >>>>>>>> >>>>>>>> ```js >>>>>>>> // rollup.js with [hypothetical] # delimited es-modules >>>>>>>> # module aa >>>>>>>> import {bb} as bb; >>>>>>>> export ...; >>>>>>>> >>>>>>>> # module bb >>>>>>>> export ...; >>>>>>>> ``` >>>>>>>> >>>>>>>> i'm generally skeptical of option 1, given how poorly npmjs.com >>>>>>>> has handled similar problems deduplicating children in node_modules/ >>>>>>>> directory. >>>>>>>> >>>>>>>> [1] jsfiddle pseudo-module rollup >>>>>>>> https://jsfiddle.net/06twrLfd/ >>>>>>>> >>>>>>>> On Sat, Jun 1, 2019 at 5:30 PM guest271314 <guest271314 at gmail.com> >>>>>>>> wrote: >>>>>>>> >>>>>>>>> > your rollup solution is interesting, >>>>>>>>> >>>>>>>>> What is "rollup" referring to? >>>>>>>>> >>>>>>>>> > but i get an error when run in chrome (i changed to n=20 to >>>>>>>>> prevent name-collision, but it still happens). >>>>>>>>> >>>>>>>>> The duplicate ("collision") entry an ```try..catch``` block is >>>>>>>>> included in the code to demonstrate given an array of module names to be >>>>>>>>> exported and imported as identifiers 1) duplicate entries can be filtered; >>>>>>>>> 2) if a plain object is exported duplicate identifiers ("collision") is not >>>>>>>>> possible as a JavaScript plain object does not have duplicate property >>>>>>>>> names ("collision"); if there is an issue with identifiers in a module the >>>>>>>>> cause would not be the number of async-modules loaded ("how many"), but the >>>>>>>>> naming of the identifiers within the code, using or not using ```const``` >>>>>>>>> or ```let```. Still not sure what the actual issue is? >>>>>>>>> >>>>>>>>> > don't completely understand how it works, >>>>>>>>> >>>>>>>>> Use an ```async``` function to fetch data, check for the described >>>>>>>>> "collision" , create a ```data URI``` to be imported, optionally, append >>>>>>>>> addition code to be executed within the ```<script type="module">```. >>>>>>>>> >>>>>>>>> > but not sure of suitability for production-use, because of its >>>>>>>>> dynamic <script> tag generation. >>>>>>>>> >>>>>>>>> What is the issue with dynamic ```<script>``` tag generation? >>>>>>>>> >>>>>>>>> There is more than one possible approach to achieve the >>>>>>>>> presumptive requirement, that is still not clear to the exclusion of what >>>>>>>>> is not the expected result. >>>>>>>>> >>>>>>>>> There were no restrictions described at the OP and following >>>>>>>>> messages other than other than >>>>>>>>> >>>>>>>>> > pure-es6 application with 20 es-modules rolled-up into one >>>>>>>>> [production] bundle? >>>>>>>>> >>>>>>>>> The example code uses only JavaScript implementation shipped with >>>>>>>>> the browser without any external, third-party libraries. >>>>>>>>> >>>>>>>>> What standard or definition are you relying for the meaning of the >>>>>>>>> term "production-use"? What procedure are you using to determine if code is >>>>>>>>> "production-use" "suitable"? How is that procedure related to "how many >>>>>>>>> async-modules can js-app practically load?"? >>>>>>>>> >>>>>>>>> >>>>>>>>> >>>>>>>>> On Sat, Jun 1, 2019 at 9:42 PM kai zhu <kaizhu256 at gmail.com> >>>>>>>>> wrote: >>>>>>>>> >>>>>>>>>> your rollup solution is interesting, but i get an error when run >>>>>>>>>> in chrome (i changed to n=20 to prevent name-collision, but it still >>>>>>>>>> happens). don't completely understand how it works, but not sure of >>>>>>>>>> suitability for production-use, because of its dynamic <script> tag >>>>>>>>>> generation. >>>>>>>>>> >>>>>>>>>> ```console >>>>>>>>>> ReferenceError: module names ["yeqjqb02mvg3yze26rc5"] are not >>>>>>>>>> unique >>>>>>>>>> at >>>>>>>>>> data:application/javascript,%0A%20%20%20%20%20%20const%20modules... >>>>>>>>>> ``` >>>>>>>>>> >>>>>>>>>> On Sat, Jun 1, 2019 at 2:33 PM guest271314 <guest271314 at gmail.com> >>>>>>>>>> wrote: >>>>>>>>>> >>>>>>>>>>> Re: how many async-modules can js-app practically load? >>>>>>>>>>> >>>>>>>>>>> An example of exporting and importing loading 1000 properties in >>>>>>>>>>> a single module, where duplicate property names are checked for. Since >>>>>>>>>>> JavaScript plain objects cannot have duplicate property names there should >>>>>>>>>>> not be any "collisions"; the code can check for and modify the object to be >>>>>>>>>>> exported, though the last duplicate property name will be exported without >>>>>>>>>>> any errors thrown unless the code is composed to throw such an error. >>>>>>>>>>> >>>>>>>>>>> ``` >>>>>>>>>>> (async() => { >>>>>>>>>>> const oneThousandModules = encodeURIComponent( >>>>>>>>>>> // substitute rand for a Set of module names to be exported >>>>>>>>>>> // e.g. const moduleNames = ['moduleA', 'moduleB', >>>>>>>>>>> ...moduleZ] >>>>>>>>>>> ` >>>>>>>>>>> const modules = {}; >>>>>>>>>>> // set a function to be exported >>>>>>>>>>> modules.fn = function() {return 'a function'}; >>>>>>>>>>> // function to set (1000) 'random' module names to be >>>>>>>>>>> exported >>>>>>>>>>> const rand = (seed = >>>>>>>>>>> 'abcdefghijklmnopqrstuvwxyz0123456789', n = 5, len = seed.length) => >>>>>>>>>>> '.'.repeat(n).replace(/./g, _ => seed[~~(Math.random() * >>>>>>>>>>> len)]); >>>>>>>>>>> // use Set for unique module identifiers >>>>>>>>>>> const moduleNames = [...Array(1000)].map(_ => rand()); >>>>>>>>>>> const moduleIdentifiers = new Set(moduleNames); >>>>>>>>>>> // below line will cause ReferenceError to be thrown >>>>>>>>>>> moduleNames.push(moduleNames[0]); >>>>>>>>>>> try { >>>>>>>>>>> if (moduleIdentifiers.size !== moduleNames.length) { >>>>>>>>>>> // check for duplicates >>>>>>>>>>> const duplicates = moduleNames.filter((moduleName, >>>>>>>>>>> index) => moduleNames.indexOf(moduleName) !== index); >>>>>>>>>>> // notification of duplicate module names >>>>>>>>>>> throw new ReferenceError('module names ' + >>>>>>>>>>> JSON.stringify(duplicates) + ' are not unique'); >>>>>>>>>>> // perform the designated task if duplicate module >>>>>>>>>>> names are found here >>>>>>>>>>> } >>>>>>>>>>> } catch (e) { >>>>>>>>>>> console.error(e); >>>>>>>>>>> console.trace(); >>>>>>>>>>> } >>>>>>>>>>> // get, set (sync or async) exported module here >>>>>>>>>>> Object.assign(modules, >>>>>>>>>>> ...[...moduleIdentifiers].map((id, value) => ({[id]:value}))); >>>>>>>>>>> // since JavaScript plain object cannot have duplicate >>>>>>>>>>> property names >>>>>>>>>>> // modules object will still be exported without >>>>>>>>>>> duplicate property names >>>>>>>>>>> // without collisions >>>>>>>>>>> export {modules} >>>>>>>>>>> `); >>>>>>>>>>> const scriptText = `import {modules} from >>>>>>>>>>> "data:application/javascript,${oneThousandModules};${encodeURIComponent('console.log(modules);for >>>>>>>>>>> (const key in modules) {if (typeof modules[key] === \'function\') >>>>>>>>>>> {console.log(modules[key]());}}')}"`; >>>>>>>>>>> const script = document.createElement("script"); >>>>>>>>>>> script.type = "module"; >>>>>>>>>>> script.textContent = scriptText; >>>>>>>>>>> document.head.appendChild(script); >>>>>>>>>>> })(); >>>>>>>>>>> ``` >>>>>>>>>>> >>>>>>>>>>> plnkr https://plnkr.co/edit/CgEhBY?p=preview >>>>>>>>>>> >>>>>>>>>>> On Sat, Jun 1, 2019 at 1:51 AM kai zhu <kaizhu256 at gmail.com> >>>>>>>>>>> wrote: >>>>>>>>>>> >>>>>>>>>>>> > Place all of the code to be exported in 1 file? >>>>>>>>>>>> >>>>>>>>>>>> that obviously will not work, because of module-scope >>>>>>>>>>>> collision. can anyone share their experience on deploying a [babel-free] >>>>>>>>>>>> pure-es6 application with 20 es-modules rolled-up into one [production] >>>>>>>>>>>> bundle? is it even possible? >>>>>>>>>>>> >>>>>>>>>>>> >>>>>>>>>>>> On Fri, May 31, 2019 at 7:55 PM guest271314 < >>>>>>>>>>>> guest271314 at gmail.com> wrote: >>>>>>>>>>>> >>>>>>>>>>>>> > how would i transition from development-mode (20 es-module >>>>>>>>>>>>> files) -> production-mode (1 rollup file)? >>>>>>>>>>>>> >>>>>>>>>>>>> Place all of the code to be exported in 1 file? >>>>>>>>>>>>> >>>>>>>>>>>>> > with some of them having circular-references >>>>>>>>>>>>> >>>>>>>>>>>>> Not certain how that is possible when using ```import``` >>>>>>>>>>>>> within ```<script type="module">```? >>>>>>>>>>>>> >>>>>>>>>>>>> > how many async-modules can js-app practically load? >>>>>>>>>>>>> >>>>>>>>>>>>> Again, how many have you tried to load? 100? 500? 1000? Either >>>>>>>>>>>>> should be possible. >>>>>>>>>>>>> >>>>>>>>>>>>> What specific issue are you actually to resolve? >>>>>>>>>>>>> >>>>>>>>>>>>> On Fri, May 31, 2019 at 5:40 PM kai zhu <kaizhu256 at gmail.com> >>>>>>>>>>>>> wrote: >>>>>>>>>>>>> >>>>>>>>>>>>>> > Oh, and yes, I've loaded upwards of 50-100 modules in >>>>>>>>>>>>>> development. 20 >>>>>>>>>>>>>> modules is *easy* to achieve in single-page apps. >>>>>>>>>>>>>> >>>>>>>>>>>>>> was that with some combination of babel/rollup/webpack or >>>>>>>>>>>>>> pure-es6? >>>>>>>>>>>>>> if i want to develop a pure-es6 webapp (no babel), how would >>>>>>>>>>>>>> i transition from development-mode (20 es-module files) -> production-mode >>>>>>>>>>>>>> (1 rollup file)? >>>>>>>>>>>>>> >>>>>>>>>>>>>> >>>>>>>>>>>>>> On Fri, May 31, 2019 at 10:47 AM Isiah Meadows < >>>>>>>>>>>>>> isiahmeadows at gmail.com> wrote: >>>>>>>>>>>>>> >>>>>>>>>>>>>>> If it's bundled by Rollup or Webpack into a single bundle, >>>>>>>>>>>>>>> it's >>>>>>>>>>>>>>> equivalent to a single `<script type="module" src="...">` >>>>>>>>>>>>>>> pointing >>>>>>>>>>>>>>> towards the original entry point, excluding network >>>>>>>>>>>>>>> requests.* But in >>>>>>>>>>>>>>> either case, you aren't listing 50 scripts, you're only >>>>>>>>>>>>>>> listing the >>>>>>>>>>>>>>> entry module and importing child modules within parent >>>>>>>>>>>>>>> modules. Rollup >>>>>>>>>>>>>>> and Webpack do mostly the same thing browsers do when it >>>>>>>>>>>>>>> comes to >>>>>>>>>>>>>>> resolving dependencies, just they generate a bundle >>>>>>>>>>>>>>> afterwards where >>>>>>>>>>>>>>> browsers execute code afterwards. Also, it's worth noting >>>>>>>>>>>>>>> that the gap >>>>>>>>>>>>>>> between a single large request and multiple smaller requests >>>>>>>>>>>>>>> has >>>>>>>>>>>>>>> shrunk a lot since HTTP/2 came along, since it's binary, it >>>>>>>>>>>>>>> allows >>>>>>>>>>>>>>> requests and response data to be interleaved, it better >>>>>>>>>>>>>>> leverages the >>>>>>>>>>>>>>> underlying TCP protocol format, and it allows servers to >>>>>>>>>>>>>>> send data >>>>>>>>>>>>>>> pre-emptively without the client requesting it first. (Web >>>>>>>>>>>>>>> sockets are >>>>>>>>>>>>>>> built on this functionality.) It's still better to bundle in >>>>>>>>>>>>>>> general, >>>>>>>>>>>>>>> but it's less of a problem not to. >>>>>>>>>>>>>>> >>>>>>>>>>>>>>> This is *not* the case for `<script type="module">` elements >>>>>>>>>>>>>>> - those >>>>>>>>>>>>>>> operate more like inline scripts that happen to have the >>>>>>>>>>>>>>> ability to >>>>>>>>>>>>>>> `import`. >>>>>>>>>>>>>>> >>>>>>>>>>>>>>> Oh, and yes, I've loaded upwards of 50-100 modules in >>>>>>>>>>>>>>> development. 20 >>>>>>>>>>>>>>> modules is *easy* to achieve in single-page apps. >>>>>>>>>>>>>>> >>>>>>>>>>>>>>> * This is, of course, not the case if you are using pure ES6 >>>>>>>>>>>>>>> and you >>>>>>>>>>>>>>> aren't using any plugins to, say, run the original source >>>>>>>>>>>>>>> through >>>>>>>>>>>>>>> Babel for React + JSX or something. >>>>>>>>>>>>>>> >>>>>>>>>>>>>>> ----- >>>>>>>>>>>>>>> >>>>>>>>>>>>>>> Isiah Meadows >>>>>>>>>>>>>>> contact at isiahmeadows.com >>>>>>>>>>>>>>> www.isiahmeadows.com >>>>>>>>>>>>>>> On Sat, May 25, 2019 at 2:12 AM kai zhu <kaizhu256 at gmail.com> >>>>>>>>>>>>>>> wrote: >>>>>>>>>>>>>>> > >>>>>>>>>>>>>>> > Asynchronous loading differs only in >>>>>>>>>>>>>>> > that it takes more code to express the same logic and you >>>>>>>>>>>>>>> have to take >>>>>>>>>>>>>>> > into account concurrent requests (and you need to cache >>>>>>>>>>>>>>> the request, >>>>>>>>>>>>>>> > not the result), but it's otherwise the same from 1km away. >>>>>>>>>>>>>>> > >>>>>>>>>>>>>>> > >>>>>>>>>>>>>>> > so async-loading 50 ```<script type="module">``` tags >>>>>>>>>>>>>>> > has equivalent side-effect >>>>>>>>>>>>>>> > as sync-loading single webpack-rollup (of same 50 modules)? >>>>>>>>>>>>>>> > >>>>>>>>>>>>>>> > i have nagging suspicion of doubts. has anyone tried >>>>>>>>>>>>>>> native async-loading large numbers (>10) of >>>>>>>>>>>>>>> > ```<script type="module">``` tags, and verify it resolves >>>>>>>>>>>>>>> identically to using a single webpack-rollup? >>>>>>>>>>>>>>> > >>>>>>>>>>>>>>> > again, i'm not that knowledgeable on es-modules, so above >>>>>>>>>>>>>>> question may be trivially true, and i'm just not aware. >>>>>>>>>>>>>>> > >>>>>>>>>>>>>>> > -kai >>>>>>>>>>>>>>> > >>>>>>>>>>>>>>> > On 24 May 2019, at 23:41, Isiah Meadows < >>>>>>>>>>>>>>> isiahmeadows at gmail.com> wrote: >>>>>>>>>>>>>>> > >>>>>>>>>>>>>>> > There's two main reasons why it scales: >>>>>>>>>>>>>>> > >>>>>>>>>>>>>>> > 1. Modules are strongly encapsulated while minimizing >>>>>>>>>>>>>>> global pollution. >>>>>>>>>>>>>>> > 2. The resolution algorithm applies the same logic no >>>>>>>>>>>>>>> matter how many >>>>>>>>>>>>>>> > modules are loaded. >>>>>>>>>>>>>>> > >>>>>>>>>>>>>>> > It's much easier for it to scale when you write the code >>>>>>>>>>>>>>> unaware of >>>>>>>>>>>>>>> > how many modules you might be loading and unaware of how >>>>>>>>>>>>>>> deep their >>>>>>>>>>>>>>> > dependency graph is. Fewer assumptions here is key. It's an >>>>>>>>>>>>>>> > engineering problem, but a relatively simple one. >>>>>>>>>>>>>>> > >>>>>>>>>>>>>>> > If you want a short example of how sync module resolution >>>>>>>>>>>>>>> works, you >>>>>>>>>>>>>>> > can take a look at this little utility I wrote: >>>>>>>>>>>>>>> > https://github.com/isiahmeadows/simple-require-loader. >>>>>>>>>>>>>>> That doesn't >>>>>>>>>>>>>>> > asynchronously resolve modules, but it should help explain >>>>>>>>>>>>>>> the process >>>>>>>>>>>>>>> > from a synchronous standpoint. Asynchronous loading >>>>>>>>>>>>>>> differs only in >>>>>>>>>>>>>>> > that it takes more code to express the same logic and you >>>>>>>>>>>>>>> have to take >>>>>>>>>>>>>>> > into account concurrent requests (and you need to cache >>>>>>>>>>>>>>> the request, >>>>>>>>>>>>>>> > not the result), but it's otherwise the same from 1km away. >>>>>>>>>>>>>>> > >>>>>>>>>>>>>>> > ----- >>>>>>>>>>>>>>> > >>>>>>>>>>>>>>> > Isiah Meadows >>>>>>>>>>>>>>> > contact at isiahmeadows.com >>>>>>>>>>>>>>> > www.isiahmeadows.com >>>>>>>>>>>>>>> > >>>>>>>>>>>>>>> > On Thu, May 23, 2019 at 10:49 AM kai zhu < >>>>>>>>>>>>>>> kaizhu256 at gmail.com> wrote: >>>>>>>>>>>>>>> > >>>>>>>>>>>>>>> > >>>>>>>>>>>>>>> > actually, i admit i don't know what i'm talking about. >>>>>>>>>>>>>>> just generally confused (through ignorance) on how large-scale es-module >>>>>>>>>>>>>>> dependencies resolve when loaded/imported asynchronously. >>>>>>>>>>>>>>> > >>>>>>>>>>>>>>> > On Wed, May 22, 2019 at 10:42 PM Logan Smyth < >>>>>>>>>>>>>>> loganfsmyth at gmail.com> wrote: >>>>>>>>>>>>>>> > >>>>>>>>>>>>>>> > >>>>>>>>>>>>>>> > Can you elaborate on what loading state you need to keep >>>>>>>>>>>>>>> track of? What is the bottleneck that you run into? Also to be sure, when >>>>>>>>>>>>>>> you say async-load, do you mean `import()`? >>>>>>>>>>>>>>> > >>>>>>>>>>>>>>> > On Wed, May 22, 2019, 20:17 kai zhu <kaizhu256 at gmail.com> >>>>>>>>>>>>>>> wrote: >>>>>>>>>>>>>>> > >>>>>>>>>>>>>>> > >>>>>>>>>>>>>>> > i don't use es-modules. >>>>>>>>>>>>>>> > but with amd/requirejs, I start having trouble with >>>>>>>>>>>>>>> module-initializations in nodejs/browser at ~5 async modules (that may or >>>>>>>>>>>>>>> may not have circular-references). 10 would be hard, and 20 would be near >>>>>>>>>>>>>>> inhuman for me. >>>>>>>>>>>>>>> > >>>>>>>>>>>>>>> > can we say its somewhat impractical for most applications >>>>>>>>>>>>>>> to load more than 50 async modules (with some of them having >>>>>>>>>>>>>>> circular-references)? and perhaps better design/spec module-loading >>>>>>>>>>>>>>> mechanisms with this usability concern in mind? >>>>>>>>>>>>>>> > >>>>>>>>>>>>>>> > p.s. its also impractical for me to async-load 5 or more >>>>>>>>>>>>>>> modules without using globalThis to keep track of each module's >>>>>>>>>>>>>>> loading-state. >>>>>>>>>>>>>>> > _______________________________________________ >>>>>>>>>>>>>>> > es-discuss mailing list >>>>>>>>>>>>>>> > es-discuss at mozilla.org >>>>>>>>>>>>>>> > https://mail.mozilla.org/listinfo/es-discuss >>>>>>>>>>>>>>> > >>>>>>>>>>>>>>> > >>>>>>>>>>>>>>> > _______________________________________________ >>>>>>>>>>>>>>> > es-discuss mailing list >>>>>>>>>>>>>>> > es-discuss at mozilla.org >>>>>>>>>>>>>>> > https://mail.mozilla.org/listinfo/es-discuss >>>>>>>>>>>>>>> > >>>>>>>>>>>>>>> > >>>>>>>>>>>>>>> >>>>>>>>>>>>>> _______________________________________________ >>>>>>>>>>>>>> es-discuss mailing list >>>>>>>>>>>>>> es-discuss at mozilla.org >>>>>>>>>>>>>> https://mail.mozilla.org/listinfo/es-discuss >>>>>>>>>>>>>> >>>>>>>>>>>>> -------------- next part -------------- An HTML attachment was scrubbed... URL: <http://mail.mozilla.org/pipermail/es-discuss/attachments/20190602/dc40489d/attachment-0001.html>
but that requires coordination among modules, which is not always possible. the idea is to inline/rollup es-modules that may not have come from same developers (and whom are unaware their es-modules collide w/ others when rolled-up).
How do you intend to know the names of the identifiers to import without
"coordination", and check for duplicate identifier names and duplicate
exports (SyntaxError: Duplicate export of 'bar'
)?
At the previous post the assertion was that multiple inline imports and exports were not possible. Using shortName
resolved that concern. The issue now is an intentional uncoordinated environment where coordination is expected to be self-assembling and automatic. Are there any more undisclosed aspects of the proposal?
> but that requires coordination among modules, which is not always possible. the idea is to inline/rollup es-modules that may not have come from same developers (and whom are unaware their es-modules collide w/ others when rolled-up). How do you intend to know the names of the identifiers to import without "coordination" and check for duplicate identifier names and duplicate exports? On Mon, Jun 3, 2019 at 2:12 AM kai zhu <kaizhu256 at gmail.com> wrote: > but that requires coordination among modules, which is not always > possible. the idea is to inline/rollup es-modules that may not have come > from same developers (and whom are unaware their es-modules collide w/ > others when rolled-up). > > you should be able to natively transition from development-env (individual > es-modules) -> production-env (rolled-up es-modules), w/o down-transpiling > to es5-amdjs. > > > > On Sun, Jun 2, 2019 at 8:29 PM guest271314 <guest271314 at gmail.com> wrote: > >> One option is to utilize ```shortName``` >> https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Statements/import#Import_an_export_with_a_more_convenient_alias >> >> ``` >> import {foo as foo1} from "./aa.js"; >> let bar1 = { baz: foo1 }; >> export { bar1 }; >> >> import {foo as foo2} from "./bb.js"; >> const bar2 = { baz: foo2 }; >> export { bar2 }; >> ``` >> >> On Sun, Jun 2, 2019 at 11:05 PM kai zhu <kaizhu256 at gmail.com> wrote: >> >>> not inline multiple ```export```'s, but inline multiple module-scopes. >>> >>> ```js >>> /* >>> * how do you inline the two es-modules below >>> * with colliding `foo` and `bar` variables? >>> * >>> * you can't unless you introduce new language-syntax >>> * to somehow delimit their scopes >>> */ >>> >>> // [hypothethical] es-module-scope delimiter >>> # es-module-scope "./inline.js" >>> >>> // module ./inline.js >>> import { foo } from "./aa.js" >>> const bar = { baz: foo }; >>> export { bar }; >>> >>> >>> >>> // [hypothethical] es-module-scope delimiter >>> # es-module-scope ./nextinline.js >>> >>> // module ./nextinline.js >>> import { foo } from "./bb.js" >>> const bar = { baz: foo }; >>> export { bar }; >>> ``` >>> >>> On Sun, Jun 2, 2019 at 2:54 PM guest271314 <guest271314 at gmail.com> >>> wrote: >>> >>>> Multiple imports are already possible >>>> >>>> ``` >>>> import {inline} from "./inline.js"; >>>> import {nextInline} from "./nextInline.js"; >>>> >>>> const o = { >>>> a:1, b:2, c:3 >>>> }; >>>> >>>> // ... >>>> >>>> export {o, cities, video, inline, nextInline}; >>>> ``` >>>> >>>> Are you proposing multiple ```export```s? >>>> >>>> ``` >>>> export {o, cities, video, inline, nextInline}; >>>> o.c = 7; >>>> export {o}; >>>> ``` >>>> >>>> >>>> >>>> On Sun, Jun 2, 2019 at 6:19 PM kai zhu <kaizhu256 at gmail.com> wrote: >>>> >>>>> @guest271314 <guest271314 at gmail.com>, your example again is not a >>>>> [native] bundle of two or more inlined es-modules. its just a single >>>>> es-module that that fetches json data. >>>>> >>>>> i'm asking if its desirable to inline multiple es-modules into a >>>>> single file natively, e.g.: >>>>> >>>>> ``` >>>>> /* >>>>> * es-module.rollup.js >>>>> * this [hypothetical] rollup-file contains multiple inlined es-modules >>>>> * to improve load-performance in production-deployment. >>>>> */ >>>>> >>>>> // 1. inlined es-module ./main.js >>>>> import { foo } from "./counter.js" >>>>> import { bar } from "./display.js" >>>>> foo(bar); >>>>> >>>>> // 2. inlined es-module ./counter.js >>>>> var foo; >>>>> foo = function (bar) { >>>>> bar(); >>>>> }; >>>>> export { foo } >>>>> >>>>> // 3. inlined es-module ./display.js >>>>> var bar; >>>>> bar = function () { >>>>> console.log("hello world"); >>>>> }; >>>>> export { bar } >>>>> ``` >>>>> >>>>> this native es-module inline-capability may not be desirable to you, >>>>> which is fine. it would be a datapoint against this feature (and rely >>>>> instead on pre-emptive import-maps and http2-push, as explained by >>>>> @frederick and @isiah). >>>>> >>>>> >>>>> On Sun, Jun 2, 2019 at 11:22 AM guest271314 <guest271314 at gmail.com> >>>>> wrote: >>>>> >>>>>> 1) original-question - is native es-module's async-behavior >>>>>>> desirable? async side-effects are difficult to manage -- i conjecture that >>>>>>> async-loading 20 es-modules (with dependent side-effects) is not practical >>>>>>> for most mortals to handle. >>>>>> >>>>>> >>>>>> It depends on what *you *mean by "desirable" in a given context. >>>>>> >>>>>> There is no difference from loading 1 module and loading 1000 modules >>>>>> except for network cost, memory and disk space usage. >>>>>> >>>>>> Mortals can handle far more than loading 20 es-modules. >>>>>> >>>>>> What are the specific "side-effects" that you are referring to? >>>>>> >>>>>> describes the mechanism for how to hint the brower to pre-fetch 20 >>>>>>> es-modules. but if you pre-fetch, then is loading-behavior effectively >>>>>>> synchronous? >>>>>> >>>>>> >>>>>> Resources can be "pre-fetched" using various means. From caching the >>>>>> first request and using the cached data instead of making future requests >>>>>> for the same resources to storing one or more entire directories in the >>>>>> browser configuration folder using `requestFileSystem` (Chromiom/Chrome). >>>>>> >>>>>> but was unclear whether they were individual [async] ```<script >>>>>>> type="module">``` tags, or some es5-transpiled rollup >>>>>> >>>>>> >>>>>> There should not be any difference between the two approaches. If >>>>>> there is a difference then you should be able to clearly state what the >>>>>> difference is, and demonstrate the difference by reproduction, without >>>>>> speculating and not demonstrating a difference by means of reproduction. >>>>>> >>>>>> 2) the second-question about es-module rollups (which you and i are >>>>>>> debating) stemmed from @isiah's response -- if he and everyone-else use >>>>>>> es5-transpiled rollups (which i suspect), >>>>>> >>>>>> >>>>>> Do not care what "everyone-else" is supposedly doing. How can you >>>>>> possibly know what everyone-else is doing and even if you did know what >>>>>> third-parties are doing how does that affect what you are doing? >>>>>> >>>>>> then shouldn't it be desirable for es-modules to natively support >>>>>>> rollups as well? currently, there's no way to natively rollup multiple >>>>>>> es-modules into a single bundle. >>>>>> >>>>>> >>>>>> There are ways to "bundle" multiple modules into a single export >>>>>> "natively", as demonstrated at the previously posted code. >>>>>> >>>>>> Another example approach >>>>>> >>>>>> ``` >>>>>> // sync >>>>>> const o = { >>>>>> a:1, b:2, c:3 >>>>>> }; >>>>>> // async >>>>>> const cities = fetch(" >>>>>> https://gist.githubusercontent.com/guest271314/ffac94353ab16f42160e/raw/aaee70a3e351f6c7bc00178eabb5970a02df87e9/states.json >>>>>> ") >>>>>> .then(response => response.json()) >>>>>> .catch(e => {console.error(e); return "error fetching >>>>>> cities module"}); >>>>>> // async >>>>>> const video = fetch(" >>>>>> https://upload.wikimedia.org/wikipedia/commons/d/d9/120-cell.ogv") >>>>>> .then(response => response.blob()) >>>>>> .catch(e => {console.error(e); return "error fetching >>>>>> video module"}); >>>>>> // multiple "modules" exported >>>>>> export {o, cities, video}; >>>>>> ``` >>>>>> >>>>>> at single ```<script type="module">``` >>>>>> >>>>>> ``` >>>>>> <script type="module"> >>>>>> import * as o from "./script.js"; >>>>>> (async(mods) => { >>>>>> for (const [key, value] of mods) { >>>>>> if (value instanceof Promise) { >>>>>> console.log("async module", key, await value) >>>>>> } else { >>>>>> console.log("sync module", key, value); >>>>>> } >>>>>> } >>>>>> })(Object.entries(o)); >>>>>> </script> >>>>>> ``` >>>>>> >>>>>> Still there is no actual problem statement. Rather, there is >>>>>> conjecture without a definitive issue to solve. >>>>>> >>>>>> >>>>>> >>>>>> >>>>>> On Sun, Jun 2, 2019 at 3:54 AM kai zhu <kaizhu256 at gmail.com> wrote: >>>>>> >>>>>>> i apologize for poor framing of my questions. they are still >>>>>>> formative, but i can clarify abit as follows: >>>>>>> >>>>>>> 1) original-question - is native es-module's async-behavior >>>>>>> desirable? async side-effects are difficult to manage -- i conjecture that >>>>>>> async-loading 20 es-modules (with dependent side-effects) is not practical >>>>>>> for most mortals to handle. >>>>>>> @frederick describes the mechanism for how to hint the brower to >>>>>>> pre-fetch 20 es-modules. but if you pre-fetch, then is loading-behavior >>>>>>> effectively synchronous? >>>>>>> @isiah says he has experience loading 50-100 modules, but was >>>>>>> unclear whether they were individual [async] ```<script >>>>>>> type="module">``` tags, or some es5-transpiled rollup. >>>>>>> >>>>>>> i may be wrong about everything, as i'm a bit ignorant on what async >>>>>>> actually means in es-modules (and appreciate it, if someone can clarify >>>>>>> that). >>>>>>> >>>>>>> >>>>>>> >>>>>>> 2) the second-question about es-module rollups (which you and i are >>>>>>> debating) stemmed from @isiah's response -- if he and everyone-else use >>>>>>> es5-transpiled rollups (which i suspect), then shouldn't it be desirable >>>>>>> for es-modules to natively support rollups as well? currently, there's no >>>>>>> way to natively rollup multiple es-modules into a single bundle. >>>>>>> >>>>>>> this 2nd question also has implications about es-module's >>>>>>> async-behavior (because rollups "load" modules in sync/blocking fashion). >>>>>>> this could change side-effect behaviors between development-mode (20 >>>>>>> [async] ```<script type="module">``` tags) and production-mode (1 >>>>>>> rollup-bundle). again, i may be wrong about that, as i'm ignorant about >>>>>>> what async actually is in es-modules. >>>>>>> >>>>>>> -kai >>>>>>> >>>>>>> On Sat, Jun 1, 2019 at 9:22 PM guest271314 <guest271314 at gmail.com> >>>>>>> wrote: >>>>>>> >>>>>>>> > it doesn't actually ```import``` 1000+ es-modules inside the >>>>>>>> rollup-file. it just creates one es-module that exports a dictionary -- and >>>>>>>> assigns the dictionary 1000+ vanilla json-objects and functions. >>>>>>>> >>>>>>>> The code provides a means to fetch N resources and export those >>>>>>>> resources within a single object. >>>>>>>> >>>>>>>> > currently, as i'm aware, nobody uses native es-modules in >>>>>>>> production, because it cannot be rolled-up. >>>>>>>> > in practice es-modules are [babel] transpiled down to es5-amd (or >>>>>>>> similar) for rollup-purposes. >>>>>>>> > >>>>>>>> > if we're actually committed to native es-modules, then we either >>>>>>>> > 1) need to depend on embedders like loading-dev at chromium.org to >>>>>>>> create sophisticated cache-systems, or >>>>>>>> > 2) introduce new language-syntax to delimit es-modules for >>>>>>>> rollup-purposes, e.g. >>>>>>>> >>>>>>>> You still have not clearly defined what you mean by "rolled-up". >>>>>>>> That language appears to be a random nickname, not any immutable principle >>>>>>>> that individuals are bound to recognize or observe (even if "rolled-up" >>>>>>>> were some form of a coding style or standard). >>>>>>>> >>>>>>>> Nor is it clear what you mean by "production". >>>>>>>> >>>>>>>> There is no external central committee that stamps code as >>>>>>>> "production". Even if there were no individual is obliged to submit to such >>>>>>>> a procedure nor have any concern for such an arbitrary and irrelevant >>>>>>>> presumptive review of code. >>>>>>>> >>>>>>>> The only observable points are input and output. In general, how >>>>>>>> output is achieved is immaterial. If there are specific restrictions as to >>>>>>>> how the output can be achieved then those restrictions need to be clearly >>>>>>>> defined. >>>>>>>> >>>>>>>> >>>>>>>> >>>>>>>> The original post asked "how many async-modules can js-app >>>>>>>> practically load?" and mentioned "circular-references" (the thread >>>>>>>> appears to mainly be about one or more coding styles, not code itself) >>>>>>>> though as yet no code has been posted which demonstrates >>>>>>>> "circular-references" or any other coding problem. >>>>>>>> >>>>>>>> On Sun, Jun 2, 2019 at 1:30 AM kai zhu <kaizhu256 at gmail.com> wrote: >>>>>>>> >>>>>>>>> i played around with your code in jsfiddle [1], and understand it >>>>>>>>> a little more. >>>>>>>>> it doesn't actually ```import``` 1000+ es-modules inside the >>>>>>>>> rollup-file. >>>>>>>>> it just creates one es-module that exports a dictionary >>>>>>>>> -- and assigns the dictionary 1000+ vanilla json-objects and >>>>>>>>> functions. >>>>>>>>> >>>>>>>>> ```js >>>>>>>>> // the "rollup-file" is a single es-module >>>>>>>>> // that exports 1000+ vanilla dictionary-entries >>>>>>>>> const modules = {}; >>>>>>>>> >>>>>>>>> // this is not a es-module, nor is it rolled-up (external fetch) >>>>>>>>> modules.image = <await fetch json from gist.github.com> >>>>>>>>> >>>>>>>>> // this is not a [rolled-up] es-module >>>>>>>>> modules.fn = function () {...} >>>>>>>>> >>>>>>>>> // these are not [rolled-up] es-modules >>>>>>>>> Object.assign(modules, <1000 json-entries>) >>>>>>>>> >>>>>>>>> export {modules} >>>>>>>>> ``` >>>>>>>>> >>>>>>>>> currently, as i'm aware, nobody uses native es-modules in >>>>>>>>> production, because it cannot be rolled-up. >>>>>>>>> in practice es-modules are [babel] transpiled down to es5-amd (or >>>>>>>>> similar) for rollup-purposes. >>>>>>>>> >>>>>>>>> if we're actually committed to native es-modules, then we either >>>>>>>>> 1) need to depend on embedders like loading-dev at chromium.org to >>>>>>>>> create sophisticated cache-systems, or >>>>>>>>> 2) introduce new language-syntax to delimit es-modules for >>>>>>>>> rollup-purposes, e.g. >>>>>>>>> >>>>>>>>> ```js >>>>>>>>> // rollup.js with [hypothetical] # delimited es-modules >>>>>>>>> # module aa >>>>>>>>> import {bb} as bb; >>>>>>>>> export ...; >>>>>>>>> >>>>>>>>> # module bb >>>>>>>>> export ...; >>>>>>>>> ``` >>>>>>>>> >>>>>>>>> i'm generally skeptical of option 1, given how poorly npmjs.com >>>>>>>>> has handled similar problems deduplicating children in node_modules/ >>>>>>>>> directory. >>>>>>>>> >>>>>>>>> [1] jsfiddle pseudo-module rollup >>>>>>>>> https://jsfiddle.net/06twrLfd/ >>>>>>>>> >>>>>>>>> On Sat, Jun 1, 2019 at 5:30 PM guest271314 <guest271314 at gmail.com> >>>>>>>>> wrote: >>>>>>>>> >>>>>>>>>> > your rollup solution is interesting, >>>>>>>>>> >>>>>>>>>> What is "rollup" referring to? >>>>>>>>>> >>>>>>>>>> > but i get an error when run in chrome (i changed to n=20 to >>>>>>>>>> prevent name-collision, but it still happens). >>>>>>>>>> >>>>>>>>>> The duplicate ("collision") entry an ```try..catch``` block is >>>>>>>>>> included in the code to demonstrate given an array of module names to be >>>>>>>>>> exported and imported as identifiers 1) duplicate entries can be filtered; >>>>>>>>>> 2) if a plain object is exported duplicate identifiers ("collision") is not >>>>>>>>>> possible as a JavaScript plain object does not have duplicate property >>>>>>>>>> names ("collision"); if there is an issue with identifiers in a module the >>>>>>>>>> cause would not be the number of async-modules loaded ("how many"), but the >>>>>>>>>> naming of the identifiers within the code, using or not using ```const``` >>>>>>>>>> or ```let```. Still not sure what the actual issue is? >>>>>>>>>> >>>>>>>>>> > don't completely understand how it works, >>>>>>>>>> >>>>>>>>>> Use an ```async``` function to fetch data, check for the >>>>>>>>>> described "collision" , create a ```data URI``` to be imported, optionally, >>>>>>>>>> append addition code to be executed within the ```<script type="module">```. >>>>>>>>>> >>>>>>>>>> > but not sure of suitability for production-use, because of its >>>>>>>>>> dynamic <script> tag generation. >>>>>>>>>> >>>>>>>>>> What is the issue with dynamic ```<script>``` tag generation? >>>>>>>>>> >>>>>>>>>> There is more than one possible approach to achieve the >>>>>>>>>> presumptive requirement, that is still not clear to the exclusion of what >>>>>>>>>> is not the expected result. >>>>>>>>>> >>>>>>>>>> There were no restrictions described at the OP and following >>>>>>>>>> messages other than other than >>>>>>>>>> >>>>>>>>>> > pure-es6 application with 20 es-modules rolled-up into one >>>>>>>>>> [production] bundle? >>>>>>>>>> >>>>>>>>>> The example code uses only JavaScript implementation shipped with >>>>>>>>>> the browser without any external, third-party libraries. >>>>>>>>>> >>>>>>>>>> What standard or definition are you relying for the meaning of >>>>>>>>>> the term "production-use"? What procedure are you using to determine if >>>>>>>>>> code is "production-use" "suitable"? How is that procedure related to "how >>>>>>>>>> many async-modules can js-app practically load?"? >>>>>>>>>> >>>>>>>>>> >>>>>>>>>> >>>>>>>>>> On Sat, Jun 1, 2019 at 9:42 PM kai zhu <kaizhu256 at gmail.com> >>>>>>>>>> wrote: >>>>>>>>>> >>>>>>>>>>> your rollup solution is interesting, but i get an error when run >>>>>>>>>>> in chrome (i changed to n=20 to prevent name-collision, but it still >>>>>>>>>>> happens). don't completely understand how it works, but not sure of >>>>>>>>>>> suitability for production-use, because of its dynamic <script> tag >>>>>>>>>>> generation. >>>>>>>>>>> >>>>>>>>>>> ```console >>>>>>>>>>> ReferenceError: module names ["yeqjqb02mvg3yze26rc5"] are not >>>>>>>>>>> unique >>>>>>>>>>> at >>>>>>>>>>> data:application/javascript,%0A%20%20%20%20%20%20const%20modules... >>>>>>>>>>> ``` >>>>>>>>>>> >>>>>>>>>>> On Sat, Jun 1, 2019 at 2:33 PM guest271314 < >>>>>>>>>>> guest271314 at gmail.com> wrote: >>>>>>>>>>> >>>>>>>>>>>> Re: how many async-modules can js-app practically load? >>>>>>>>>>>> >>>>>>>>>>>> An example of exporting and importing loading 1000 properties >>>>>>>>>>>> in a single module, where duplicate property names are checked for. Since >>>>>>>>>>>> JavaScript plain objects cannot have duplicate property names there should >>>>>>>>>>>> not be any "collisions"; the code can check for and modify the object to be >>>>>>>>>>>> exported, though the last duplicate property name will be exported without >>>>>>>>>>>> any errors thrown unless the code is composed to throw such an error. >>>>>>>>>>>> >>>>>>>>>>>> ``` >>>>>>>>>>>> (async() => { >>>>>>>>>>>> const oneThousandModules = encodeURIComponent( >>>>>>>>>>>> // substitute rand for a Set of module names to be >>>>>>>>>>>> exported >>>>>>>>>>>> // e.g. const moduleNames = ['moduleA', 'moduleB', >>>>>>>>>>>> ...moduleZ] >>>>>>>>>>>> ` >>>>>>>>>>>> const modules = {}; >>>>>>>>>>>> // set a function to be exported >>>>>>>>>>>> modules.fn = function() {return 'a function'}; >>>>>>>>>>>> // function to set (1000) 'random' module names to be >>>>>>>>>>>> exported >>>>>>>>>>>> const rand = (seed = >>>>>>>>>>>> 'abcdefghijklmnopqrstuvwxyz0123456789', n = 5, len = seed.length) => >>>>>>>>>>>> '.'.repeat(n).replace(/./g, _ => seed[~~(Math.random() >>>>>>>>>>>> * len)]); >>>>>>>>>>>> // use Set for unique module identifiers >>>>>>>>>>>> const moduleNames = [...Array(1000)].map(_ => rand()); >>>>>>>>>>>> const moduleIdentifiers = new Set(moduleNames); >>>>>>>>>>>> // below line will cause ReferenceError to be thrown >>>>>>>>>>>> moduleNames.push(moduleNames[0]); >>>>>>>>>>>> try { >>>>>>>>>>>> if (moduleIdentifiers.size !== moduleNames.length) { >>>>>>>>>>>> // check for duplicates >>>>>>>>>>>> const duplicates = moduleNames.filter((moduleName, >>>>>>>>>>>> index) => moduleNames.indexOf(moduleName) !== index); >>>>>>>>>>>> // notification of duplicate module names >>>>>>>>>>>> throw new ReferenceError('module names ' + >>>>>>>>>>>> JSON.stringify(duplicates) + ' are not unique'); >>>>>>>>>>>> // perform the designated task if duplicate module >>>>>>>>>>>> names are found here >>>>>>>>>>>> } >>>>>>>>>>>> } catch (e) { >>>>>>>>>>>> console.error(e); >>>>>>>>>>>> console.trace(); >>>>>>>>>>>> } >>>>>>>>>>>> // get, set (sync or async) exported module here >>>>>>>>>>>> Object.assign(modules, >>>>>>>>>>>> ...[...moduleIdentifiers].map((id, value) => ({[id]:value}))); >>>>>>>>>>>> // since JavaScript plain object cannot have duplicate >>>>>>>>>>>> property names >>>>>>>>>>>> // modules object will still be exported without >>>>>>>>>>>> duplicate property names >>>>>>>>>>>> // without collisions >>>>>>>>>>>> export {modules} >>>>>>>>>>>> `); >>>>>>>>>>>> const scriptText = `import {modules} from >>>>>>>>>>>> "data:application/javascript,${oneThousandModules};${encodeURIComponent('console.log(modules);for >>>>>>>>>>>> (const key in modules) {if (typeof modules[key] === \'function\') >>>>>>>>>>>> {console.log(modules[key]());}}')}"`; >>>>>>>>>>>> const script = document.createElement("script"); >>>>>>>>>>>> script.type = "module"; >>>>>>>>>>>> script.textContent = scriptText; >>>>>>>>>>>> document.head.appendChild(script); >>>>>>>>>>>> })(); >>>>>>>>>>>> ``` >>>>>>>>>>>> >>>>>>>>>>>> plnkr https://plnkr.co/edit/CgEhBY?p=preview >>>>>>>>>>>> >>>>>>>>>>>> On Sat, Jun 1, 2019 at 1:51 AM kai zhu <kaizhu256 at gmail.com> >>>>>>>>>>>> wrote: >>>>>>>>>>>> >>>>>>>>>>>>> > Place all of the code to be exported in 1 file? >>>>>>>>>>>>> >>>>>>>>>>>>> that obviously will not work, because of module-scope >>>>>>>>>>>>> collision. can anyone share their experience on deploying a [babel-free] >>>>>>>>>>>>> pure-es6 application with 20 es-modules rolled-up into one [production] >>>>>>>>>>>>> bundle? is it even possible? >>>>>>>>>>>>> >>>>>>>>>>>>> >>>>>>>>>>>>> On Fri, May 31, 2019 at 7:55 PM guest271314 < >>>>>>>>>>>>> guest271314 at gmail.com> wrote: >>>>>>>>>>>>> >>>>>>>>>>>>>> > how would i transition from development-mode (20 es-module >>>>>>>>>>>>>> files) -> production-mode (1 rollup file)? >>>>>>>>>>>>>> >>>>>>>>>>>>>> Place all of the code to be exported in 1 file? >>>>>>>>>>>>>> >>>>>>>>>>>>>> > with some of them having circular-references >>>>>>>>>>>>>> >>>>>>>>>>>>>> Not certain how that is possible when using ```import``` >>>>>>>>>>>>>> within ```<script type="module">```? >>>>>>>>>>>>>> >>>>>>>>>>>>>> > how many async-modules can js-app practically load? >>>>>>>>>>>>>> >>>>>>>>>>>>>> Again, how many have you tried to load? 100? 500? 1000? >>>>>>>>>>>>>> Either should be possible. >>>>>>>>>>>>>> >>>>>>>>>>>>>> What specific issue are you actually to resolve? >>>>>>>>>>>>>> >>>>>>>>>>>>>> On Fri, May 31, 2019 at 5:40 PM kai zhu <kaizhu256 at gmail.com> >>>>>>>>>>>>>> wrote: >>>>>>>>>>>>>> >>>>>>>>>>>>>>> > Oh, and yes, I've loaded upwards of 50-100 modules in >>>>>>>>>>>>>>> development. 20 >>>>>>>>>>>>>>> modules is *easy* to achieve in single-page apps. >>>>>>>>>>>>>>> >>>>>>>>>>>>>>> was that with some combination of babel/rollup/webpack or >>>>>>>>>>>>>>> pure-es6? >>>>>>>>>>>>>>> if i want to develop a pure-es6 webapp (no babel), how would >>>>>>>>>>>>>>> i transition from development-mode (20 es-module files) -> production-mode >>>>>>>>>>>>>>> (1 rollup file)? >>>>>>>>>>>>>>> >>>>>>>>>>>>>>> >>>>>>>>>>>>>>> On Fri, May 31, 2019 at 10:47 AM Isiah Meadows < >>>>>>>>>>>>>>> isiahmeadows at gmail.com> wrote: >>>>>>>>>>>>>>> >>>>>>>>>>>>>>>> If it's bundled by Rollup or Webpack into a single bundle, >>>>>>>>>>>>>>>> it's >>>>>>>>>>>>>>>> equivalent to a single `<script type="module" src="...">` >>>>>>>>>>>>>>>> pointing >>>>>>>>>>>>>>>> towards the original entry point, excluding network >>>>>>>>>>>>>>>> requests.* But in >>>>>>>>>>>>>>>> either case, you aren't listing 50 scripts, you're only >>>>>>>>>>>>>>>> listing the >>>>>>>>>>>>>>>> entry module and importing child modules within parent >>>>>>>>>>>>>>>> modules. Rollup >>>>>>>>>>>>>>>> and Webpack do mostly the same thing browsers do when it >>>>>>>>>>>>>>>> comes to >>>>>>>>>>>>>>>> resolving dependencies, just they generate a bundle >>>>>>>>>>>>>>>> afterwards where >>>>>>>>>>>>>>>> browsers execute code afterwards. Also, it's worth noting >>>>>>>>>>>>>>>> that the gap >>>>>>>>>>>>>>>> between a single large request and multiple smaller >>>>>>>>>>>>>>>> requests has >>>>>>>>>>>>>>>> shrunk a lot since HTTP/2 came along, since it's binary, it >>>>>>>>>>>>>>>> allows >>>>>>>>>>>>>>>> requests and response data to be interleaved, it better >>>>>>>>>>>>>>>> leverages the >>>>>>>>>>>>>>>> underlying TCP protocol format, and it allows servers to >>>>>>>>>>>>>>>> send data >>>>>>>>>>>>>>>> pre-emptively without the client requesting it first. (Web >>>>>>>>>>>>>>>> sockets are >>>>>>>>>>>>>>>> built on this functionality.) It's still better to bundle >>>>>>>>>>>>>>>> in general, >>>>>>>>>>>>>>>> but it's less of a problem not to. >>>>>>>>>>>>>>>> >>>>>>>>>>>>>>>> This is *not* the case for `<script type="module">` >>>>>>>>>>>>>>>> elements - those >>>>>>>>>>>>>>>> operate more like inline scripts that happen to have the >>>>>>>>>>>>>>>> ability to >>>>>>>>>>>>>>>> `import`. >>>>>>>>>>>>>>>> >>>>>>>>>>>>>>>> Oh, and yes, I've loaded upwards of 50-100 modules in >>>>>>>>>>>>>>>> development. 20 >>>>>>>>>>>>>>>> modules is *easy* to achieve in single-page apps. >>>>>>>>>>>>>>>> >>>>>>>>>>>>>>>> * This is, of course, not the case if you are using pure >>>>>>>>>>>>>>>> ES6 and you >>>>>>>>>>>>>>>> aren't using any plugins to, say, run the original source >>>>>>>>>>>>>>>> through >>>>>>>>>>>>>>>> Babel for React + JSX or something. >>>>>>>>>>>>>>>> >>>>>>>>>>>>>>>> ----- >>>>>>>>>>>>>>>> >>>>>>>>>>>>>>>> Isiah Meadows >>>>>>>>>>>>>>>> contact at isiahmeadows.com >>>>>>>>>>>>>>>> www.isiahmeadows.com >>>>>>>>>>>>>>>> On Sat, May 25, 2019 at 2:12 AM kai zhu < >>>>>>>>>>>>>>>> kaizhu256 at gmail.com> wrote: >>>>>>>>>>>>>>>> > >>>>>>>>>>>>>>>> > Asynchronous loading differs only in >>>>>>>>>>>>>>>> > that it takes more code to express the same logic and you >>>>>>>>>>>>>>>> have to take >>>>>>>>>>>>>>>> > into account concurrent requests (and you need to cache >>>>>>>>>>>>>>>> the request, >>>>>>>>>>>>>>>> > not the result), but it's otherwise the same from 1km >>>>>>>>>>>>>>>> away. >>>>>>>>>>>>>>>> > >>>>>>>>>>>>>>>> > >>>>>>>>>>>>>>>> > so async-loading 50 ```<script type="module">``` tags >>>>>>>>>>>>>>>> > has equivalent side-effect >>>>>>>>>>>>>>>> > as sync-loading single webpack-rollup (of same 50 >>>>>>>>>>>>>>>> modules)? >>>>>>>>>>>>>>>> > >>>>>>>>>>>>>>>> > i have nagging suspicion of doubts. has anyone tried >>>>>>>>>>>>>>>> native async-loading large numbers (>10) of >>>>>>>>>>>>>>>> > ```<script type="module">``` tags, and verify it resolves >>>>>>>>>>>>>>>> identically to using a single webpack-rollup? >>>>>>>>>>>>>>>> > >>>>>>>>>>>>>>>> > again, i'm not that knowledgeable on es-modules, so above >>>>>>>>>>>>>>>> question may be trivially true, and i'm just not aware. >>>>>>>>>>>>>>>> > >>>>>>>>>>>>>>>> > -kai >>>>>>>>>>>>>>>> > >>>>>>>>>>>>>>>> > On 24 May 2019, at 23:41, Isiah Meadows < >>>>>>>>>>>>>>>> isiahmeadows at gmail.com> wrote: >>>>>>>>>>>>>>>> > >>>>>>>>>>>>>>>> > There's two main reasons why it scales: >>>>>>>>>>>>>>>> > >>>>>>>>>>>>>>>> > 1. Modules are strongly encapsulated while minimizing >>>>>>>>>>>>>>>> global pollution. >>>>>>>>>>>>>>>> > 2. The resolution algorithm applies the same logic no >>>>>>>>>>>>>>>> matter how many >>>>>>>>>>>>>>>> > modules are loaded. >>>>>>>>>>>>>>>> > >>>>>>>>>>>>>>>> > It's much easier for it to scale when you write the code >>>>>>>>>>>>>>>> unaware of >>>>>>>>>>>>>>>> > how many modules you might be loading and unaware of how >>>>>>>>>>>>>>>> deep their >>>>>>>>>>>>>>>> > dependency graph is. Fewer assumptions here is key. It's >>>>>>>>>>>>>>>> an >>>>>>>>>>>>>>>> > engineering problem, but a relatively simple one. >>>>>>>>>>>>>>>> > >>>>>>>>>>>>>>>> > If you want a short example of how sync module resolution >>>>>>>>>>>>>>>> works, you >>>>>>>>>>>>>>>> > can take a look at this little utility I wrote: >>>>>>>>>>>>>>>> > https://github.com/isiahmeadows/simple-require-loader. >>>>>>>>>>>>>>>> That doesn't >>>>>>>>>>>>>>>> > asynchronously resolve modules, but it should help >>>>>>>>>>>>>>>> explain the process >>>>>>>>>>>>>>>> > from a synchronous standpoint. Asynchronous loading >>>>>>>>>>>>>>>> differs only in >>>>>>>>>>>>>>>> > that it takes more code to express the same logic and you >>>>>>>>>>>>>>>> have to take >>>>>>>>>>>>>>>> > into account concurrent requests (and you need to cache >>>>>>>>>>>>>>>> the request, >>>>>>>>>>>>>>>> > not the result), but it's otherwise the same from 1km >>>>>>>>>>>>>>>> away. >>>>>>>>>>>>>>>> > >>>>>>>>>>>>>>>> > ----- >>>>>>>>>>>>>>>> > >>>>>>>>>>>>>>>> > Isiah Meadows >>>>>>>>>>>>>>>> > contact at isiahmeadows.com >>>>>>>>>>>>>>>> > www.isiahmeadows.com >>>>>>>>>>>>>>>> > >>>>>>>>>>>>>>>> > On Thu, May 23, 2019 at 10:49 AM kai zhu < >>>>>>>>>>>>>>>> kaizhu256 at gmail.com> wrote: >>>>>>>>>>>>>>>> > >>>>>>>>>>>>>>>> > >>>>>>>>>>>>>>>> > actually, i admit i don't know what i'm talking about. >>>>>>>>>>>>>>>> just generally confused (through ignorance) on how large-scale es-module >>>>>>>>>>>>>>>> dependencies resolve when loaded/imported asynchronously. >>>>>>>>>>>>>>>> > >>>>>>>>>>>>>>>> > On Wed, May 22, 2019 at 10:42 PM Logan Smyth < >>>>>>>>>>>>>>>> loganfsmyth at gmail.com> wrote: >>>>>>>>>>>>>>>> > >>>>>>>>>>>>>>>> > >>>>>>>>>>>>>>>> > Can you elaborate on what loading state you need to keep >>>>>>>>>>>>>>>> track of? What is the bottleneck that you run into? Also to be sure, when >>>>>>>>>>>>>>>> you say async-load, do you mean `import()`? >>>>>>>>>>>>>>>> > >>>>>>>>>>>>>>>> > On Wed, May 22, 2019, 20:17 kai zhu <kaizhu256 at gmail.com> >>>>>>>>>>>>>>>> wrote: >>>>>>>>>>>>>>>> > >>>>>>>>>>>>>>>> > >>>>>>>>>>>>>>>> > i don't use es-modules. >>>>>>>>>>>>>>>> > but with amd/requirejs, I start having trouble with >>>>>>>>>>>>>>>> module-initializations in nodejs/browser at ~5 async modules (that may or >>>>>>>>>>>>>>>> may not have circular-references). 10 would be hard, and 20 would be near >>>>>>>>>>>>>>>> inhuman for me. >>>>>>>>>>>>>>>> > >>>>>>>>>>>>>>>> > can we say its somewhat impractical for most applications >>>>>>>>>>>>>>>> to load more than 50 async modules (with some of them having >>>>>>>>>>>>>>>> circular-references)? and perhaps better design/spec module-loading >>>>>>>>>>>>>>>> mechanisms with this usability concern in mind? >>>>>>>>>>>>>>>> > >>>>>>>>>>>>>>>> > p.s. its also impractical for me to async-load 5 or more >>>>>>>>>>>>>>>> modules without using globalThis to keep track of each module's >>>>>>>>>>>>>>>> loading-state. >>>>>>>>>>>>>>>> > _______________________________________________ >>>>>>>>>>>>>>>> > es-discuss mailing list >>>>>>>>>>>>>>>> > es-discuss at mozilla.org >>>>>>>>>>>>>>>> > https://mail.mozilla.org/listinfo/es-discuss >>>>>>>>>>>>>>>> > >>>>>>>>>>>>>>>> > >>>>>>>>>>>>>>>> > _______________________________________________ >>>>>>>>>>>>>>>> > es-discuss mailing list >>>>>>>>>>>>>>>> > es-discuss at mozilla.org >>>>>>>>>>>>>>>> > https://mail.mozilla.org/listinfo/es-discuss >>>>>>>>>>>>>>>> > >>>>>>>>>>>>>>>> > >>>>>>>>>>>>>>>> >>>>>>>>>>>>>>> _______________________________________________ >>>>>>>>>>>>>>> es-discuss mailing list >>>>>>>>>>>>>>> es-discuss at mozilla.org >>>>>>>>>>>>>>> https://mail.mozilla.org/listinfo/es-discuss >>>>>>>>>>>>>>> >>>>>>>>>>>>>> -------------- next part -------------- An HTML attachment was scrubbed... URL: <http://mail.mozilla.org/pipermail/es-discuss/attachments/20190603/d16534af/attachment-0001.html>
you would need to introduce a new language-syntax that hints delimited module-scope, e.g.
/*
* es-module.rollup.js
*
* example rolling-up es-modules with [hypothetical] pragma
* "use module_scope xxx";
* which would be web-compat and minifier-friendly
*/
"use module_scope ./aa.js";
// foo is scoped inside module_scope ./aa.js
var foo = ...
...
"use module_scope ./bb.js";
// foo is scoped inside module_scope ./bb.js
var foo = ...
...
i'll be honest. i'm not really proposing this language-syntax in good-faith, as javascript is already chock-full of confusing-features that are distracting/harmful to UX-workflow programming.
i'm mainly criticizing tc39 for their design-decision pushing through es-modules, and how disruptive it is to operationalize (natively, w/o transpiling) in production-systems. web-development could've stayed simpler if the committee had done absolutely nothing. people would've continued using es5-style rollups (w/ yui/amdjs-like module-loaders), and devop-folks wouldn't be forced to deal with import-maps and http2-push to solve a problem that shouldn't have existed.
you would need to introduce a new language-syntax that hints delimited module-scope, e.g. ```js /* * es-module.rollup.js * * example rolling-up es-modules with [hypothetical] pragma * "use module_scope xxx"; * which would be web-compat and minifier-friendly */ "use module_scope ./aa.js"; // foo is scoped inside module_scope ./aa.js var foo = ... ... "use module_scope ./bb.js"; // foo is scoped inside module_scope ./bb.js var foo = ... ... ``` i'll be honest. i'm not really proposing this language-syntax in good-faith, as javascript is already chock-full of confusing-features that are distracting/harmful to UX-workflow programming. i'm mainly criticizing tc39 for their design-decision pushing through es-modules, and how disruptive it is to operationalize (natively, w/o transpiling) in production-systems. web-development could've stayed simpler if the committee had done absolutely nothing. people would've continued using es5-style rollups (w/ yui/amdjs-like module-loaders), and devop-folks wouldn't be forced to deal with import-maps and http2-push to solve a problem that shouldn't have existed. On Sun, Jun 2, 2019 at 9:25 PM guest271314 <guest271314 at gmail.com> wrote: > > but that requires coordination among modules, which is not always > possible. the idea is to inline/rollup es-modules that may not have come > from same developers (and whom are unaware their es-modules collide w/ > others when rolled-up). > > How do you intend to know the names of the identifiers to import without > "coordination" and check for duplicate identifier names and duplicate > exports? > -------------- next part -------------- An HTML attachment was scrubbed... URL: <http://mail.mozilla.org/pipermail/es-discuss/attachments/20190602/ec7a1c88/attachment.html>
Thus far each of the prospective edge cases relevant to the proposal have been technically solved, save for duplicate identifier names and exports from the same file, which appears to be avoidable.
Have no "faith" in anything; "good" and "bad" preceding "faith" are as irrelevant as "faith" is.
You can use what is available now and write your own language in your spare time (What programming languages have been created by PPCG users? codegolf.meta.stackexchange.com/q/6918) though beware ("Anyone, from the most clueless amateur to the best cryptographer, can create an algorithm that he himself can't break." -Schneier, Bruce (1998-10-15). Memo to the Amateur Cipher Designer www.schneier.com/crypto-gram-9810.html#cipherdesign. Cryptogram newsletter. (aka Schneier's Law)).
Thus far each of the prospective edge cases relevant to the proposal have been technically solved, save for duplicate identifier names and exports from the same file, which appears to be avoidable. Have no "faith" in anything, therefore "good" and "bad" preceding "faith" are as irrelevant as "good" or "bad". You can use what is available now and write your own language in your spare time (What programming languages have been created by PPCG users? https://codegolf.meta.stackexchange.com/q/6918) though beware ("Anyone, from the most clueless amateur to the best cryptographer, can create an algorithm that he himself can't break." -Schneier, Bruce (1998-10-15). Memo to the Amateur Cipher Design <http://www.schneier.com/crypto-gram-9810.html#cipherdesign>. Cryptogram newsletter. (aka Schneier's Law) On Mon, Jun 3, 2019 at 4:12 AM kai zhu <kaizhu256 at gmail.com> wrote: > you would need to introduce a new language-syntax that hints delimited > module-scope, e.g. > > ```js > /* > * es-module.rollup.js > * > * example rolling-up es-modules with [hypothetical] pragma > * "use module_scope xxx"; > * which would be web-compat and minifier-friendly > */ > > "use module_scope ./aa.js"; > // foo is scoped inside module_scope ./aa.js > var foo = ... > ... > > "use module_scope ./bb.js"; > // foo is scoped inside module_scope ./bb.js > var foo = ... > ... > ``` > > i'll be honest. i'm not really proposing this language-syntax in > good-faith, as javascript is already chock-full of confusing-features that > are distracting/harmful to UX-workflow programming. > > i'm mainly criticizing tc39 for their design-decision pushing through > es-modules, and how disruptive it is to operationalize (natively, w/o > transpiling) in production-systems. web-development could've stayed > simpler if the committee had done absolutely nothing. people would've > continued using es5-style rollups (w/ yui/amdjs-like module-loaders), and > devop-folks wouldn't be forced to deal with import-maps and http2-push to > solve a problem that shouldn't have existed. > > > > On Sun, Jun 2, 2019 at 9:25 PM guest271314 <guest271314 at gmail.com> wrote: > >> > but that requires coordination among modules, which is not always >> possible. the idea is to inline/rollup es-modules that may not have come >> from same developers (and whom are unaware their es-modules collide w/ >> others when rolled-up). >> >> How do you intend to know the names of the identifiers to import without >> "coordination" and check for duplicate identifier names and duplicate >> exports? >> > -------------- next part -------------- An HTML attachment was scrubbed... URL: <http://mail.mozilla.org/pipermail/es-discuss/attachments/20190603/ca64341d/attachment.html>
That would be pure ES6 running in Chrome natively, before I introduced Webpack or Rollup to generate the bundle. Transitioning to those is as simple as:
- Installing the relevant build tool.
- Creating the relevant config file.
- Changing the HTML file to load the bundle instead of the entry point.
I generally use either a bundler in both dev + prod or just a bunch of ES6 modules in dev + prod - I don't mix them, because it makes it harder to maintain in the future. (Native for dev, Rollup for prod got unwieldy within literally just the entry point. Having to switch between entry points is itself enough to get in the way of things.)
Isiah Meadows contact at isiahmeadows.com, www.isiahmeadows.com
That would be pure ES6 running in Chrome natively, before I introduced Webpack or Rollup to generate the bundle. Transitioning to those is as simple as: 1. Installing the relevant build tool. 2. Creating the relevant config file. 3. Changing the HTML file to load the bundle instead of the entry point. I generally use either a bundler in both dev + prod or just a bunch of ES6 modules in dev + prod - I don't mix them, because it makes it harder to maintain in the future. (Native for dev, Rollup for prod got unwieldy within literally just the entry point. Having to switch between entry points is itself enough to get in the way of things.) ----- Isiah Meadows contact at isiahmeadows.com www.isiahmeadows.com On Fri, May 31, 2019 at 1:40 PM kai zhu <kaizhu256 at gmail.com> wrote: > > > Oh, and yes, I've loaded upwards of 50-100 modules in development. 20 > modules is *easy* to achieve in single-page apps. > > was that with some combination of babel/rollup/webpack or pure-es6? > if i want to develop a pure-es6 webapp (no babel), how would i transition from development-mode (20 es-module files) -> production-mode (1 rollup file)? > > > On Fri, May 31, 2019 at 10:47 AM Isiah Meadows <isiahmeadows at gmail.com> wrote: >> >> If it's bundled by Rollup or Webpack into a single bundle, it's >> equivalent to a single `<script type="module" src="...">` pointing >> towards the original entry point, excluding network requests.* But in >> either case, you aren't listing 50 scripts, you're only listing the >> entry module and importing child modules within parent modules. Rollup >> and Webpack do mostly the same thing browsers do when it comes to >> resolving dependencies, just they generate a bundle afterwards where >> browsers execute code afterwards. Also, it's worth noting that the gap >> between a single large request and multiple smaller requests has >> shrunk a lot since HTTP/2 came along, since it's binary, it allows >> requests and response data to be interleaved, it better leverages the >> underlying TCP protocol format, and it allows servers to send data >> pre-emptively without the client requesting it first. (Web sockets are >> built on this functionality.) It's still better to bundle in general, >> but it's less of a problem not to. >> >> This is *not* the case for `<script type="module">` elements - those >> operate more like inline scripts that happen to have the ability to >> `import`. >> >> Oh, and yes, I've loaded upwards of 50-100 modules in development. 20 >> modules is *easy* to achieve in single-page apps. >> >> * This is, of course, not the case if you are using pure ES6 and you >> aren't using any plugins to, say, run the original source through >> Babel for React + JSX or something. >> >> ----- >> >> Isiah Meadows >> contact at isiahmeadows.com >> www.isiahmeadows.com >> On Sat, May 25, 2019 at 2:12 AM kai zhu <kaizhu256 at gmail.com> wrote: >> > >> > Asynchronous loading differs only in >> > that it takes more code to express the same logic and you have to take >> > into account concurrent requests (and you need to cache the request, >> > not the result), but it's otherwise the same from 1km away. >> > >> > >> > so async-loading 50 ```<script type="module">``` tags >> > has equivalent side-effect >> > as sync-loading single webpack-rollup (of same 50 modules)? >> > >> > i have nagging suspicion of doubts. has anyone tried native async-loading large numbers (>10) of >> > ```<script type="module">``` tags, and verify it resolves identically to using a single webpack-rollup? >> > >> > again, i'm not that knowledgeable on es-modules, so above question may be trivially true, and i'm just not aware. >> > >> > -kai >> > >> > On 24 May 2019, at 23:41, Isiah Meadows <isiahmeadows at gmail.com> wrote: >> > >> > There's two main reasons why it scales: >> > >> > 1. Modules are strongly encapsulated while minimizing global pollution. >> > 2. The resolution algorithm applies the same logic no matter how many >> > modules are loaded. >> > >> > It's much easier for it to scale when you write the code unaware of >> > how many modules you might be loading and unaware of how deep their >> > dependency graph is. Fewer assumptions here is key. It's an >> > engineering problem, but a relatively simple one. >> > >> > If you want a short example of how sync module resolution works, you >> > can take a look at this little utility I wrote: >> > https://github.com/isiahmeadows/simple-require-loader. That doesn't >> > asynchronously resolve modules, but it should help explain the process >> > from a synchronous standpoint. Asynchronous loading differs only in >> > that it takes more code to express the same logic and you have to take >> > into account concurrent requests (and you need to cache the request, >> > not the result), but it's otherwise the same from 1km away. >> > >> > ----- >> > >> > Isiah Meadows >> > contact at isiahmeadows.com >> > www.isiahmeadows.com >> > >> > On Thu, May 23, 2019 at 10:49 AM kai zhu <kaizhu256 at gmail.com> wrote: >> > >> > >> > actually, i admit i don't know what i'm talking about. just generally confused (through ignorance) on how large-scale es-module dependencies resolve when loaded/imported asynchronously. >> > >> > On Wed, May 22, 2019 at 10:42 PM Logan Smyth <loganfsmyth at gmail.com> wrote: >> > >> > >> > Can you elaborate on what loading state you need to keep track of? What is the bottleneck that you run into? Also to be sure, when you say async-load, do you mean `import()`? >> > >> > On Wed, May 22, 2019, 20:17 kai zhu <kaizhu256 at gmail.com> wrote: >> > >> > >> > i don't use es-modules. >> > but with amd/requirejs, I start having trouble with module-initializations in nodejs/browser at ~5 async modules (that may or may not have circular-references). 10 would be hard, and 20 would be near inhuman for me. >> > >> > can we say its somewhat impractical for most applications to load more than 50 async modules (with some of them having circular-references)? and perhaps better design/spec module-loading mechanisms with this usability concern in mind? >> > >> > p.s. its also impractical for me to async-load 5 or more modules without using globalThis to keep track of each module's loading-state. >> > _______________________________________________ >> > es-discuss mailing list >> > es-discuss at mozilla.org >> > https://mail.mozilla.org/listinfo/es-discuss >> > >> > >> > _______________________________________________ >> > es-discuss mailing list >> > es-discuss at mozilla.org >> > https://mail.mozilla.org/listinfo/es-discuss >> > >> >
i don't use es-modules. but with amd/requirejs, I start having trouble with module-initializations in nodejs/browser at ~5 async modules (that may or may not have circular-references). 10 would be hard, and 20 would be near inhuman for me.
can we say its somewhat impractical for most applications to load more than 50 async modules (with some of them having circular-references)? and perhaps better design/spec module-loading mechanisms with this usability concern in mind?
p.s. its also impractical for me to async-load 5 or more modules without using globalThis to keep track of each module's loading-state.