Overcoming JavaScript Load Issues: Import Maps and Performance Enhancements - JSJ 643
In this episode, they dive deep into the intricate world of JavaScript loading and web performance. Join the panel with insightful discussions led by Dan, Charles, Steve, and special guest Yoav Weiss—an expert with extensive experience in web performance from his time at Google, Akamai, and Shopify.
Special Guests:
Yoav Weiss
Show Notes
In this episode, they dive deep into the intricate world of JavaScript loading and web performance. Join the panel with insightful discussions led by Dan, Charles, Steve, and special guest Yoav Weiss—an expert with extensive experience in web performance from his time at Google, Akamai, and Shopify.
They explore the latest initiatives aimed at improving ES modules, import maps, and the challenges faced with script loading, especially when dealing with web workers. They uncover the critical role of sub-resource integrity, the successful integration of integrity support in Chrome and Safari, and the urgent need for advanced import map solutions for large applications.
They also delve into the nuts and bolts of optimizing web performance, including the impact of script execution on browser responsiveness, bundling techniques, and innovative strategies for managing resource download priorities. Tune in to hear about the latest developments, engage with provocative questions, and discover ways you can contribute to the ongoing work of the W3C web performance working group. Plus, stay for heartfelt moments, personal anecdotes, and practical recommendations from the speakers.
They explore the latest initiatives aimed at improving ES modules, import maps, and the challenges faced with script loading, especially when dealing with web workers. They uncover the critical role of sub-resource integrity, the successful integration of integrity support in Chrome and Safari, and the urgent need for advanced import map solutions for large applications.
They also delve into the nuts and bolts of optimizing web performance, including the impact of script execution on browser responsiveness, bundling techniques, and innovative strategies for managing resource download priorities. Tune in to hear about the latest developments, engage with provocative questions, and discover ways you can contribute to the ongoing work of the W3C web performance working group. Plus, stay for heartfelt moments, personal anecdotes, and practical recommendations from the speakers.
Sponsors
Socials
Picks
- AJ - Jason Bourne 5-part Trilogy
- AJ - Crucial MX500 has dethroned SP as my pick for best value server SSD
- Charles - Imaginiff | Board Game
- Charles - A Quiet Place: Day One (2024)
- Steve - How Does OpenAI Survive?
Transcript
Charles Max Wood [00:00:05]:
Hey, folks. Welcome back to another episode of JavaScript Jabber. This week on our panel, we have Steve Edwards.
Steve Edwards [00:00:11]:
Yo, yo, yo, coming at you live from Portland. I'm filling in for AJ since he's not here right now.
Charles Max Wood [00:00:18]:
Right. We also have Dan Shapir.
Dan Shappir [00:00:20]:
Hey. Sitting in the air conditioning room in hot and sunny Tel Aviv.
Charles Max Wood [00:00:26]:
Yeah. I'm Charles Max Wood from Top End Devs, and we have a special guest this week, and that's Yoav, Weiss. Do you wanna introduce yourself? Let people know if we've had you on before, so I think some people know who you are, and then
Yoav Weiss [00:00:39]:
there may be a few people.
Dan Shappir [00:00:40]:
They don't. They should.
Charles Max Wood [00:00:41]:
Yeah. Sure.
Yoav Weiss [00:00:43]:
I I can introduce myself. So, hey, I'm Yoav. I've been working on web performance for way too long, trying to solve it and so far, not being super successful. I've been, working on browsers since 2012, and initially on my own, then at Akamai, working on both, browsers and server features, then at Google for a few years, and nowadays I'm at Shopify still working on the web platform. Amongst other things, I co chair the web performance working group, and I'm one of the blank API owners, which is basically, the folks that sign off on features getting released in Chromium.
Dan Shappir [00:01:46]:
The working group is it's worth mentioning is part of the w three c.
Yoav Weiss [00:01:50]:
Yes. Yeah. Yeah. The w three c work performance working group. Yeah.
Steve Edwards [00:01:54]:
I would like to point out that it's from a visual standpoint, it's easy to tell how smart he is by his haircut. Just saying.
Dan Shappir [00:02:00]:
So Yeah. He's one of these guys that shaves his head even though he has hair. Yeah.
Yoav Weiss [00:02:08]:
I see. Yeah. I
Steve Edwards [00:02:09]:
I can say it.
Yoav Weiss [00:02:10]:
Accordingly. Yeah. I wouldn't define it as has hair. But yeah.
Steve Edwards [00:02:15]:
Well, got made only so many perfect heads and the rest he covered with hair. So
Charles Max Wood [00:02:19]:
That's right.
Dan Shappir [00:02:20]:
Like like to say that, I'm, also, I'm an invited expert on the that same working group. The guy who invited me over is. So I'm very thankful for that.
Yoav Weiss [00:02:33]:
I'm I'm thankful for your contribution. So
Dan Shappir [00:02:36]:
Yeah. Doing fighting the good fight, trying to make the web faster for everybody's sake.
Charles Max Wood [00:02:43]:
So, Yoav, we got this, document from you about JavaScript floating, and it it it's interesting because it starts off with you change jobs. So Yeah. You wanna kinda give us some context on that and then, we can jump in and talk about JavaScript loading?
Yoav Weiss [00:03:00]:
Yeah. Sure. So yeah. So, basically, I yeah. Like I said, worked on Chrome at Google for, 5 years, up until a few months back. And yeah. And earlier this year, I changed employers, but the good thing about open source is that I get to do a lot of the same things, with a different head on. Basically, I've been working on making the web faster by default.
Yoav Weiss [00:03:36]:
I've been doing that, before, joining Google, and I get to do that afterwards. So I continue to work on, on Chromium. I now also get to work on WebKit, which is an a refreshing change. And the only thing with, I guess, with the change from working for a browser vendor to working more, like, closer to the industry, it kinda helps to keep me aligned with what developers actually need. Because, working for a browser vendor is great, but it's also it makes it hard to keep up with what actual developers are doing because browser developers are not web developers, at least not really. Yeah. And working as part of the, you know, quote, unquote industry makes it easier, to make sure that my work is actually aligned with what people need. So that part is something I'm very very happy about.
Yoav Weiss [00:04:51]:
Yeah. Other than that, there aren't a lot of commerce voices amongst, people who work on browsers. So I'm very happy to bring in that perspective to those discussions.
Dan Shappir [00:05:04]:
That's especially interesting given that probably the organizations or or the the web, that's websites, web apps that have potentially the greatest need for web performance or see the greatest impact from from improving web performance are commerce related websites in many cases. Yeah. Like, there's always, those, you know, research papers showing, like, Amazon increased their revenue by a $1,000,000,000,000 because they sped up loading time by 5 milliseconds or something along these lines.
Charles Max Wood [00:05:42]:
Right. Yeah.
Yoav Weiss [00:05:42]:
I I don't know about these exact numbers, but, but, yeah, basically, performance is very important. There are a lot of public case studies about the relationship between, web performance and conversion rates. And I'm biased, but it seems to me that it's, like, crucial to have that kind of influence on, you know, on web standards and and and where the web platform is going.
Dan Shappir [00:06:12]:
Yeah. By the way, the the Google driven website web.dev, which is an excellent website, has case study section, which actually has real numbers, not numbers invented by me, that describe how companies did, in fact, significantly increase their conversion, their income, their whatever, thanks to improving performance. And like you said, it's not it's not really surprising. You know, it's we have we're in an age of, you know, little patience and a lot of distractions. And if your website takes too long to load, then people will go elsewhere.
Yoav Weiss [00:06:55]:
Yeah. If you if you remove friction, good things happen. That's a general Yep. Yeah.
Dan Shappir [00:07:02]:
It reminds me of when I told someone that, the, the, the pipeline or the the funnel at the previous company that I worked at is implemented in Angular. Their response was, don't let Angular get between your customers and potential customers and the payments. Something along these lines. But but yeah. It's it is important to reduce friction as much as possible, and improving performance is certainly a good way to do that.
Charles Max Wood [00:07:40]:
So we're we're talking about, JavaScript loading today. So so how does that get into this friction or frictionless performance of setup?
Yoav Weiss [00:07:53]:
So I've been unhappy with the way that JavaScript is being loaded on the web for a long while, but haven't been able to move that, too much just yet. But it's, essentially, I think that in in many ways, when we're looking at, web performance and loading performance, there isn't really a good way to load JavaScript. And the main advice that web performance folks can tell people or have been telling people, is just to load less JavaScript, which is correct, but not necessarily useful in today's, web development environment. If you can load your site, with less JavaScript, you should. And but at the same time, there are a lot of JavaScript based apps. But, like, even for those, loading performance matters. Loading performance matters because your users, interact with your website. They they will right click and open a new tab.
Yoav Weiss [00:09:15]:
They will reload. Your browser will unload your app in the background, in order to save memory. And in those cases, you're, you're effectively hitting reload even if you, even if your, if your site is, you know, there all day, there are a lot of interactions where loading performance matters. So, essentially, there are no good ways today to load scripts. And, yeah, Ben and I as part of, we started enumerating the different number of ways of, that you can load scripts. But it's essentially if if you go back to the basics, we have blocking scripts that are, you know, they are not a not a good pattern because they are blocking the parser from, processing the rest of the document. There are async scripts who are not necessarily a good pattern because they are racy and will potentially get in the way of more important things if they happen to load earlier. And we have deferred scripts who are real like, it's it's a relatively, well defined model, and it doesn't block the rent the the parser.
Yoav Weiss [00:10:41]:
But at the same time, they are often like, they're they're always loading at a single milestone, a single point in time in the page life cycle, and that may or may not be sufficient. So
Dan Shappir [00:10:56]:
I I think, though, it is important to mention that even though so talking about blocking scripts, which are the most obvious way, in in in kind of the oldest way, I guess, because, really, if you don't say anything else, then a script is blocking by by default. Like, the this is the way the web was originally built. It's it's problematic. Like you said, it's usually bad, but it's needed because sometimes you need to do some things before rendering can proceed. So it's it's when we say blocking, what it really means is render blocking. Means that when the browser hits that point, that script tag, it has to stop rendering until that script finishes. I know that some browsers do hacks around that. But really, at the logical level, that's what it means.
Yoav Weiss [00:11:55]:
Right? Yeah. But there so there is a better alternative to that, which is, blocking equals render, which gives you, essentially, it gives your async script or deferred script the ability to block rendering, but not log the parser. So the browser can continue to do work, but the user doesn't see things flashing around beak before that's script.
Dan Shappir [00:12:26]:
Oh, yeah. I I forgot that one, and maybe I should have even added that to the list. In in this in this context, it's, you know, the the web is something of of, you know, like an archaeological site. You know? And it's it's layers upon layers of history. And and the thing about the web is that once something has been implemented, it can almost never be taken away and must be supported forever and ever. So in the very olden days, I think it was Brendan Eich that introduced the concept of document rights, which enabled JavaScript to kind of inject content into the HTML stream, into the document downloading stream. And therefore, because of that, scripts had to be blocking because you couldn't proceed with processing the HTML just in case something happened to be injected into it. Now, nobody uses document for well, I can't say nobody.
Dan Shappir [00:13:31]:
But hardly anybody uses document right anymore. It's like a fraction of a fraction of a percent of websites, I would say. But but it still needs to be there. You're smiling, Yoft. So I'm guessing more websites you're saying that I would like to work.
Yoav Weiss [00:13:50]:
I'm sure there are stats, and we can let me see if I
Dan Shappir [00:13:54]:
can like, like, SSL VPNs or something. Use it for evil thing, nefarious things, or maybe all sorts of firewalls or whatnot. Use it for for crazy stuff. But but it's not something that that's put a difficulty. 99.99% of web developers don't use it. And but it still needs to be supported, so it's still there. So scripts are not just render blocking, they're download and parsing blocking as it were. And like you have said, if you put loading equals render, then you're telling it basically telling the browser, look.
Dan Shappir [00:14:35]:
You need to pause the rendering because maybe I'm doing logic around dark mode, and I don't want content flashing or something. So you need to pause the rendering, but I'm not using document right. I promise. So you can actually continue parsing stuff because I won't be modifying the the download the document stream. So yeah. I I I to be honest, like I said, I actually forgot about about that that option. Another, by the way, interesting option is, again, if you have a blocking script, whether it's in the head or the bottom of the body, that also kind of modifies the behavior as I recall. Like, browser is not the priority.
Yoav Weiss [00:15:24]:
It it modifies the priority. It's not like the the script will block parsing whenever it's discovered. But if it's discovered at the bottom of the document that, like, parser blocking doesn't have a huge effect because there's nothing more than that actual script to parse. So it's blocking nothing behind it. So if you're looking browsers
Dan Shappir [00:15:52]:
yeah. We talked about it with Robin Marks. Some browsers in that scenario would actually reduce the priority of the script download. Some don't, by the
Yoav Weiss [00:16:03]:
way. Yes. Yeah. The whole, yeah. So there are generally for blocking scripts. Browsers all browsers nowadays have a mechanism or all all commercial browsers, like, if I'm I I'm not sure about, for example, Lady Bird, but, all big browsers, have a mechanism where they continue to parse the document in order to speculatively fetch resources when they're when they encounter a blocking script. And, yes, whenever like, a blocking script at the head would have a higher priority in some browsers than a blocking script at the bottom. But all the, like, the priorities as well as this speculative, preloading of assets of resources, none of that is specified.
Yoav Weiss [00:16:59]:
So every browser can pretty much do their thing and web developers shouldn't really rely on it. Yes. So basically, we have multiple, multiple ways to load scripts. I am unhappy with all of them. And then, we have essentially for, like, the future of script loading for the last, I don't know how many years, have been ES modules.
Dan Shappir [00:17:33]:
And one more thing before we get to ES modules. Sure. I think that another key aspect that confuses people when they think about script loading, but really any asset loading in the browser, is that the difference between important and urgent isn't always obvious. That some stuff is important because the page can't work without it, but it might not be urgent as in that certain things need to be downloaded sooner. So for example, in this day and age of, SSR and SSG where we present stuff visually before it actually becomes interactive. Like, there's a difference in time between when a page is seen and when a page becomes interactive, you might say that visibility is more urgent than interactivity as long as the difference between the two is sufficiently small.
Yoav Weiss [00:18:40]:
Like, I'm not sure I personally
Dan Shappir [00:18:41]:
it's a painful it's a painful thing because because sufficiently small is is a problematic definition in and of itself. And if it's even slightly too big, it becomes a real problem. Like, the page literally doesn't properly respond to user interactions, which is worse than slow. It's literally broken. But, but yeah. I I still think that this distinction between what is urgent and what is important. Like, what is important is stuff that the page can't properly work without. If a certain image, for example, is not downloaded, that's not necessarily important if it's if it's doesn't get in the way of the pages operation.
Dan Shappir [00:19:24]:
So you get a broken icon. Right? You know, it still work. On the other hand, let's say if the CSS doesn't download, then there's a good chance that the page becomes totally illegible. So that's kind of really important. And it's also urgent because you need that CSS really quickly. And JavaScript can be somewhere in the middle between these 2.
Yoav Weiss [00:19:46]:
Yeah. Yeah. I guess fonts also is, you know, one of those assets which is like, there's no good way to load them because they are potentially important for branding and user experience and whatnot. But if they don't download the new fault system fonts, that's also, like, it's still a usable site. So, yeah. There's also so it's an interesting distinction between important and urgent. I think that there's also no current way like, another interesting distinction that there's no way to express today is, the difference between when when you want the script to load and when you want the script to execute. And at least for async scripts, those 2 happen at the same time.
Yoav Weiss [00:20:45]:
As soon as the script is loaded and the main thread is clear, that script gets executed, and that may or may not be the right choice depending on when you need that script. So there are scripts that you want them to, like, load earlier, but still wants to be able to control their execution either manually, and then you can use preload for that, but that is hacky and cumbersome. Or otherwise, the only currently official milestone you have in the page, life cycle is the DOM content loaded. When the whole HTML finished parsing, that's when deferred scripts trigger. And, yeah, there's no way today to express different preferences there.
Dan Shappir [00:21:39]:
And again, there is even a a middle step in between the two that's kind of less important, but still exists, that people might want to be aware of, which is the parsing. So you're really you're really downloading the script. You're parsing the script, and then you're executing the parts the parsed script. Now per my recollection, some browsers, not all browsers, can parse the script as it downloads. Some of them can even do it off of off of the main thread. Some don't. Some bundlers get in the way of this by putting all the script inside strings and then converting those strings into scripts, which I never really understood why bundlers do that, but some of them do.
Yoav Weiss [00:22:34]:
I did not know that. That's that's interesting, and that seems yeah. I
Dan Shappir [00:22:42]:
think Webpack does that in in certain situations at least.
AJ O'Neil [00:22:47]:
I wonder if it's dev mode.
Dan Shappir [00:22:50]:
I don't think so. I think that if you I I don't I don't think it's dev mode, is right.
Yoav Weiss [00:22:55]:
Okay. That's that's interesting, and that can also that can get in the way of, yeah, of parsing, like, a parallel parsing in the background. It can also maybe get in the way of code caching. Although, I guess, if those strings don't change, then eventually yeah. I'm yeah. Not sure. But it's it it seems less than ideal.
Dan Shappir [00:23:23]:
So you were saying that we can separate so the the downloading and parsing can happen together, not even so we can actually download without parsing by prefetching. We can download and and parse together by but not execute by preloading, Or we can just load the script which does all 3 or maybe avoid some of them if you've already prefetched or preloaded.
Yoav Weiss [00:23:55]:
Yes. But the problem with the script loading, like, if the the most straightforward mechanism for just loading the script doesn't give you any control regarding to when that script is executed at least when you're going with async scripts. And, like, with deferred as well, it gives you a certain point in time in which your script will execute. And
Dan Shappir [00:24:19]:
Yeah. So so talking about the sync scripts for a second. So sync script scripts become a sync either because you explicitly put the sync attribute on the script tag, Or if you've added them dynamically into the HTML, then they are synced by default as I recall.
Yoav Weiss [00:24:42]:
Yeah.
Dan Shappir [00:24:43]:
Or if there are are modules by default to sync or deferred. I always forget
Yoav Weiss [00:24:50]:
deferred. Modules are deferred by default.
Dan Shappir [00:24:52]:
Okay. So those are the 2 scenarios in which it's a sync. A sync as its name implies downloads without blocking. It downloads the background. But the problem with it, as you said, is that it's executed as soon as it's it's finished downloading and the browser can execute it, it will execute it.
Yoav Weiss [00:25:15]:
Yes.
Dan Shappir [00:25:15]:
Which means that there's no guarantee about order of things and what else the browser may or may not have done.
Yoav Weiss [00:25:22]:
Yeah. And beyond the lack of guarantees regarding ordering, I've seen a lot of cases in the past where, you know, people have some scripts are critical for, for rendering. They are like, they contain they render the main content and other scripts aren't. People load all of them with async scripts. And then if you naively preload those scripts, basically, if if if you make async scripts go faster, some pages will get slower, some pages will get will get faster, and some will see a mix of book like, essentially both, where, some parts of the, like, some parts of the critical experience get faster, but then they there are other scripts that should have run later that get in the way. Because execute execution times essentially, grabs a hold of the of the main thread for things that aren't critical. Yeah.
Dan Shappir [00:26:29]:
So, again, you're you're saying something is not urgent. I'll make it a sync. But what you're not taking into account is that the browser will start downloading it immediately even if at the lower priority. And if it happens to be a relatively quick download, then it might get executed faster than you expect ahead of more more urgent stuff. And if its execution is lengthy for any reason whatsoever, because it loops up to a trillion or whatever, then you're basically stuck. So you either need to write if it's your own script, you need to write it in a way that ensures that it doesn't execute really too soon. Or, alternatively, you might want to load it at a later time, not just using a sync.
Yoav Weiss [00:27:20]:
Yeah. And in the past, I've seen optimizations that preloaded things and made, like, made everything slower because those async scripts ran too too early.
Dan Shappir [00:27:34]:
And, again, we kind of spoke about it with Robin as well. The reason that people preload scripts, you might ask if I'm loading scripts up front, why would I preload the scripts? You know, seems like a useless operation. But the thing is that preloading actually impacted the the download priority or could impact the download priority, which could make the scripts that are making air quotes download faster. These days, you've got more let's call it the natural way of doing it, which is the fetch priority, attribute.
Yoav Weiss [00:28:11]:
Yeah. But you also have, you know, there are systems out there who detect scripts as, like, get, for example, script URLs from run data and then automatically preload those in order to excel. Like, let's get all the scripts that loaded before FCP or or LCP, preload them, and then make things faster. And some of those scripts are in HTML and could have just had the fetch priority, but some of them are late discovered and, are dynamically injected through other scripts, and that part is not like it's less trivial. Like, in those cases, preload helps more. Also, we used to have a thing called, server push, which even, like, loaded these scripts even earlier. And those kind of optimizations often ended up with, basically Mixed results. Yeah.
Yoav Weiss [00:29:18]:
Bimodal results. Some pages get way faster. Some pages get way slower. And it's very pages
Dan Shappir [00:29:25]:
get faster in some scenarios and slower in other scenarios. Yeah. Yeah. Like, depending on network conditions and stuff like that.
Yoav Weiss [00:29:32]:
Yeah.
Dan Shappir [00:29:32]:
Yeah. So we live in
Yoav Weiss [00:29:33]:
So what do we do then?
Steve Edwards [00:29:34]:
It's
Charles Max Wood [00:29:34]:
a tough one. It it sounds like you're kind of outlining what the the issues could be, but then yeah. What do I, as the regular old web developer, do to make this better?
Yoav Weiss [00:29:51]:
So right now, I I don't really have I I don't have a perfect answer. I can like, I think as a web developer, you should probably prefer deferred scripts over Yeah. Basing
Dan Shappir [00:30:07]:
or Defer defer is defer is the good baseline. Always start with defer with you when you can.
Yoav Weiss [00:30:13]:
Yeah. With the caveat that deferred scripts all run-in a sing like, all of your pages deferred scripts run-in a single task, and they don't get interrupted. So that could be a source of responsiveness issues, because they're
Dan Shappir [00:30:33]:
Is that clear? I think you need to explain what that means.
Yoav Weiss [00:30:38]:
Okay. Sure. Let's say I have a page with 10 different deferred scripts from different sources. All of these scripts, will run one after the other without, the ability for browsers to interject and handle events while all those scripts are running. At least that's the current, Chromium implementation, and I believe other browsers follow the same pattern. It's not really defined in like, the spec doesn't force that kind of behavior as far as I know. But at the same time, it will be somewhat risky to change it because pages can break if side effects can now be internally then between in in between deferred scripts. So, basically, what that means is that, yeah, we can't handle any events between those different scripts.
Yoav Weiss [00:31:41]:
We can't handle any microtasks, any promise resolutions. And and that
Dan Shappir [00:31:49]:
Going going back to your example, if we've got ten scripts and each one of them runs for a 100 milliseconds, then effectively your browser is stuck for a whole second and won't respond to any user interactions during that one second, which might be less than ideal.
Yoav Weiss [00:32:06]:
Yeah. So yeah. So I I would like, my baseline recommendation would be deferred scripts, but there's this caveat to take into account if your scripts are ex if you expect those scripts to run for a long while, then maybe the first script is not the best option there occur. Like, there is current effort, to modify this behavior, but, yeah, it it's not not trivial because there is risk, compatibility risk in changing it. So, essentially, yeah, I think that today's best option is maybe, like, yeah, somewhere in between ASIC and deferred, but both of them have drawbacks.
Dan Shappir [00:33:04]:
I think that that most bundlers or most meta frameworks either put use defer with all the downsides because, like we said, it's it's the best of the worst. Or, alternatively, they use blocking scripts at the very end of the document. I think those are the most common ways that most, frameworks use because it's also the safest approach in a lot of ways.
Yoav Weiss [00:33:36]:
Yeah. I guess.
Dan Shappir [00:33:38]:
And and as we said, there are two ways to get deferred behavior. Either you add the deferred attributes or you put the type equals module, which makes your script an e s ESM module, and then it's deferred by default.
Yoav Weiss [00:33:55]:
Yeah. Which kinda brings me to the problems with ES modules because they are also not, like, they are how a lot of people, at least a lot of people around me are writing code. They are not necessarily how a lot of people are delivering code. Bundlers, a lot of bundlers are turning ESM into, COM JS or other, classic script patterns. And the reason for that is that if you deliver ES modules to the browser and rely on that, essentially have static imports as part of what you deliver, those static imports are, by definition, discovered late. The browser needs to parse that first script in order to discover the 2nd layer of imports. It downloads them, it parses them, and and it's only then discovers the 3rd layer of imports and so on and so forth. So by definition, you're hitting a waterfall pattern.
Yoav Weiss [00:35:09]:
If you are delivering ES modules as is to the browser.
Dan Shappir [00:35:16]:
And those and those static imports, if I recall correctly, are are blocking. Right?
Yoav Weiss [00:35:25]:
They are blocking the script from running. Yes. They all and and yeah. Essentially, the whole module 3 will wait until everything is loaded and only then will it execute in a single task. Similar to how the fur like, it basically, you wouldn't have, a way to interrupt the browser won't have a way to interrupt this single task of the script while it's running. So the But
Dan Shappir [00:35:54]:
but will
Yoav Weiss [00:35:55]:
load at once.
Dan Shappir [00:35:56]:
But if you I I I don't know if you remember, but do it is the browser itself responsive during that import? Or is it kind of like an alert or something?
Yoav Weiss [00:36:08]:
So the renderer will not be so while everything is downloaded, the main thread is still free. It's just when when some like, when something when when the module 3 starts executing, that's when, the main thread blocks.
Dan Shappir [00:36:32]:
So So execution so execution is blocked, but not the browser until all these imports finish.
Yoav Weiss [00:36:40]:
Yeah. Yeah. The the download of the imports is done asynchronously. Okay. But it's it's late, like, there's a discoverability problem.
Dan Shappir [00:36:49]:
Yeah. The browser
Yoav Weiss [00:36:50]:
doesn't know about them until it parses, like, doesn't know about the next layer until it parses the layer above it.
Dan Shappir [00:36:58]:
Okay. But there is a solution for that kind of. Isn't there? With module preloads or stuff like that?
Yoav Weiss [00:37:04]:
Sure. But you would need to module preload the entire tree In in order for in order to solve this discoverability, you would need to module preload the entire tree. And and one more thing that I was surprised with, when poking at, ES modules from, like, slightly closer. Import maps are, which are maybe I should first start by talking about import maps. So essentially, import maps enable us to map module specifiers to URLs And that has a very strong, attribute of, enabling us to avoid invalidating entire trees if a single module has changed. So if if we have a module that is changed, Typically, when bundling modules, we are maintaining a hash or a version of that of that module in the URL itself. And those hash invalidations because it essentially, if one of the leaf modules have changed, that, its URL has changed as well. That means that the module that refers to it also has a content change that changes its hash, which then propagates up all the way, up the module tree.
Dan Shappir [00:38:58]:
Oh, so it kinda bubbles up the module tree if if any leaf kinda changed.
Yoav Weiss [00:39:04]:
Exactly.
Charles Max Wood [00:39:05]:
Incidentally, I'm just gonna point out that, import maps is what Rails uses now as it's,
Dan Shappir [00:39:12]:
default. Yeah. The whole, it's kind of the whole DHH thing, I think, is is avoiding bundlers and relying on the built in browser capabilities, which means ES modules, the the built in ES modules and and import maps.
Steve Edwards [00:39:28]:
Yep.
Yoav Weiss [00:39:28]:
Yeah. So import maps are great, for that purpose, but they are also, at least today, are rather fragile. And there can only be a single import map in a document, and it has to be the first thing that loads inside of that document. So if you have any module script that loads before an import map, the import map froze and nothing of what it does is valid. And if you have a very large JavaScript app that has, let's say, a few 1,000 modules, which I've now heard multiple real life examples of in multiple companies, you would have to load all of these thousands of modules, into your like, the mapping for all of those modules will have to be part of your initial import map, which is the very first thing that your HTML should contain. In line. So there are
Dan Shappir [00:40:42]:
In line? It has to be In line?
Yoav Weiss [00:40:44]:
Yes. There are no ex no supports for external module. Well, external import maps. And external like
Dan Shappir [00:40:53]:
better and better.
Yoav Weiss [00:40:54]:
Yeah. I I guess
Dan Shappir [00:40:57]:
I I guess I see the reason. I mean, given that it's so urgent and so so fragile, you don't want it as a separate document that you need to go and and and download on the side. But but still, it's it's not wonderful to to have this huge thing stuck at the very beginning of your lovely semantic document.
Yoav Weiss [00:41:24]:
Yeah. So I tend to agree. I think that we, like basically, what I've spent a large chunk of my day to day on is trying to figure out what a spec for having the ability to have multiple module multiple import maps and then merge them, what would that look like? And yeah. So I'm I'm basically I think this is one of the more urgent problems, for both, very large, JavaScript apps, but also for smaller ones that don't necessarily have control over their entire content. I don't know if you, like then if you imagine your days at Wix, like, there are a lot of CMSs that integrate content from multiple places. Some content is, you know, coming from the platform. Some content is coming from your, customers and their third parties, and you integrate all that together. And if any one of those folks is using an import map and another was using modules before it, everything breaks.
Dan Shappir [00:42:46]:
Yeah. I'm also thinking of stuff like, Google Tag Manager or any other kind of pixel system, which could theoretically or ideally benefit from from such a mechanism. But, again, you're bringing in resources from multiple vendors, from multiple URLs. You know, it's it's it's having a single source of truth and everything else ignored is a is a very problematic model.
Yoav Weiss [00:43:18]:
I agree. And I think, like, the the yeah. Dynamics crap loading from 3rd party, I think that's a very interesting use case here as well. And, yeah, that's so so basically, I think, yeah, that right now, there are a bunch of issues with ES modules and import maps and yeah. I'm I'm on my, you know, starting my path to fixing them.
Dan Shappir [00:43:51]:
And it can get even more complicated if you throw web workers into the mix, I would imagine.
Yoav Weiss [00:43:58]:
To be honest, I haven't even thought a whole lot about web workers in this context. I mean, there are, yeah. Because right now, they don't have a way to like, web workers don't have import maps.
Dan Shappir [00:44:14]:
And they need it because you can actually okay. So first of all, we talked about the various ways to load scripts. So web workers are another way to load scripts because if you do a new worker, the parameter you specify is the script file that gets loaded into that web worker. So, effectively, here's another way to load scripts. Not only that, there's a parameter that controls whether or not the script that you load into the web workers is ESM or not. It's ESM or classic, I think, and the default is classic, but it might be ESM. So you might be loading an ESM script into the web worker, and then you definitely would need some sort of a mapping mechanism to work with the worker.
Yoav Weiss [00:45:02]:
Yep. Yep.
Dan Shappir [00:45:03]:
Pun intended or pun not intended.
Yoav Weiss [00:45:06]:
I agree. And right now, yeah, import maps are only defined for documents and only defined With the
Dan Shappir [00:45:14]:
inline map.
Yoav Weiss [00:45:15]:
For for worker, you don't really have where to inline that import map today.
Dan Shappir [00:45:19]:
So would it use the do you again, I don't know if you remember, but would it use the documents, the parent document? So it just doesn't have a map at all, and that's it. I can kinda get it because it might be a shared worker and then where or or a service worker. And then where would it take the map from? But
Yoav Weiss [00:45:40]:
Yeah.
Dan Shappir [00:45:40]:
The web worker I don't know. Maybe.
Yoav Weiss [00:45:44]:
Yeah. Yeah. To be like, I think it's a very valid case. And yes. Module workers are the future especially because, import scripts for classic workers is also very, like, that's it's they're a fraud. Yeah. That It's bad. It is
Dan Shappir [00:46:10]:
I I I let's put it this way. I I made Wix, significant loaded scripts since web workers scripts significantly faster by hacking around import scripts, which is yet another way of loading scripts into the browser, and I won't even go there.
Yoav Weiss [00:46:29]:
Because it's loading them like, if you have a list of scripts, they will load sequentially.
Dan Shappir [00:46:35]:
Synchronously and sequentially.
Yoav Weiss [00:46:37]:
Synchronously and sequentially and yes. And that is like, without any good reason. So yeah.
Charles Max Wood [00:46:47]:
So or it sounds like you're working on a new, standard to to handle some of this. So what what does what does that look like and what are kind of the hang ups getting there?
Yoav Weiss [00:47:08]:
So so yeah. So basically, I've been, like, I'm planning to work on a bunch of, standard improvements or, web platform improvements on that front. So the the very first thing that already shipped, that was, missing from my perspective for ES modules is, integrity, sub resource integrity. So, SRI. If you're familiar with that, for regular, for classic scripts, you have an integrity attribute where you can say, only execute this script if, it matches this hash. So if as part of my build process, I like, I have controls over my build process, then I upload these assets somewhere. And then when the site loads, I wanna make sure that my assets match what I think they should be. And no one no malicious actor has switched them up in between.
Dan Shappir [00:48:19]:
Like, avoiding a man in the middle kind of attack.
Yoav Weiss [00:48:22]:
Mhmm. It's not really man in the middle. It's more of a, like, you know I don't know if there's a fancy name for it, but, basically, the content swap at rest. So the content is uploaded to your hosting provider, and then someone with the keys can swap it to add malicious payload. You want to avoid that scenario. You want to have, integrity checks in place in the browser.
AJ O'Neil [00:48:53]:
So you
Dan Shappir [00:48:53]:
can actually put an attribute on the script tag that says this is the check sum that my script should have. And if it doesn't, then just no digit.
Yoav Weiss [00:49:04]:
Yes. Same for CSS, and preload. And that's it. You can't do that for any other type of content, but that is sufficient because images are presumably not very important and at the same time, they are also harder to pull up. Like, harder to do that integrity check without slowing them down. But this piece was missing from, module imports. So if you have dynamic imports for modules where you want to, like, load the critical scripts upfront and then dynamically load stuff you need for later once things come calm down or once the user did something. Those scripts didn't have any way to to get an integrity check, without jumping through many hoops, because it didn't have like, there was no native support for ES modules and integrity checks.
Yoav Weiss [00:50:10]:
So the first step I took in that, potentially long path to making, script loading better is to add that kind of, that kind of support with an integrity section as part of the import map. So that has landed in Chrome 127 last week, hitting stable last week, and it's on its way to, Safari 18, which is presumably gonna hit users sometimes this fall. So that Cool. Yeah. Yeah. I'm it it was a relatively relatively fast, project. Basically, I, during a flight, put together initial prototype, initial spec, and, rudimentary tests. And then, like, the the whole thing took roughly 2 weeks to to
Dan Shappir [00:51:19]:
You you built you built Chrome while on a flight?
Yoav Weiss [00:51:23]:
Yes. This is what I do on a
Dan Shappir [00:51:30]:
flight. Interesting. Yeah. To each their own, I guess.
Charles Max Wood [00:51:35]:
So you've got the integrity check.
Yoav Weiss [00:51:39]:
So so are there other Yeah. That that was the first step. I think that the next step is probably, the multiple, import maps and dynamic import maps.
Charles Max Wood [00:51:54]:
Okay.
Yoav Weiss [00:51:55]:
I think that that's the the next thing to reduce fragility and, and and generally yeah. Make it more more feasible for large apps to use import maps, because the cache cascade problems that they solve are real, but, yeah, the the blocking nature is blocking.
Dan Shappir [00:52:19]:
Yeah. But that opens interesting questions, like, unless I'm I'm overthinking it may which is possible. I do that. But it for example, it it means that script a can control where unrelated script b loads from. Uh-huh. I'm kind of kind of it's kind of like what I would do with the service worker in a sense. Like, I I can tell it it says this URL, but actually download it from that URL.
Yoav Weiss [00:52:55]:
So Verify like, you wouldn't have the ability to redefine a script that was already loaded. No.
Dan Shappir [00:53:14]:
Obviously. So the
Yoav Weiss [00:53:15]:
Or a script that was, already defined in another import map. So you wouldn't be able to redefine a specifier.
Dan Shappir [00:53:24]:
So it's not like cascading. It's kind of like a join sort of the same.
Yoav Weiss [00:53:31]:
A join where, you know, first in stays kinda.
Dan Shappir [00:53:38]:
Yeah. No variety.
Yoav Weiss [00:53:40]:
Yeah. And that is still up for grabs. Like, I have an algorithm in mind. I will like, once I have a PR up, I will definitely, share it with the world as well as with you. And, yeah, I'm happy to get feedback on that. But I think it's, yeah, I think that the model where you can't, yeah, you can't override something that was already defined gives us enough safety for some definition of safety. I mean, theoretically, like, it import maps are essentially scripts that are running in the top level documents context. So they can like, the fact that they can override things is not a security risk because you already like, you've introduced the vampire into your home kinda kinda scenario.
Yoav Weiss [00:54:41]:
But, at the same time, we don't want developers to be surprised, and we don't want, import maps that are coming from different sources to collide. So, yeah, we we want this to be as predictable as possible.
Charles Max Wood [00:54:56]:
There's a question on on Twitter from, Gal, Weissman. I'm sorry if I say your name wrong, my friend.
Dan Shappir [00:55:05]:
Oh, you only have him as a guest, I think.
Charles Max Wood [00:55:08]:
Yeah. But he asked about a compromised script can potentially leverage an iframe to bypass the SRI checks dictated by the top document and thus load a remote third party script that's not allowed to load, I think. The I, I think, is in parentheses. Is that being taken into consideration so this is back on
Yoav Weiss [00:55:32]:
the SRI? So knowing goal, I'm sure he has a scenario in mind that I don't, but I think that that nonverifiable, like, an iframe, we're we're talking like like, does he mention, like, same origin, cross origin? Because No.
Dan Shappir [00:55:58]:
It would have to be same origin. Otherwise, it's Yeah.
Yoav Weiss [00:56:01]:
Because otherwise, it's irrelevant. Yeah. A a same origin iframe, if it's compromised, then, yeah, it would have a different as, like, it would have a different, integrity. Like, the import map doesn't apply to same origin iframes. So it would be able to load that script. At the same time, I wouldn't expect the cache to like, if that script is cached from the same origin iframe, I wouldn't expect it to be loaded at the top level without failing, like, because one has integrity checks and one doesn't. So I I would expect the browser to fail that load at the top level frame. Mhmm.
Dan Shappir [00:56:53]:
I also actually have a question. Like, looking at all the stuff that you're doing, so the SRI, the, the mod the module maps. Also, the work on compression dictionaries. I think we had Patrick Meehan on the show to talk about it. All this stuff is about how to better load JavaScript into the browser so that we don't need bundlers as much. Or that bundlers can be, maybe, less heavy handed than they are? You're you're shaking your head.
Yoav Weiss [00:57:29]:
That's not so I think we need bundlers. I think that there are some issues with, like, physics when it comes to loading a lot of, small modules into the browser. Browsers have overhead, like, per request overhead. That overhead is unlikely to
Dan Shappir [00:57:52]:
go away. Lookup. Just Cookie lookup.
Yoav Weiss [00:57:56]:
Yeah.
Dan Shappir [00:57:57]:
Inter process communication.
Yoav Weiss [00:58:00]:
Yes. Networking stack. Foundations, all that. Like, that takes time and it I think at the time we looked at Chrome and it was around, like, 1 to 2 millisecond per resource which is not awful unless you're loading 5,000 resources. And in that case, you're talking about, like, 10 seconds just to get the thing, like, even if it's on disk, even if it's like 0 RTT, on the network, it still takes a long time to load these assets. If you so that part is unlikely to go away. Go ahead.
AJ O'Neil [00:58:45]:
In those cases, isn't the problem somewhere else? I mean, if your if your application's designed in such a way that you don't have any sort of segmentation and you're loading 5,000 assets? I mean, it just it just kinda seems disproportionate. You know? Like, is this really the problem over here?
Dan Shappir [00:59:07]:
But but, AJ, this is kind of the DHH model. I mean, DHH basically said, I'm and I'm kind of paraphrasing. Like, let's not bundle at all, which means that the structure of your code in your code base is the also the structure in which the code loads. Now if you're one of those people who likes to put every function or every component in their own separate file, then you can end up with and it's a large enough project, you will end up with thousands of resources.
AJ O'Neil [00:59:44]:
Well, maybe you shouldn't do that. Maybe that should be a signal. That's a bad way to code. Stop doing it. So Mhmm.
Dan Shappir [00:59:51]:
Yeah. So if you have a
Yoav Weiss [00:59:54]:
very large team if you have a very large team that's building a very large web app, Let's say, you know, Facebook. They have a lot of people working on different parts of the app, They share code. There are a lot of modules involved. So
AJ O'Neil [01:00:15]:
Well, you but that's more for the benefit of of investors. Like, trying to show continual growth by continually hiring more people, not because people are needed. Like, Twitter 5 70% of their workforce, and Twitter got better.
Yoav Weiss [01:00:31]:
I I I would argue that got better part, but yeah.
AJ O'Neil [01:00:36]:
It it didn't get worse. It's not slower. It's not less reliable.
Charles Max Wood [01:00:41]:
I I think though that the point is is you've got you've got so so let's say that you've got things broken up by components and you've got components in
Yoav Weiss [01:00:52]:
different files like we're talking about. There there are a lot
Charles Max Wood [01:00:53]:
of things that are really convenient as far as, like, developer ergonomics that come from that, and that's why we do it. Right? But at the end of the day, when we deliver it to the browser, the point is is that you you can pull all of that together with a bundler and deliver one deliverable and and reduce a lot of that overhead, which also
Dan Shappir [01:01:14]:
makes sense.
Charles Max Wood [01:01:15]:
And I'm a big fan of having tools that solve the different problems in the right way. And so that that's where I'm I'm sitting here and agreeing with Yoav on this even though I am, you know, I generally agree in a lot of cases with DHH. In this case, it makes a lot of sense to have that bumbler pick up those things and, you know, any of the other tiny bits that kind of have similar responsibilities. And then something like import maps solve some of the other issues where I'm pulling in a bunch of 3rd party stuff and saying, okay. I need this and I need this and I need this and I need this, but I'm not necessarily fiddling with that stuff.
Dan Shappir [01:01:52]:
And I'll put it and I'll also phrase it in a different way. If I'm using a compiled language, like, I don't know, like c or rust or or whatever, There is a separation between how the code is organized and how the bytes are delivered for execution. And unless and and the DHH model, for better and worse, cancels this separation. If I prefer using a lot of small files, it's a choice, a choice that you might not agree with, but it's a legitimate choice for some organizations. It means that I can't use the DHH model or the DHH approach without paying a potentially hefty price for
Yoav Weiss [01:02:39]:
it.
AJ O'Neil [01:02:40]:
I fair. I mean, I I agree with that. I I just I've seen code bases where it's 1 function per file. It seems it's almost like a meme. It's so popular. But it's just it's it's silly. I mean, you can't even understand the context of how a button fits into something because you gotta look at 10 files to figure out. That yeah.
AJ O'Neil [01:03:04]:
That that that like, I'm thinking I'm thinking I don't know. I I was thinking why would something have 5,000 files. I wasn't even thinking of the, like, one function per file because I wouldn't think a serious business would do that. I I
Dan Shappir [01:03:17]:
I don't know if
AJ O'Neil [01:03:18]:
Facebook does that.
Yoav Weiss [01:03:19]:
Yeah. I I don't think it's a one function per file, but I think it does, like, it does result, like, code sharing between teams does result in a lot of small modules. They're not necessarily a single function, but they are a single functionality. And I don't know if this is the, like, the best way to develop or the west or the worst way to develop. Like I said in the beginning, I'm not really a web developer. I pretend to be 1 once in a while, but I'm not doing that in, like, in my day to day. I'm mostly, hanging on browsers, but it is a legitimate way to deliver software on the web. And we should like and I think that, bundlers are essential for that part, both for the browser overhead as well as for compression ratios.
Yoav Weiss [01:04:16]:
Because if you're compressing very small files, you will compress them very poorly compared to large files that compress very well. So, Yeah.
Dan Shappir [01:04:25]:
But then we have the compression dictionaries which mostly solve that.
Yoav Weiss [01:04:30]:
I I don't think they will solve it for very small, like, you would still have to deliver the very small files once and you would still have a very like, I I think compression dictionaries solve a different problem with bundlers. Or at least in my view, like, they could solve it as well to some extent. But, they in my view, with bundlers, one of the issues with a large bundle, one of the issues is you're losing caching granularity. If any single, function a single character inside that bundle changes, you have to download the whole thing back again. And compression dictionaries will help us avoid that at least on the on the network.
Dan Shappir [01:05:20]:
Yeah. So but but my initial point was kind of different. We're doing a lot of things that that impact the the form in a way that certainly affects how bundlers work or should work. How much cooperation are you guys getting from the bundle makers? Because it seems that they should be significantly involved in all this effort.
Yoav Weiss [01:05:49]:
So at the time, I think maybe on the podcast, we were talking about, like, web bundles in, a long while ago. And bundlers were very much, part of the loop on on this. And, Daniel Arenberg, from yeah. I don't like, he may have been at Igalia. He's nowadays at Bloomberg. He was super involved in bringing the bundler community into the room, and, there's a TC 39 tooling meeting, that, we talked about multiple times, at the time about web bundles. And I think that they are like, they were super supportive. I think that once this, what what I'm talking about will reach a more, mature level, I would be very happy to talk to them, and I'm assuming that they will be, similarly supportive because none of the like, essentially, this is all not, like, talking about maybe, like, improving bundlers and improving the output of bundlers to deliver better experiences.
Yoav Weiss [01:07:05]:
So I think it aligns well with everyone's, goals and intentions. In the meantime, a lot of the bundlers are very configurable, and you you can you can go a long way just by mucking around with roll up plug ins. And that is at least the approach that I'm taking now with the various prototypes that I'm working on.
Dan Shappir [01:07:38]:
Which means that you're effectively compatible with ES build, which means that you're effectively compatible with Vite.
Charles Max Wood [01:07:45]:
Yep. I love Vite.
Yoav Weiss [01:07:48]:
Any Same.
Charles Max Wood [01:07:50]:
So sorry. Just came out. Anyway, yeah. Because like I said, you know, I follow along with Rails, DHH. I mean, that's kinda where I live my programming life, but I'm using Vite on my Rails projects. I'm not using import maps.
Dan Shappir [01:08:05]:
Who is this?
Charles Max Wood [01:08:09]:
So, but but I kinda wanna jump back over. So you so far, we've got, compression dictionaries. We've got import maps, doing multiple import maps. We've got SRI. I mean, what what other things are you proposing to fix this stuff?
Yoav Weiss [01:08:25]:
So proposing is a bit of a, like, you know, a a big word. I have ideas that I wanna play around with. One of them is, defining different controls as to when the scripts are loaded versus when they're executed and defining more milestones for the browser to execute deferred semantic scripts other than just the dumb content loaded. So maybe adds more milestones around first render, like, FCP fired now executes these other scripts. Unload fired, execute these other scripts after unload, things along those lines, are things that I'm planning to play around with. I'm
Dan Shappir [01:09:16]:
I guess what you mean what you mean is to, like, declarative support because programmatic support already exists. For example, obviously, for on load, I can do window dot on load equals Sure. And I can specify code to execute on the on load.
Yoav Weiss [01:09:34]:
Yeah. So I would love to play around with a polyfill of what, declarative support for that would look like and see if this these kind of modules, give us any benefits in terms of, execution. And then if they are, then this would be potentially something to, you know, propose as new keywords that will enable us to better load scripts without the, you know, hacking through, like, preloading the assets and then executing the the script manually in different milestones. Yeah. So so this is one thing I'm thinking of playing around with. Another is, with stream execution of bundles. So we talked about the fact that bundles are, you know, if anything changes inside the bundle, then
Charles Max Wood [01:10:39]:
Right.
Yoav Weiss [01:10:40]:
The entire bundle gets, invalid and then the cache and you need to download a new one. But beside that, bundles also, delay execution because you have to download the entire bundle before you can start executing anything. But because we are starting off from ES modules, we could maintain those module boundaries and then recreate them in the browser, in ways that enable the browser to execute the modules separately. And there's a TC 39 proposal, around module declarations. Again, from Daniel Ehrenberg that I mentioned earlier. I am playing around with the user land prototype to see what that gives. It requires a lot of hacks, both on the bundler side as well as on the browser side. But, we'll see where that gets it gets me.
Yoav Weiss [01:11:41]:
I still haven't seen it working yet, but, you know, Yeah. I'm I'm hopeful that this would be a successful, module to start executing earlier.
Dan Shappir [01:11:56]:
An interesting idea that just occurred to me while we were speaking is you were talking about declaratively controlling when scripts execute.
Steve Edwards [01:12:05]:
Yeah.
Dan Shappir [01:12:05]:
It might be worthwhile to also have declared or to try out ways of controlling when resources or scripts start downloading. Like Yeah. I want to download something asynchronously, but I don't want to to for it to start downloading before the LCP because I don't want it to get in the way in the way of the LCP in any shape or form. Yeah. But, by by the way, another and, it's worth mentioning that if people who are listening to us find all this stuff interesting and have their own ideas, they can basically join, you know, participate in the w three c web performance working group and make their thoughts heard.
Yoav Weiss [01:12:53]:
Yeah. For sure. Definitely so some of these things are like, some of these things are hacky projects that haven't gotten anywhere just yet. Some are, going to probably live mostly as, what w g PRs against the HTML spec. But all of this is something that we can and should discuss in the web performance working group. So, yes, if folks are interested, feel free to hit me up. I can, like, yeah, join the calls, and, yeah, make your horses heard.
Charles Max Wood [01:13:33]:
Yeah. It this sounds like a good place to kinda start to wrap up too. It is there a list of these proposals or these ideas somewhere that you have, Yov, or are we kind of it right now?
Yoav Weiss [01:13:46]:
I need to write it down. This is all, like, there's a a list of things I put together for this, for this podcast, but it's, like, not something I can publish. But, yeah, I I need to write down this, as a app. Master plan to improve script loading. And and then, yeah, I I need to publish something on that front.
Charles Max Wood [01:14:17]:
Cool. Well, if people have ideas, how how do they join that working group? I think that might be an interesting place to go.
Yoav Weiss [01:14:24]:
Yeah. Basically, the main path. So if they work for a w three c member, then they can just join, and ask their AC representative to to join the working group and yeah. And that's it. Otherwise, they can, ping me or or the yeah. Or Nick Jansma, who's the other chair at Akamai. And, yeah, we can, you know, talk through the the issue with them. Yeah.
Yoav Weiss [01:15:11]:
I'm I'm pasting the a link to the web performance, to the working groups, page where you can you know, if you're, a WCC member, you can join through there. And, otherwise, yeah, just, email me, or Nick Jansma, and we can set you up. They're like, we're available over email, over the there's the web performance, Slack group that a lot of people are on. And, yeah, otherwise, you know, on the Internets.
Charles Max Wood [01:15:48]:
Good deal. Alright. Well, I'm gonna go ahead and slide us into our picks. But this this has been really fascinating. But, yeah, let's do our picks. AJ, do you wanna start us off with picks?
AJ O'Neil [01:16:04]:
Let's see. What have I got? My wife and I recently watched the Jason jet the well, we start we've started watching the Jason Bourne trilogy, but we started with the best one, which is Bourne Supremacy. And she liked that, so we're probably gonna watch the others as well. So I will I will pick the the Bourne trilogy because it's kind of a kind of a cool movie.
Dan Shappir [01:16:36]:
And She has sufficient context?
AJ O'Neil [01:16:41]:
Well, I when the movie started, I told her, okay. The the thing is this guy is basically James Bond, except he wakes up one day with amnesia and is trying to figure out what he's doing. And this is the 2nd movie, and we're starting with this one because it's it's better. And if we started with the first one and you didn't like it, you might not wanna watch the rest of them, but the other yeah. You know? They're they're all the kind of the same movie. It's kinda like Terminator and Terminator 2. It's the same movie. It's just way better production.
Dan Shappir [01:17:11]:
By the way by the way, I'm one of the few people I imagine who've actually read the Ludlam book before they even watched the first movie.
AJ O'Neil [01:17:20]:
So there's there's, like, 10 books. Aren't there?
Dan Shappir [01:17:24]:
To be honest, I don't remember. The problem with Ludlam is that all his books kind of are the same book.
AJ O'Neil [01:17:32]:
Well, the movies are the same movie, so that tracks. But, I mean, same thing with James Bond. Right?
Dan Shappir [01:17:39]:
Yeah. I guess.
AJ O'Neil [01:17:40]:
Yeah. So there's that. I'm still motorcycling. Still absolutely love it. And,
Dan Shappir [01:17:48]:
I'm trying
AJ O'Neil [01:17:48]:
to think if there's there's anything else worth worth picking. I do I do have to send a pick from earlier. I at one point, I'd picked silicon power drives. I've loved silicon power for micro SD cards. They have been amazing. However, I I had ordered about 16 of the silicon power SSDs. Actually, I don't think it was that many. Yeah.
AJ O'Neil [01:18:13]:
Well, it was about that many. 4 of them have failed over the course of the last year and a half. And this is in a server environment. And they told me you know, I got a business account with them. They told me they would, you know, warranty them for the server. They'll warranty them, but they fail. And we've also got 16 crucial MX 5 100, and not a single one of them has had a hiccup. So I guess my my pick would be crucial MX 5 100 if you're if you're putting together a server and you want the best value drives, I have to switch my pick on that to being crucial.
AJ O'Neil [01:18:46]:
Silicon power is, like, half the price, but you don't wanna be going to your data center replacing drives except for when you have to. So I'll, I'll pick those as my picks.
Charles Max Wood [01:18:58]:
Steve, what are your picks?
Steve Edwards [01:19:02]:
Well, before we get to the high point of every episode, came across an interesting, blog post or article, whatever you wanna call it, on Hacker News about OpenAI. And, you know, we've been using AI more and more in my work, but in a, you know, in a scope limited sort of capacity based on our own data. But the title is how does OpenAI survive? And it's a pretty detailed walk through the business model and what OpenAI would need, in terms of huge growth of money and just a bunch of unprecedented things to happen in order of them to survive over the next couple years. So, if you want something as a cure for insomnia, it's pretty good, I think, but it's also pretty interesting if you're into, reading about OpenAI. Says they seem to be on a lot of tips of everybody's tongues these days.
Dan Shappir [01:20:00]:
We kind of spoke about this subject when Steve Sewell was on the show. I think, I I kind of have tongue in cheek said that, like, the only company actually making money off of the AI revolution is NVIDIA.
Steve Edwards [01:20:15]:
Right. Because of the chips. Right? Yep.
AJ O'Neil [01:20:17]:
Well, I'm looking forward to where we could just download the model on you know, when when when OpenAI goes out of business and they and they open source the model, I'm happy to download that, you know, 40 gigabytes on my computer and run it off the power of my MacBook.
Dan Shappir [01:20:32]:
I think there's the Ollama model Ollama model that you can from Facebook, I think, where which you can already download.
AJ O'Neil [01:20:39]:
It's that's true. And it's it's better in some ways than chat GPT 3, but it's not better than chat GPT 4
Charles Max Wood [01:20:47]:
o. Yeah. The way the way that I understand it, and I'm still learning about this stuff. But, yeah, it it's good for a baseline if you're gonna train your own stuff on top of it, right, to give it better context. But, yeah, the GPT 4 models are much more comprehensive and give better answers.
AJ O'Neil [01:21:16]:
I mean, they do have access to every book that's ever been made in every journal and because they get asked questions like, so are you using copyrighted content that's, you know, like, paid content that you're just putting into the model and making available to everyone, and you're gonna face major lawsuits? And they're like, well, you know, it's hard to say because, I I don't know exactly where all the data comes from, but it's definitely data that's available online. So, you know, you your your is, like, basically Wikipedia, Stack Overflow. You know, it's it's the the big sites, but GPT 4 o is all of the content that humanity has ever created. There's not gonna be a GPT 5 because there's no more data left.
Steve Edwards [01:22:07]:
Alright. And then moving on to the highlighted Or
Dan Shappir [01:22:12]:
Unless they just to say, unless they start putting in pictures of cats because there are always new pictures of cats.
Steve Edwards [01:22:19]:
Always. Always. Some of those
Charles Max Wood [01:22:21]:
are gonna be AI generated too.
AJ O'Neil [01:22:23]:
That's why I'm paying the $20 a month.
Charles Max Wood [01:22:24]:
Except shit.
AJ O'Neil [01:22:25]:
Best cats. The best cats.
Dan Shappir [01:22:27]:
The cats with 6 fingers.
Yoav Weiss [01:22:31]:
So,
Steve Edwards [01:22:32]:
I am suing the doctor who delivered my baby. My son now has to grow up without a liver. Delivered. Anyway, sorry. Sometimes you gotta explain them. I was attacked by a flock of sheep yesterday, but luckily, I was only grazed. That one's sort of bad.
AJ O'Neil [01:22:56]:
We can see that there. We can see that.
Steve Edwards [01:22:59]:
Yeah. Right there. Right there. Grazed. And then, I love this one. I got I thought for sure I'd get shot down on this next one. People loved it. I was, I was gassing up my Honda Accord the other day at a gas station, and, a snarky Tesla owner asked me how much I spend on gas.
Steve Edwards [01:23:18]:
I said, about 5 minutes.
AJ O'Neil [01:23:23]:
That was that was well done. And I I I need to make a remark on Tesla, by the way. They are the number 2 per capita as in per Tesla owner versus per other car owner. They are number 2 and most likely to get into a wreck, and they are the number 1 motorcyclist killers. So if you own a Tesla, wake up, get your hands on the steering wheel, watch what's in front of you. Don't run over people. K. Thanks.
Dan Shappir [01:23:51]:
By the way, about the delivered, it kind of reminded me there was the scene from Monty Python, the meaning of life movie, where they knock on his door and they said, you're you're a registered organ donor. I said, yes. We've come to collect.
Steve Edwards [01:24:10]:
Oh, boy. Yes. That my favorite scene from that particular movie is the guy in the restaurant. Oh. Just a wafers in mid 3rd. That's all.
Dan Shappir [01:24:19]:
No. I think my best one and my favorite one is that that every sperm is sacred, song and dance routine.
Steve Edwards [01:24:28]:
Anyway, those are my picks.
Charles Max Wood [01:24:30]:
Dan, why don't you just keep us going? What are your picks?
Dan Shappir [01:24:34]:
Not exactly a pick. The 20 twenties have sucked so far, and, this year has not been different in any way, shape, or form. And, week and a half ago, our lovely and beloved my lovely and beloved mother-in-law passed away. So it's been a really tough week for us. So I would like to dedicate my part of this show to her memory. I miss her dearly. We all do. And that's all I have.
Charles Max Wood [01:25:13]:
Yeah. Yeah. Losing people's hard.
Dan Shappir [01:25:15]:
Yep.
Charles Max Wood [01:25:18]:
Alright. I'm gonna jump in with some picks. I usually do a board game, and so I'm gonna do a board game. We played this yesterday. What we've been doing with my family is, we we've been picking a game that we haven't played in a while out of our collection, and then, you know, we play it and we decide if we wanna keep it or not. And the one that we picked up was Imagine If, and this is more of a party game, which I have to say generally are not my favorite games. The I mean, this one's fun. I just sometimes when when I'm in the mood for a board game, I usually want something that's gonna make me kinda think and strategize and stuff.
Charles Max Wood [01:26:02]:
The, you know, the party games aren't that way, but this one's a fun one, especially if you're all part of the same group that know the same set of people. You just you write down names around the outside of the board. There's a marker. You roll the die. You move it that many spaces. You pull a card. You read the card, and let's imagine if, Betty were a type of shoe, which one would she be? Right? And then it's like a stiletto, a hiking boot, you know, a baby booty. Right? And so then you, everybody has 1 through not cards numbered 1 through 6 in their hand.
Charles Max Wood [01:26:39]:
They put 1 face down. You flip them over. If you're in the majority, then or if you're in the group that has the most, I guess, that doesn't mean you're in the majority. Then you move up 1. If you're the person who read the card, you move up 2, and then you do it again. There's a space for challenge, and that one, you pick another person that you think you're gonna match with, you roll the die again, you move the marker, You read the card. The 2 of you put down your numbers, and if your numbers match, you move 4. And if you don't, then you move back 2.
Charles Max Wood [01:27:11]:
And, my 8 year old sabotaged me by challenging me and then picking a number that she knew I wouldn't pick so that I wouldn't win. That's the way that game went last night. But overall, it's fun game. Board game, Geek, weights it at 1 point 22, which means it's super simple. I mean, I basically explained all the rules to you in less than a minute. But it is kind of a fun party game. And so, you know, we had all of our family members and then, you know, grandpa who wasn't there. So, anyway, I'll go ahead and link, to the, BoardGameGeek, listing in the the comments only show up on Twitch, YouTube, and Facebook.
Charles Max Wood [01:27:56]:
So if you're watching on Twitter, which is where most people are watching, you just have to go look it up. It's imagine if, drop the e at the end of imagine, put I f f at the end, you'll find it. And then other picks. So my my oldest son is 18, and his favorite movie is A Quiet Place. And so we went and saw A Quiet Place day 1. I mean, no spoilers. He said that some of the people are in the that are in A Quiet Place day 1 are in A Quiet Place part 2, which I haven't seen, but they're pretty minor characters. So I guess it's kind of an origin story for that group of people that you'll see in the A Quiet Place part 2, but it, it was good.
Charles Max Wood [01:28:45]:
It, you know, it's not it's not the best movie I've ever seen, but it wasn't something I regretted going to see in the theater. So I'm gonna pick that. And
AJ O'Neil [01:28:56]:
There's there's a Quiet Place day 1, then there's a Quiet Place, and then there's, like, still a Quiet Place.
Charles Max Wood [01:29:03]:
So A Quiet Place is the first movie they made, and then A Quiet Place part 2 apparent is the second movie, and then this one's a prequel that they made.
Dan Shappir [01:29:13]:
It's like the Star Wars prequels that came out.
Charles Max Wood [01:29:16]:
Yeah.
Dan Shappir [01:29:17]:
I Yeah.
AJ O'Neil [01:29:17]:
That's that doesn't sound like good.
Charles Max Wood [01:29:20]:
Yeah. Well, yeah. Anyway, so I I enjoyed those. So my I'm gonna pick that and then
Yoav Weiss [01:29:30]:
K.
AJ O'Neil [01:29:31]:
Okay. Yeah. I I was I was just confused about it. It actually is called part 2 because I did see those. Yes.
Yoav Weiss [01:29:37]:
But I
AJ O'Neil [01:29:37]:
didn't remember what the name of the segment. It literally is called part 2. Got it.
Charles Max Wood [01:29:40]:
Yep. Yep. So yeah. So I'm enjoying those. And then, one other TV show. So I'm I'm picking nothing technical, I guess, is I was browsing through Netflix, and I saw that they did a live action Avatar The Last Airbender. And, so I watched a few episodes of that with my same my 18 year old son. And we enjoyed those.
Charles Max Wood [01:30:04]:
So I'm gonna pick those. And that's that's it. That's it for my picks. Yoav, do you have some picks for us?
Yoav Weiss [01:30:12]:
Sure. So the first one, I guess, is, I mean, hiking or I don't know if I have more than that. But, like, basically, it took me, way too long to realize that I the So it's the like, hiking is the best. Almost everyone can do that. And even if you suck at it at first, you get better. And yeah. It's great for your health. It's great for your mind.
Yoav Weiss [01:30:51]:
And, yeah, everyone should hike more.
Dan Shappir [01:30:54]:
That's I can confirm and attest that you do live in a beautiful area, but given that you live in Southern France, that's not really surprising.
Yoav Weiss [01:31:03]:
Yeah. Yeah. But, at the same time, I think everyone I I don't know. Not everyone, but if you live next to a mountain of some sort, you should go up it once in a while. That's that's what I see.
Charles Max Wood [01:31:19]:
Yeah. It's it's interesting you bring that up because, AJ and I here, we live pretty close to the mountains here too, and, boy, there are some amazing hikes to go on. Yeah. Definitely, if you have the opportunity, get out and see it. Or get out and see the world.
Dan Shappir [01:31:39]:
Can you get that? You even go
AJ O'Neil [01:31:40]:
to Denver. Those are the best mountains, even better than Utah mountains.
Dan Shappir [01:31:47]:
You are. But you're the one
Charles Max Wood [01:31:48]:
on the plains, you're you wanna kinda get up toward the but, yeah, the mountains down
AJ O'Neil [01:31:52]:
there. I meant Colorado Springs. I meant I meant to say Colorado. I didn't mean to say Denver. I meant to say Colorado. But we were we took a weekend trip to to Colorado Springs area to see the Royal Gorge Bridge and the Garden of the Gods. And
Steve Edwards [01:32:06]:
Garden of the Gods is awesome.
Charles Max Wood [01:32:07]:
Is gorgeous.
Yoav Weiss [01:32:08]:
Yeah.
Steve Edwards [01:32:08]:
I went to college just a couple miles from there, so that was a popular place to go hang out, ride bikes out there and stuff.
Yoav Weiss [01:32:14]:
Yeah. Yeah.
AJ O'Neil [01:32:14]:
And we and we went white water rafting?
Steve Edwards [01:32:17]:
Yeah. I did that Friday too. Good times. Cool.
Yoav Weiss [01:32:21]:
Yeah. There's some gorgeous
Charles Max Wood [01:32:22]:
places up in Boulder too.
Yoav Weiss [01:32:24]:
Yeah. Never been to Utah or Colorado, so I should probably do that at some point.
Charles Max Wood [01:32:29]:
Come on out.
Steve Edwards [01:32:29]:
Well, Utah's awesome. My daughter and I did a sort of a loop around, Utah 2, 3 years ago. We met up with AJ and his family, when we were down there. And, you know, what did the loop come down through Canyon Lab through Moab, Canyonlands, and, we'll try across from Canyonlands. Can't even remember. And then down to Lake Powell and come up over to Bryce Canyon. Oh, Arches. Yeah.
Steve Edwards [01:32:57]:
Arches and Canyonlands and Bryce Canyon and Lake Powell, and, it's awesome. It's really pretty. Didn't hit Zion, which we would've hit Zion, but it's it's an amazing trip.
Dan Shappir [01:33:07]:
The only the only problem is kind of
Steve Edwards [01:33:09]:
on the
Charles Max Wood [01:33:09]:
other side of the state.
Dan Shappir [01:33:10]:
Mhmm. Yeah. The only problem is that the US is just so big. So getting from one place to the other requires so much driving.
AJ O'Neil [01:33:19]:
Isn't it around the same size as Europe though?
Dan Shappir [01:33:22]:
What? Oh, UK?
Yoav Weiss [01:33:25]:
Yeah. Utah is the same size as Europe. Not I'm not No. I'm not here.
Charles Max Wood [01:33:28]:
It's it's No. It's the same size as some of the European countries.
Yoav Weiss [01:33:34]:
Yeah. I I mean, it's it's I think it's big. Like yeah. It's a lot of a lot of driving involved.
Dan Shappir [01:33:41]:
I would concur that driving around all of Europe would also require a lot of driving. The thing about Europe is that it's, especially if if if you it's most it's less about the scenery in most cases. It's more about, like, you know, art and and architecture and stuff like that. And then things tend to be closer together.
Charles Max Wood [01:34:06]:
Mhmm.
Dan Shappir [01:34:07]:
Also, there are bet there are better railways.
AJ O'Neil [01:34:10]:
I stand correctly. The United States is twice the size of Europe.
Steve Edwards [01:34:15]:
Oh, wow.
AJ O'Neil [01:34:16]:
Or the European Union,
Dan Shappir [01:34:18]:
which is not all European. Like, half of Europe is Russia. So
Steve Edwards [01:34:23]:
Yeah. Yeah. It's interesting.
Yoav Weiss [01:34:26]:
Yeah. But when when I
Charles Max Wood [01:34:27]:
lived in Italy, Italy is basically if you took Arizona or Utah and you stretched it out to the length of California. Right? So so, anyway, you you get different geographic deals when you go to different countries. But, yeah, I mean, you can roughly say, you know, land size, you know, some of the western states are as big as some of the bigger European countries. So, anyway, I'm gonna go and wrap this up. Thanks for coming, Yol. This was really fascinating. And, hopefully, yeah, we get some more ideas coming your way, and we can see some of these things, you know, come come to fruition and make the Internet better.
Yoav Weiss [01:35:10]:
Thank you. Thanks for having me. It's been fun.
Dan Shappir [01:35:12]:
Yeah. Yeah. Whatever you can do to actually make the web platform and the web itself better is a literal win for
Charles Max Wood [01:35:21]:
everybody. Alright. Well, till next time, folks. Hack's app.
Hey, folks. Welcome back to another episode of JavaScript Jabber. This week on our panel, we have Steve Edwards.
Steve Edwards [00:00:11]:
Yo, yo, yo, coming at you live from Portland. I'm filling in for AJ since he's not here right now.
Charles Max Wood [00:00:18]:
Right. We also have Dan Shapir.
Dan Shappir [00:00:20]:
Hey. Sitting in the air conditioning room in hot and sunny Tel Aviv.
Charles Max Wood [00:00:26]:
Yeah. I'm Charles Max Wood from Top End Devs, and we have a special guest this week, and that's Yoav, Weiss. Do you wanna introduce yourself? Let people know if we've had you on before, so I think some people know who you are, and then
Yoav Weiss [00:00:39]:
there may be a few people.
Dan Shappir [00:00:40]:
They don't. They should.
Charles Max Wood [00:00:41]:
Yeah. Sure.
Yoav Weiss [00:00:43]:
I I can introduce myself. So, hey, I'm Yoav. I've been working on web performance for way too long, trying to solve it and so far, not being super successful. I've been, working on browsers since 2012, and initially on my own, then at Akamai, working on both, browsers and server features, then at Google for a few years, and nowadays I'm at Shopify still working on the web platform. Amongst other things, I co chair the web performance working group, and I'm one of the blank API owners, which is basically, the folks that sign off on features getting released in Chromium.
Dan Shappir [00:01:46]:
The working group is it's worth mentioning is part of the w three c.
Yoav Weiss [00:01:50]:
Yes. Yeah. Yeah. The w three c work performance working group. Yeah.
Steve Edwards [00:01:54]:
I would like to point out that it's from a visual standpoint, it's easy to tell how smart he is by his haircut. Just saying.
Dan Shappir [00:02:00]:
So Yeah. He's one of these guys that shaves his head even though he has hair. Yeah.
Yoav Weiss [00:02:08]:
I see. Yeah. I
Steve Edwards [00:02:09]:
I can say it.
Yoav Weiss [00:02:10]:
Accordingly. Yeah. I wouldn't define it as has hair. But yeah.
Steve Edwards [00:02:15]:
Well, got made only so many perfect heads and the rest he covered with hair. So
Charles Max Wood [00:02:19]:
That's right.
Dan Shappir [00:02:20]:
Like like to say that, I'm, also, I'm an invited expert on the that same working group. The guy who invited me over is. So I'm very thankful for that.
Yoav Weiss [00:02:33]:
I'm I'm thankful for your contribution. So
Dan Shappir [00:02:36]:
Yeah. Doing fighting the good fight, trying to make the web faster for everybody's sake.
Charles Max Wood [00:02:43]:
So, Yoav, we got this, document from you about JavaScript floating, and it it it's interesting because it starts off with you change jobs. So Yeah. You wanna kinda give us some context on that and then, we can jump in and talk about JavaScript loading?
Yoav Weiss [00:03:00]:
Yeah. Sure. So yeah. So, basically, I yeah. Like I said, worked on Chrome at Google for, 5 years, up until a few months back. And yeah. And earlier this year, I changed employers, but the good thing about open source is that I get to do a lot of the same things, with a different head on. Basically, I've been working on making the web faster by default.
Yoav Weiss [00:03:36]:
I've been doing that, before, joining Google, and I get to do that afterwards. So I continue to work on, on Chromium. I now also get to work on WebKit, which is an a refreshing change. And the only thing with, I guess, with the change from working for a browser vendor to working more, like, closer to the industry, it kinda helps to keep me aligned with what developers actually need. Because, working for a browser vendor is great, but it's also it makes it hard to keep up with what actual developers are doing because browser developers are not web developers, at least not really. Yeah. And working as part of the, you know, quote, unquote industry makes it easier, to make sure that my work is actually aligned with what people need. So that part is something I'm very very happy about.
Yoav Weiss [00:04:51]:
Yeah. Other than that, there aren't a lot of commerce voices amongst, people who work on browsers. So I'm very happy to bring in that perspective to those discussions.
Dan Shappir [00:05:04]:
That's especially interesting given that probably the organizations or or the the web, that's websites, web apps that have potentially the greatest need for web performance or see the greatest impact from from improving web performance are commerce related websites in many cases. Yeah. Like, there's always, those, you know, research papers showing, like, Amazon increased their revenue by a $1,000,000,000,000 because they sped up loading time by 5 milliseconds or something along these lines.
Charles Max Wood [00:05:42]:
Right. Yeah.
Yoav Weiss [00:05:42]:
I I don't know about these exact numbers, but, but, yeah, basically, performance is very important. There are a lot of public case studies about the relationship between, web performance and conversion rates. And I'm biased, but it seems to me that it's, like, crucial to have that kind of influence on, you know, on web standards and and and where the web platform is going.
Dan Shappir [00:06:12]:
Yeah. By the way, the the Google driven website web.dev, which is an excellent website, has case study section, which actually has real numbers, not numbers invented by me, that describe how companies did, in fact, significantly increase their conversion, their income, their whatever, thanks to improving performance. And like you said, it's not it's not really surprising. You know, it's we have we're in an age of, you know, little patience and a lot of distractions. And if your website takes too long to load, then people will go elsewhere.
Yoav Weiss [00:06:55]:
Yeah. If you if you remove friction, good things happen. That's a general Yep. Yeah.
Dan Shappir [00:07:02]:
It reminds me of when I told someone that, the, the, the pipeline or the the funnel at the previous company that I worked at is implemented in Angular. Their response was, don't let Angular get between your customers and potential customers and the payments. Something along these lines. But but yeah. It's it is important to reduce friction as much as possible, and improving performance is certainly a good way to do that.
Charles Max Wood [00:07:40]:
So we're we're talking about, JavaScript loading today. So so how does that get into this friction or frictionless performance of setup?
Yoav Weiss [00:07:53]:
So I've been unhappy with the way that JavaScript is being loaded on the web for a long while, but haven't been able to move that, too much just yet. But it's, essentially, I think that in in many ways, when we're looking at, web performance and loading performance, there isn't really a good way to load JavaScript. And the main advice that web performance folks can tell people or have been telling people, is just to load less JavaScript, which is correct, but not necessarily useful in today's, web development environment. If you can load your site, with less JavaScript, you should. And but at the same time, there are a lot of JavaScript based apps. But, like, even for those, loading performance matters. Loading performance matters because your users, interact with your website. They they will right click and open a new tab.
Yoav Weiss [00:09:15]:
They will reload. Your browser will unload your app in the background, in order to save memory. And in those cases, you're, you're effectively hitting reload even if you, even if your, if your site is, you know, there all day, there are a lot of interactions where loading performance matters. So, essentially, there are no good ways today to load scripts. And, yeah, Ben and I as part of, we started enumerating the different number of ways of, that you can load scripts. But it's essentially if if you go back to the basics, we have blocking scripts that are, you know, they are not a not a good pattern because they are blocking the parser from, processing the rest of the document. There are async scripts who are not necessarily a good pattern because they are racy and will potentially get in the way of more important things if they happen to load earlier. And we have deferred scripts who are real like, it's it's a relatively, well defined model, and it doesn't block the rent the the parser.
Yoav Weiss [00:10:41]:
But at the same time, they are often like, they're they're always loading at a single milestone, a single point in time in the page life cycle, and that may or may not be sufficient. So
Dan Shappir [00:10:56]:
I I think, though, it is important to mention that even though so talking about blocking scripts, which are the most obvious way, in in in kind of the oldest way, I guess, because, really, if you don't say anything else, then a script is blocking by by default. Like, the this is the way the web was originally built. It's it's problematic. Like you said, it's usually bad, but it's needed because sometimes you need to do some things before rendering can proceed. So it's it's when we say blocking, what it really means is render blocking. Means that when the browser hits that point, that script tag, it has to stop rendering until that script finishes. I know that some browsers do hacks around that. But really, at the logical level, that's what it means.
Yoav Weiss [00:11:55]:
Right? Yeah. But there so there is a better alternative to that, which is, blocking equals render, which gives you, essentially, it gives your async script or deferred script the ability to block rendering, but not log the parser. So the browser can continue to do work, but the user doesn't see things flashing around beak before that's script.
Dan Shappir [00:12:26]:
Oh, yeah. I I forgot that one, and maybe I should have even added that to the list. In in this in this context, it's, you know, the the web is something of of, you know, like an archaeological site. You know? And it's it's layers upon layers of history. And and the thing about the web is that once something has been implemented, it can almost never be taken away and must be supported forever and ever. So in the very olden days, I think it was Brendan Eich that introduced the concept of document rights, which enabled JavaScript to kind of inject content into the HTML stream, into the document downloading stream. And therefore, because of that, scripts had to be blocking because you couldn't proceed with processing the HTML just in case something happened to be injected into it. Now, nobody uses document for well, I can't say nobody.
Dan Shappir [00:13:31]:
But hardly anybody uses document right anymore. It's like a fraction of a fraction of a percent of websites, I would say. But but it still needs to be there. You're smiling, Yoft. So I'm guessing more websites you're saying that I would like to work.
Yoav Weiss [00:13:50]:
I'm sure there are stats, and we can let me see if I
Dan Shappir [00:13:54]:
can like, like, SSL VPNs or something. Use it for evil thing, nefarious things, or maybe all sorts of firewalls or whatnot. Use it for for crazy stuff. But but it's not something that that's put a difficulty. 99.99% of web developers don't use it. And but it still needs to be supported, so it's still there. So scripts are not just render blocking, they're download and parsing blocking as it were. And like you have said, if you put loading equals render, then you're telling it basically telling the browser, look.
Dan Shappir [00:14:35]:
You need to pause the rendering because maybe I'm doing logic around dark mode, and I don't want content flashing or something. So you need to pause the rendering, but I'm not using document right. I promise. So you can actually continue parsing stuff because I won't be modifying the the download the document stream. So yeah. I I I to be honest, like I said, I actually forgot about about that that option. Another, by the way, interesting option is, again, if you have a blocking script, whether it's in the head or the bottom of the body, that also kind of modifies the behavior as I recall. Like, browser is not the priority.
Yoav Weiss [00:15:24]:
It it modifies the priority. It's not like the the script will block parsing whenever it's discovered. But if it's discovered at the bottom of the document that, like, parser blocking doesn't have a huge effect because there's nothing more than that actual script to parse. So it's blocking nothing behind it. So if you're looking browsers
Dan Shappir [00:15:52]:
yeah. We talked about it with Robin Marks. Some browsers in that scenario would actually reduce the priority of the script download. Some don't, by the
Yoav Weiss [00:16:03]:
way. Yes. Yeah. The whole, yeah. So there are generally for blocking scripts. Browsers all browsers nowadays have a mechanism or all all commercial browsers, like, if I'm I I'm not sure about, for example, Lady Bird, but, all big browsers, have a mechanism where they continue to parse the document in order to speculatively fetch resources when they're when they encounter a blocking script. And, yes, whenever like, a blocking script at the head would have a higher priority in some browsers than a blocking script at the bottom. But all the, like, the priorities as well as this speculative, preloading of assets of resources, none of that is specified.
Yoav Weiss [00:16:59]:
So every browser can pretty much do their thing and web developers shouldn't really rely on it. Yes. So basically, we have multiple, multiple ways to load scripts. I am unhappy with all of them. And then, we have essentially for, like, the future of script loading for the last, I don't know how many years, have been ES modules.
Dan Shappir [00:17:33]:
And one more thing before we get to ES modules. Sure. I think that another key aspect that confuses people when they think about script loading, but really any asset loading in the browser, is that the difference between important and urgent isn't always obvious. That some stuff is important because the page can't work without it, but it might not be urgent as in that certain things need to be downloaded sooner. So for example, in this day and age of, SSR and SSG where we present stuff visually before it actually becomes interactive. Like, there's a difference in time between when a page is seen and when a page becomes interactive, you might say that visibility is more urgent than interactivity as long as the difference between the two is sufficiently small.
Yoav Weiss [00:18:40]:
Like, I'm not sure I personally
Dan Shappir [00:18:41]:
it's a painful it's a painful thing because because sufficiently small is is a problematic definition in and of itself. And if it's even slightly too big, it becomes a real problem. Like, the page literally doesn't properly respond to user interactions, which is worse than slow. It's literally broken. But, but yeah. I I still think that this distinction between what is urgent and what is important. Like, what is important is stuff that the page can't properly work without. If a certain image, for example, is not downloaded, that's not necessarily important if it's if it's doesn't get in the way of the pages operation.
Dan Shappir [00:19:24]:
So you get a broken icon. Right? You know, it still work. On the other hand, let's say if the CSS doesn't download, then there's a good chance that the page becomes totally illegible. So that's kind of really important. And it's also urgent because you need that CSS really quickly. And JavaScript can be somewhere in the middle between these 2.
Yoav Weiss [00:19:46]:
Yeah. Yeah. I guess fonts also is, you know, one of those assets which is like, there's no good way to load them because they are potentially important for branding and user experience and whatnot. But if they don't download the new fault system fonts, that's also, like, it's still a usable site. So, yeah. There's also so it's an interesting distinction between important and urgent. I think that there's also no current way like, another interesting distinction that there's no way to express today is, the difference between when when you want the script to load and when you want the script to execute. And at least for async scripts, those 2 happen at the same time.
Yoav Weiss [00:20:45]:
As soon as the script is loaded and the main thread is clear, that script gets executed, and that may or may not be the right choice depending on when you need that script. So there are scripts that you want them to, like, load earlier, but still wants to be able to control their execution either manually, and then you can use preload for that, but that is hacky and cumbersome. Or otherwise, the only currently official milestone you have in the page, life cycle is the DOM content loaded. When the whole HTML finished parsing, that's when deferred scripts trigger. And, yeah, there's no way today to express different preferences there.
Dan Shappir [00:21:39]:
And again, there is even a a middle step in between the two that's kind of less important, but still exists, that people might want to be aware of, which is the parsing. So you're really you're really downloading the script. You're parsing the script, and then you're executing the parts the parsed script. Now per my recollection, some browsers, not all browsers, can parse the script as it downloads. Some of them can even do it off of off of the main thread. Some don't. Some bundlers get in the way of this by putting all the script inside strings and then converting those strings into scripts, which I never really understood why bundlers do that, but some of them do.
Yoav Weiss [00:22:34]:
I did not know that. That's that's interesting, and that seems yeah. I
Dan Shappir [00:22:42]:
think Webpack does that in in certain situations at least.
AJ O'Neil [00:22:47]:
I wonder if it's dev mode.
Dan Shappir [00:22:50]:
I don't think so. I think that if you I I don't I don't think it's dev mode, is right.
Yoav Weiss [00:22:55]:
Okay. That's that's interesting, and that can also that can get in the way of, yeah, of parsing, like, a parallel parsing in the background. It can also maybe get in the way of code caching. Although, I guess, if those strings don't change, then eventually yeah. I'm yeah. Not sure. But it's it it seems less than ideal.
Dan Shappir [00:23:23]:
So you were saying that we can separate so the the downloading and parsing can happen together, not even so we can actually download without parsing by prefetching. We can download and and parse together by but not execute by preloading, Or we can just load the script which does all 3 or maybe avoid some of them if you've already prefetched or preloaded.
Yoav Weiss [00:23:55]:
Yes. But the problem with the script loading, like, if the the most straightforward mechanism for just loading the script doesn't give you any control regarding to when that script is executed at least when you're going with async scripts. And, like, with deferred as well, it gives you a certain point in time in which your script will execute. And
Dan Shappir [00:24:19]:
Yeah. So so talking about the sync scripts for a second. So sync script scripts become a sync either because you explicitly put the sync attribute on the script tag, Or if you've added them dynamically into the HTML, then they are synced by default as I recall.
Yoav Weiss [00:24:42]:
Yeah.
Dan Shappir [00:24:43]:
Or if there are are modules by default to sync or deferred. I always forget
Yoav Weiss [00:24:50]:
deferred. Modules are deferred by default.
Dan Shappir [00:24:52]:
Okay. So those are the 2 scenarios in which it's a sync. A sync as its name implies downloads without blocking. It downloads the background. But the problem with it, as you said, is that it's executed as soon as it's it's finished downloading and the browser can execute it, it will execute it.
Yoav Weiss [00:25:15]:
Yes.
Dan Shappir [00:25:15]:
Which means that there's no guarantee about order of things and what else the browser may or may not have done.
Yoav Weiss [00:25:22]:
Yeah. And beyond the lack of guarantees regarding ordering, I've seen a lot of cases in the past where, you know, people have some scripts are critical for, for rendering. They are like, they contain they render the main content and other scripts aren't. People load all of them with async scripts. And then if you naively preload those scripts, basically, if if if you make async scripts go faster, some pages will get slower, some pages will get will get faster, and some will see a mix of book like, essentially both, where, some parts of the, like, some parts of the critical experience get faster, but then they there are other scripts that should have run later that get in the way. Because execute execution times essentially, grabs a hold of the of the main thread for things that aren't critical. Yeah.
Dan Shappir [00:26:29]:
So, again, you're you're saying something is not urgent. I'll make it a sync. But what you're not taking into account is that the browser will start downloading it immediately even if at the lower priority. And if it happens to be a relatively quick download, then it might get executed faster than you expect ahead of more more urgent stuff. And if its execution is lengthy for any reason whatsoever, because it loops up to a trillion or whatever, then you're basically stuck. So you either need to write if it's your own script, you need to write it in a way that ensures that it doesn't execute really too soon. Or, alternatively, you might want to load it at a later time, not just using a sync.
Yoav Weiss [00:27:20]:
Yeah. And in the past, I've seen optimizations that preloaded things and made, like, made everything slower because those async scripts ran too too early.
Dan Shappir [00:27:34]:
And, again, we kind of spoke about it with Robin as well. The reason that people preload scripts, you might ask if I'm loading scripts up front, why would I preload the scripts? You know, seems like a useless operation. But the thing is that preloading actually impacted the the download priority or could impact the download priority, which could make the scripts that are making air quotes download faster. These days, you've got more let's call it the natural way of doing it, which is the fetch priority, attribute.
Yoav Weiss [00:28:11]:
Yeah. But you also have, you know, there are systems out there who detect scripts as, like, get, for example, script URLs from run data and then automatically preload those in order to excel. Like, let's get all the scripts that loaded before FCP or or LCP, preload them, and then make things faster. And some of those scripts are in HTML and could have just had the fetch priority, but some of them are late discovered and, are dynamically injected through other scripts, and that part is not like it's less trivial. Like, in those cases, preload helps more. Also, we used to have a thing called, server push, which even, like, loaded these scripts even earlier. And those kind of optimizations often ended up with, basically Mixed results. Yeah.
Yoav Weiss [00:29:18]:
Bimodal results. Some pages get way faster. Some pages get way slower. And it's very pages
Dan Shappir [00:29:25]:
get faster in some scenarios and slower in other scenarios. Yeah. Yeah. Like, depending on network conditions and stuff like that.
Yoav Weiss [00:29:32]:
Yeah.
Dan Shappir [00:29:32]:
Yeah. So we live in
Yoav Weiss [00:29:33]:
So what do we do then?
Steve Edwards [00:29:34]:
It's
Charles Max Wood [00:29:34]:
a tough one. It it sounds like you're kind of outlining what the the issues could be, but then yeah. What do I, as the regular old web developer, do to make this better?
Yoav Weiss [00:29:51]:
So right now, I I don't really have I I don't have a perfect answer. I can like, I think as a web developer, you should probably prefer deferred scripts over Yeah. Basing
Dan Shappir [00:30:07]:
or Defer defer is defer is the good baseline. Always start with defer with you when you can.
Yoav Weiss [00:30:13]:
Yeah. With the caveat that deferred scripts all run-in a sing like, all of your pages deferred scripts run-in a single task, and they don't get interrupted. So that could be a source of responsiveness issues, because they're
Dan Shappir [00:30:33]:
Is that clear? I think you need to explain what that means.
Yoav Weiss [00:30:38]:
Okay. Sure. Let's say I have a page with 10 different deferred scripts from different sources. All of these scripts, will run one after the other without, the ability for browsers to interject and handle events while all those scripts are running. At least that's the current, Chromium implementation, and I believe other browsers follow the same pattern. It's not really defined in like, the spec doesn't force that kind of behavior as far as I know. But at the same time, it will be somewhat risky to change it because pages can break if side effects can now be internally then between in in between deferred scripts. So, basically, what that means is that, yeah, we can't handle any events between those different scripts.
Yoav Weiss [00:31:41]:
We can't handle any microtasks, any promise resolutions. And and that
Dan Shappir [00:31:49]:
Going going back to your example, if we've got ten scripts and each one of them runs for a 100 milliseconds, then effectively your browser is stuck for a whole second and won't respond to any user interactions during that one second, which might be less than ideal.
Yoav Weiss [00:32:06]:
Yeah. So yeah. So I I would like, my baseline recommendation would be deferred scripts, but there's this caveat to take into account if your scripts are ex if you expect those scripts to run for a long while, then maybe the first script is not the best option there occur. Like, there is current effort, to modify this behavior, but, yeah, it it's not not trivial because there is risk, compatibility risk in changing it. So, essentially, yeah, I think that today's best option is maybe, like, yeah, somewhere in between ASIC and deferred, but both of them have drawbacks.
Dan Shappir [00:33:04]:
I think that that most bundlers or most meta frameworks either put use defer with all the downsides because, like we said, it's it's the best of the worst. Or, alternatively, they use blocking scripts at the very end of the document. I think those are the most common ways that most, frameworks use because it's also the safest approach in a lot of ways.
Yoav Weiss [00:33:36]:
Yeah. I guess.
Dan Shappir [00:33:38]:
And and as we said, there are two ways to get deferred behavior. Either you add the deferred attributes or you put the type equals module, which makes your script an e s ESM module, and then it's deferred by default.
Yoav Weiss [00:33:55]:
Yeah. Which kinda brings me to the problems with ES modules because they are also not, like, they are how a lot of people, at least a lot of people around me are writing code. They are not necessarily how a lot of people are delivering code. Bundlers, a lot of bundlers are turning ESM into, COM JS or other, classic script patterns. And the reason for that is that if you deliver ES modules to the browser and rely on that, essentially have static imports as part of what you deliver, those static imports are, by definition, discovered late. The browser needs to parse that first script in order to discover the 2nd layer of imports. It downloads them, it parses them, and and it's only then discovers the 3rd layer of imports and so on and so forth. So by definition, you're hitting a waterfall pattern.
Yoav Weiss [00:35:09]:
If you are delivering ES modules as is to the browser.
Dan Shappir [00:35:16]:
And those and those static imports, if I recall correctly, are are blocking. Right?
Yoav Weiss [00:35:25]:
They are blocking the script from running. Yes. They all and and yeah. Essentially, the whole module 3 will wait until everything is loaded and only then will it execute in a single task. Similar to how the fur like, it basically, you wouldn't have, a way to interrupt the browser won't have a way to interrupt this single task of the script while it's running. So the But
Dan Shappir [00:35:54]:
but will
Yoav Weiss [00:35:55]:
load at once.
Dan Shappir [00:35:56]:
But if you I I I don't know if you remember, but do it is the browser itself responsive during that import? Or is it kind of like an alert or something?
Yoav Weiss [00:36:08]:
So the renderer will not be so while everything is downloaded, the main thread is still free. It's just when when some like, when something when when the module 3 starts executing, that's when, the main thread blocks.
Dan Shappir [00:36:32]:
So So execution so execution is blocked, but not the browser until all these imports finish.
Yoav Weiss [00:36:40]:
Yeah. Yeah. The the download of the imports is done asynchronously. Okay. But it's it's late, like, there's a discoverability problem.
Dan Shappir [00:36:49]:
Yeah. The browser
Yoav Weiss [00:36:50]:
doesn't know about them until it parses, like, doesn't know about the next layer until it parses the layer above it.
Dan Shappir [00:36:58]:
Okay. But there is a solution for that kind of. Isn't there? With module preloads or stuff like that?
Yoav Weiss [00:37:04]:
Sure. But you would need to module preload the entire tree In in order for in order to solve this discoverability, you would need to module preload the entire tree. And and one more thing that I was surprised with, when poking at, ES modules from, like, slightly closer. Import maps are, which are maybe I should first start by talking about import maps. So essentially, import maps enable us to map module specifiers to URLs And that has a very strong, attribute of, enabling us to avoid invalidating entire trees if a single module has changed. So if if we have a module that is changed, Typically, when bundling modules, we are maintaining a hash or a version of that of that module in the URL itself. And those hash invalidations because it essentially, if one of the leaf modules have changed, that, its URL has changed as well. That means that the module that refers to it also has a content change that changes its hash, which then propagates up all the way, up the module tree.
Dan Shappir [00:38:58]:
Oh, so it kinda bubbles up the module tree if if any leaf kinda changed.
Yoav Weiss [00:39:04]:
Exactly.
Charles Max Wood [00:39:05]:
Incidentally, I'm just gonna point out that, import maps is what Rails uses now as it's,
Dan Shappir [00:39:12]:
default. Yeah. The whole, it's kind of the whole DHH thing, I think, is is avoiding bundlers and relying on the built in browser capabilities, which means ES modules, the the built in ES modules and and import maps.
Steve Edwards [00:39:28]:
Yep.
Yoav Weiss [00:39:28]:
Yeah. So import maps are great, for that purpose, but they are also, at least today, are rather fragile. And there can only be a single import map in a document, and it has to be the first thing that loads inside of that document. So if you have any module script that loads before an import map, the import map froze and nothing of what it does is valid. And if you have a very large JavaScript app that has, let's say, a few 1,000 modules, which I've now heard multiple real life examples of in multiple companies, you would have to load all of these thousands of modules, into your like, the mapping for all of those modules will have to be part of your initial import map, which is the very first thing that your HTML should contain. In line. So there are
Dan Shappir [00:40:42]:
In line? It has to be In line?
Yoav Weiss [00:40:44]:
Yes. There are no ex no supports for external module. Well, external import maps. And external like
Dan Shappir [00:40:53]:
better and better.
Yoav Weiss [00:40:54]:
Yeah. I I guess
Dan Shappir [00:40:57]:
I I guess I see the reason. I mean, given that it's so urgent and so so fragile, you don't want it as a separate document that you need to go and and and download on the side. But but still, it's it's not wonderful to to have this huge thing stuck at the very beginning of your lovely semantic document.
Yoav Weiss [00:41:24]:
Yeah. So I tend to agree. I think that we, like basically, what I've spent a large chunk of my day to day on is trying to figure out what a spec for having the ability to have multiple module multiple import maps and then merge them, what would that look like? And yeah. So I'm I'm basically I think this is one of the more urgent problems, for both, very large, JavaScript apps, but also for smaller ones that don't necessarily have control over their entire content. I don't know if you, like then if you imagine your days at Wix, like, there are a lot of CMSs that integrate content from multiple places. Some content is, you know, coming from the platform. Some content is coming from your, customers and their third parties, and you integrate all that together. And if any one of those folks is using an import map and another was using modules before it, everything breaks.
Dan Shappir [00:42:46]:
Yeah. I'm also thinking of stuff like, Google Tag Manager or any other kind of pixel system, which could theoretically or ideally benefit from from such a mechanism. But, again, you're bringing in resources from multiple vendors, from multiple URLs. You know, it's it's it's having a single source of truth and everything else ignored is a is a very problematic model.
Yoav Weiss [00:43:18]:
I agree. And I think, like, the the yeah. Dynamics crap loading from 3rd party, I think that's a very interesting use case here as well. And, yeah, that's so so basically, I think, yeah, that right now, there are a bunch of issues with ES modules and import maps and yeah. I'm I'm on my, you know, starting my path to fixing them.
Dan Shappir [00:43:51]:
And it can get even more complicated if you throw web workers into the mix, I would imagine.
Yoav Weiss [00:43:58]:
To be honest, I haven't even thought a whole lot about web workers in this context. I mean, there are, yeah. Because right now, they don't have a way to like, web workers don't have import maps.
Dan Shappir [00:44:14]:
And they need it because you can actually okay. So first of all, we talked about the various ways to load scripts. So web workers are another way to load scripts because if you do a new worker, the parameter you specify is the script file that gets loaded into that web worker. So, effectively, here's another way to load scripts. Not only that, there's a parameter that controls whether or not the script that you load into the web workers is ESM or not. It's ESM or classic, I think, and the default is classic, but it might be ESM. So you might be loading an ESM script into the web worker, and then you definitely would need some sort of a mapping mechanism to work with the worker.
Yoav Weiss [00:45:02]:
Yep. Yep.
Dan Shappir [00:45:03]:
Pun intended or pun not intended.
Yoav Weiss [00:45:06]:
I agree. And right now, yeah, import maps are only defined for documents and only defined With the
Dan Shappir [00:45:14]:
inline map.
Yoav Weiss [00:45:15]:
For for worker, you don't really have where to inline that import map today.
Dan Shappir [00:45:19]:
So would it use the do you again, I don't know if you remember, but would it use the documents, the parent document? So it just doesn't have a map at all, and that's it. I can kinda get it because it might be a shared worker and then where or or a service worker. And then where would it take the map from? But
Yoav Weiss [00:45:40]:
Yeah.
Dan Shappir [00:45:40]:
The web worker I don't know. Maybe.
Yoav Weiss [00:45:44]:
Yeah. Yeah. To be like, I think it's a very valid case. And yes. Module workers are the future especially because, import scripts for classic workers is also very, like, that's it's they're a fraud. Yeah. That It's bad. It is
Dan Shappir [00:46:10]:
I I I let's put it this way. I I made Wix, significant loaded scripts since web workers scripts significantly faster by hacking around import scripts, which is yet another way of loading scripts into the browser, and I won't even go there.
Yoav Weiss [00:46:29]:
Because it's loading them like, if you have a list of scripts, they will load sequentially.
Dan Shappir [00:46:35]:
Synchronously and sequentially.
Yoav Weiss [00:46:37]:
Synchronously and sequentially and yes. And that is like, without any good reason. So yeah.
Charles Max Wood [00:46:47]:
So or it sounds like you're working on a new, standard to to handle some of this. So what what does what does that look like and what are kind of the hang ups getting there?
Yoav Weiss [00:47:08]:
So so yeah. So basically, I've been, like, I'm planning to work on a bunch of, standard improvements or, web platform improvements on that front. So the the very first thing that already shipped, that was, missing from my perspective for ES modules is, integrity, sub resource integrity. So, SRI. If you're familiar with that, for regular, for classic scripts, you have an integrity attribute where you can say, only execute this script if, it matches this hash. So if as part of my build process, I like, I have controls over my build process, then I upload these assets somewhere. And then when the site loads, I wanna make sure that my assets match what I think they should be. And no one no malicious actor has switched them up in between.
Dan Shappir [00:48:19]:
Like, avoiding a man in the middle kind of attack.
Yoav Weiss [00:48:22]:
Mhmm. It's not really man in the middle. It's more of a, like, you know I don't know if there's a fancy name for it, but, basically, the content swap at rest. So the content is uploaded to your hosting provider, and then someone with the keys can swap it to add malicious payload. You want to avoid that scenario. You want to have, integrity checks in place in the browser.
AJ O'Neil [00:48:53]:
So you
Dan Shappir [00:48:53]:
can actually put an attribute on the script tag that says this is the check sum that my script should have. And if it doesn't, then just no digit.
Yoav Weiss [00:49:04]:
Yes. Same for CSS, and preload. And that's it. You can't do that for any other type of content, but that is sufficient because images are presumably not very important and at the same time, they are also harder to pull up. Like, harder to do that integrity check without slowing them down. But this piece was missing from, module imports. So if you have dynamic imports for modules where you want to, like, load the critical scripts upfront and then dynamically load stuff you need for later once things come calm down or once the user did something. Those scripts didn't have any way to to get an integrity check, without jumping through many hoops, because it didn't have like, there was no native support for ES modules and integrity checks.
Yoav Weiss [00:50:10]:
So the first step I took in that, potentially long path to making, script loading better is to add that kind of, that kind of support with an integrity section as part of the import map. So that has landed in Chrome 127 last week, hitting stable last week, and it's on its way to, Safari 18, which is presumably gonna hit users sometimes this fall. So that Cool. Yeah. Yeah. I'm it it was a relatively relatively fast, project. Basically, I, during a flight, put together initial prototype, initial spec, and, rudimentary tests. And then, like, the the whole thing took roughly 2 weeks to to
Dan Shappir [00:51:19]:
You you built you built Chrome while on a flight?
Yoav Weiss [00:51:23]:
Yes. This is what I do on a
Dan Shappir [00:51:30]:
flight. Interesting. Yeah. To each their own, I guess.
Charles Max Wood [00:51:35]:
So you've got the integrity check.
Yoav Weiss [00:51:39]:
So so are there other Yeah. That that was the first step. I think that the next step is probably, the multiple, import maps and dynamic import maps.
Charles Max Wood [00:51:54]:
Okay.
Yoav Weiss [00:51:55]:
I think that that's the the next thing to reduce fragility and, and and generally yeah. Make it more more feasible for large apps to use import maps, because the cache cascade problems that they solve are real, but, yeah, the the blocking nature is blocking.
Dan Shappir [00:52:19]:
Yeah. But that opens interesting questions, like, unless I'm I'm overthinking it may which is possible. I do that. But it for example, it it means that script a can control where unrelated script b loads from. Uh-huh. I'm kind of kind of it's kind of like what I would do with the service worker in a sense. Like, I I can tell it it says this URL, but actually download it from that URL.
Yoav Weiss [00:52:55]:
So Verify like, you wouldn't have the ability to redefine a script that was already loaded. No.
Dan Shappir [00:53:14]:
Obviously. So the
Yoav Weiss [00:53:15]:
Or a script that was, already defined in another import map. So you wouldn't be able to redefine a specifier.
Dan Shappir [00:53:24]:
So it's not like cascading. It's kind of like a join sort of the same.
Yoav Weiss [00:53:31]:
A join where, you know, first in stays kinda.
Dan Shappir [00:53:38]:
Yeah. No variety.
Yoav Weiss [00:53:40]:
Yeah. And that is still up for grabs. Like, I have an algorithm in mind. I will like, once I have a PR up, I will definitely, share it with the world as well as with you. And, yeah, I'm happy to get feedback on that. But I think it's, yeah, I think that the model where you can't, yeah, you can't override something that was already defined gives us enough safety for some definition of safety. I mean, theoretically, like, it import maps are essentially scripts that are running in the top level documents context. So they can like, the fact that they can override things is not a security risk because you already like, you've introduced the vampire into your home kinda kinda scenario.
Yoav Weiss [00:54:41]:
But, at the same time, we don't want developers to be surprised, and we don't want, import maps that are coming from different sources to collide. So, yeah, we we want this to be as predictable as possible.
Charles Max Wood [00:54:56]:
There's a question on on Twitter from, Gal, Weissman. I'm sorry if I say your name wrong, my friend.
Dan Shappir [00:55:05]:
Oh, you only have him as a guest, I think.
Charles Max Wood [00:55:08]:
Yeah. But he asked about a compromised script can potentially leverage an iframe to bypass the SRI checks dictated by the top document and thus load a remote third party script that's not allowed to load, I think. The I, I think, is in parentheses. Is that being taken into consideration so this is back on
Yoav Weiss [00:55:32]:
the SRI? So knowing goal, I'm sure he has a scenario in mind that I don't, but I think that that nonverifiable, like, an iframe, we're we're talking like like, does he mention, like, same origin, cross origin? Because No.
Dan Shappir [00:55:58]:
It would have to be same origin. Otherwise, it's Yeah.
Yoav Weiss [00:56:01]:
Because otherwise, it's irrelevant. Yeah. A a same origin iframe, if it's compromised, then, yeah, it would have a different as, like, it would have a different, integrity. Like, the import map doesn't apply to same origin iframes. So it would be able to load that script. At the same time, I wouldn't expect the cache to like, if that script is cached from the same origin iframe, I wouldn't expect it to be loaded at the top level without failing, like, because one has integrity checks and one doesn't. So I I would expect the browser to fail that load at the top level frame. Mhmm.
Dan Shappir [00:56:53]:
I also actually have a question. Like, looking at all the stuff that you're doing, so the SRI, the, the mod the module maps. Also, the work on compression dictionaries. I think we had Patrick Meehan on the show to talk about it. All this stuff is about how to better load JavaScript into the browser so that we don't need bundlers as much. Or that bundlers can be, maybe, less heavy handed than they are? You're you're shaking your head.
Yoav Weiss [00:57:29]:
That's not so I think we need bundlers. I think that there are some issues with, like, physics when it comes to loading a lot of, small modules into the browser. Browsers have overhead, like, per request overhead. That overhead is unlikely to
Dan Shappir [00:57:52]:
go away. Lookup. Just Cookie lookup.
Yoav Weiss [00:57:56]:
Yeah.
Dan Shappir [00:57:57]:
Inter process communication.
Yoav Weiss [00:58:00]:
Yes. Networking stack. Foundations, all that. Like, that takes time and it I think at the time we looked at Chrome and it was around, like, 1 to 2 millisecond per resource which is not awful unless you're loading 5,000 resources. And in that case, you're talking about, like, 10 seconds just to get the thing, like, even if it's on disk, even if it's like 0 RTT, on the network, it still takes a long time to load these assets. If you so that part is unlikely to go away. Go ahead.
AJ O'Neil [00:58:45]:
In those cases, isn't the problem somewhere else? I mean, if your if your application's designed in such a way that you don't have any sort of segmentation and you're loading 5,000 assets? I mean, it just it just kinda seems disproportionate. You know? Like, is this really the problem over here?
Dan Shappir [00:59:07]:
But but, AJ, this is kind of the DHH model. I mean, DHH basically said, I'm and I'm kind of paraphrasing. Like, let's not bundle at all, which means that the structure of your code in your code base is the also the structure in which the code loads. Now if you're one of those people who likes to put every function or every component in their own separate file, then you can end up with and it's a large enough project, you will end up with thousands of resources.
AJ O'Neil [00:59:44]:
Well, maybe you shouldn't do that. Maybe that should be a signal. That's a bad way to code. Stop doing it. So Mhmm.
Dan Shappir [00:59:51]:
Yeah. So if you have a
Yoav Weiss [00:59:54]:
very large team if you have a very large team that's building a very large web app, Let's say, you know, Facebook. They have a lot of people working on different parts of the app, They share code. There are a lot of modules involved. So
AJ O'Neil [01:00:15]:
Well, you but that's more for the benefit of of investors. Like, trying to show continual growth by continually hiring more people, not because people are needed. Like, Twitter 5 70% of their workforce, and Twitter got better.
Yoav Weiss [01:00:31]:
I I I would argue that got better part, but yeah.
AJ O'Neil [01:00:36]:
It it didn't get worse. It's not slower. It's not less reliable.
Charles Max Wood [01:00:41]:
I I think though that the point is is you've got you've got so so let's say that you've got things broken up by components and you've got components in
Yoav Weiss [01:00:52]:
different files like we're talking about. There there are a lot
Charles Max Wood [01:00:53]:
of things that are really convenient as far as, like, developer ergonomics that come from that, and that's why we do it. Right? But at the end of the day, when we deliver it to the browser, the point is is that you you can pull all of that together with a bundler and deliver one deliverable and and reduce a lot of that overhead, which also
Dan Shappir [01:01:14]:
makes sense.
Charles Max Wood [01:01:15]:
And I'm a big fan of having tools that solve the different problems in the right way. And so that that's where I'm I'm sitting here and agreeing with Yoav on this even though I am, you know, I generally agree in a lot of cases with DHH. In this case, it makes a lot of sense to have that bumbler pick up those things and, you know, any of the other tiny bits that kind of have similar responsibilities. And then something like import maps solve some of the other issues where I'm pulling in a bunch of 3rd party stuff and saying, okay. I need this and I need this and I need this and I need this, but I'm not necessarily fiddling with that stuff.
Dan Shappir [01:01:52]:
And I'll put it and I'll also phrase it in a different way. If I'm using a compiled language, like, I don't know, like c or rust or or whatever, There is a separation between how the code is organized and how the bytes are delivered for execution. And unless and and the DHH model, for better and worse, cancels this separation. If I prefer using a lot of small files, it's a choice, a choice that you might not agree with, but it's a legitimate choice for some organizations. It means that I can't use the DHH model or the DHH approach without paying a potentially hefty price for
Yoav Weiss [01:02:39]:
it.
AJ O'Neil [01:02:40]:
I fair. I mean, I I agree with that. I I just I've seen code bases where it's 1 function per file. It seems it's almost like a meme. It's so popular. But it's just it's it's silly. I mean, you can't even understand the context of how a button fits into something because you gotta look at 10 files to figure out. That yeah.
AJ O'Neil [01:03:04]:
That that that like, I'm thinking I'm thinking I don't know. I I was thinking why would something have 5,000 files. I wasn't even thinking of the, like, one function per file because I wouldn't think a serious business would do that. I I
Dan Shappir [01:03:17]:
I don't know if
AJ O'Neil [01:03:18]:
Facebook does that.
Yoav Weiss [01:03:19]:
Yeah. I I don't think it's a one function per file, but I think it does, like, it does result, like, code sharing between teams does result in a lot of small modules. They're not necessarily a single function, but they are a single functionality. And I don't know if this is the, like, the best way to develop or the west or the worst way to develop. Like I said in the beginning, I'm not really a web developer. I pretend to be 1 once in a while, but I'm not doing that in, like, in my day to day. I'm mostly, hanging on browsers, but it is a legitimate way to deliver software on the web. And we should like and I think that, bundlers are essential for that part, both for the browser overhead as well as for compression ratios.
Yoav Weiss [01:04:16]:
Because if you're compressing very small files, you will compress them very poorly compared to large files that compress very well. So, Yeah.
Dan Shappir [01:04:25]:
But then we have the compression dictionaries which mostly solve that.
Yoav Weiss [01:04:30]:
I I don't think they will solve it for very small, like, you would still have to deliver the very small files once and you would still have a very like, I I think compression dictionaries solve a different problem with bundlers. Or at least in my view, like, they could solve it as well to some extent. But, they in my view, with bundlers, one of the issues with a large bundle, one of the issues is you're losing caching granularity. If any single, function a single character inside that bundle changes, you have to download the whole thing back again. And compression dictionaries will help us avoid that at least on the on the network.
Dan Shappir [01:05:20]:
Yeah. So but but my initial point was kind of different. We're doing a lot of things that that impact the the form in a way that certainly affects how bundlers work or should work. How much cooperation are you guys getting from the bundle makers? Because it seems that they should be significantly involved in all this effort.
Yoav Weiss [01:05:49]:
So at the time, I think maybe on the podcast, we were talking about, like, web bundles in, a long while ago. And bundlers were very much, part of the loop on on this. And, Daniel Arenberg, from yeah. I don't like, he may have been at Igalia. He's nowadays at Bloomberg. He was super involved in bringing the bundler community into the room, and, there's a TC 39 tooling meeting, that, we talked about multiple times, at the time about web bundles. And I think that they are like, they were super supportive. I think that once this, what what I'm talking about will reach a more, mature level, I would be very happy to talk to them, and I'm assuming that they will be, similarly supportive because none of the like, essentially, this is all not, like, talking about maybe, like, improving bundlers and improving the output of bundlers to deliver better experiences.
Yoav Weiss [01:07:05]:
So I think it aligns well with everyone's, goals and intentions. In the meantime, a lot of the bundlers are very configurable, and you you can you can go a long way just by mucking around with roll up plug ins. And that is at least the approach that I'm taking now with the various prototypes that I'm working on.
Dan Shappir [01:07:38]:
Which means that you're effectively compatible with ES build, which means that you're effectively compatible with Vite.
Charles Max Wood [01:07:45]:
Yep. I love Vite.
Yoav Weiss [01:07:48]:
Any Same.
Charles Max Wood [01:07:50]:
So sorry. Just came out. Anyway, yeah. Because like I said, you know, I follow along with Rails, DHH. I mean, that's kinda where I live my programming life, but I'm using Vite on my Rails projects. I'm not using import maps.
Dan Shappir [01:08:05]:
Who is this?
Charles Max Wood [01:08:09]:
So, but but I kinda wanna jump back over. So you so far, we've got, compression dictionaries. We've got import maps, doing multiple import maps. We've got SRI. I mean, what what other things are you proposing to fix this stuff?
Yoav Weiss [01:08:25]:
So proposing is a bit of a, like, you know, a a big word. I have ideas that I wanna play around with. One of them is, defining different controls as to when the scripts are loaded versus when they're executed and defining more milestones for the browser to execute deferred semantic scripts other than just the dumb content loaded. So maybe adds more milestones around first render, like, FCP fired now executes these other scripts. Unload fired, execute these other scripts after unload, things along those lines, are things that I'm planning to play around with. I'm
Dan Shappir [01:09:16]:
I guess what you mean what you mean is to, like, declarative support because programmatic support already exists. For example, obviously, for on load, I can do window dot on load equals Sure. And I can specify code to execute on the on load.
Yoav Weiss [01:09:34]:
Yeah. So I would love to play around with a polyfill of what, declarative support for that would look like and see if this these kind of modules, give us any benefits in terms of, execution. And then if they are, then this would be potentially something to, you know, propose as new keywords that will enable us to better load scripts without the, you know, hacking through, like, preloading the assets and then executing the the script manually in different milestones. Yeah. So so this is one thing I'm thinking of playing around with. Another is, with stream execution of bundles. So we talked about the fact that bundles are, you know, if anything changes inside the bundle, then
Charles Max Wood [01:10:39]:
Right.
Yoav Weiss [01:10:40]:
The entire bundle gets, invalid and then the cache and you need to download a new one. But beside that, bundles also, delay execution because you have to download the entire bundle before you can start executing anything. But because we are starting off from ES modules, we could maintain those module boundaries and then recreate them in the browser, in ways that enable the browser to execute the modules separately. And there's a TC 39 proposal, around module declarations. Again, from Daniel Ehrenberg that I mentioned earlier. I am playing around with the user land prototype to see what that gives. It requires a lot of hacks, both on the bundler side as well as on the browser side. But, we'll see where that gets it gets me.
Yoav Weiss [01:11:41]:
I still haven't seen it working yet, but, you know, Yeah. I'm I'm hopeful that this would be a successful, module to start executing earlier.
Dan Shappir [01:11:56]:
An interesting idea that just occurred to me while we were speaking is you were talking about declaratively controlling when scripts execute.
Steve Edwards [01:12:05]:
Yeah.
Dan Shappir [01:12:05]:
It might be worthwhile to also have declared or to try out ways of controlling when resources or scripts start downloading. Like Yeah. I want to download something asynchronously, but I don't want to to for it to start downloading before the LCP because I don't want it to get in the way in the way of the LCP in any shape or form. Yeah. But, by by the way, another and, it's worth mentioning that if people who are listening to us find all this stuff interesting and have their own ideas, they can basically join, you know, participate in the w three c web performance working group and make their thoughts heard.
Yoav Weiss [01:12:53]:
Yeah. For sure. Definitely so some of these things are like, some of these things are hacky projects that haven't gotten anywhere just yet. Some are, going to probably live mostly as, what w g PRs against the HTML spec. But all of this is something that we can and should discuss in the web performance working group. So, yes, if folks are interested, feel free to hit me up. I can, like, yeah, join the calls, and, yeah, make your horses heard.
Charles Max Wood [01:13:33]:
Yeah. It this sounds like a good place to kinda start to wrap up too. It is there a list of these proposals or these ideas somewhere that you have, Yov, or are we kind of it right now?
Yoav Weiss [01:13:46]:
I need to write it down. This is all, like, there's a a list of things I put together for this, for this podcast, but it's, like, not something I can publish. But, yeah, I I need to write down this, as a app. Master plan to improve script loading. And and then, yeah, I I need to publish something on that front.
Charles Max Wood [01:14:17]:
Cool. Well, if people have ideas, how how do they join that working group? I think that might be an interesting place to go.
Yoav Weiss [01:14:24]:
Yeah. Basically, the main path. So if they work for a w three c member, then they can just join, and ask their AC representative to to join the working group and yeah. And that's it. Otherwise, they can, ping me or or the yeah. Or Nick Jansma, who's the other chair at Akamai. And, yeah, we can, you know, talk through the the issue with them. Yeah.
Yoav Weiss [01:15:11]:
I'm I'm pasting the a link to the web performance, to the working groups, page where you can you know, if you're, a WCC member, you can join through there. And, otherwise, yeah, just, email me, or Nick Jansma, and we can set you up. They're like, we're available over email, over the there's the web performance, Slack group that a lot of people are on. And, yeah, otherwise, you know, on the Internets.
Charles Max Wood [01:15:48]:
Good deal. Alright. Well, I'm gonna go ahead and slide us into our picks. But this this has been really fascinating. But, yeah, let's do our picks. AJ, do you wanna start us off with picks?
AJ O'Neil [01:16:04]:
Let's see. What have I got? My wife and I recently watched the Jason jet the well, we start we've started watching the Jason Bourne trilogy, but we started with the best one, which is Bourne Supremacy. And she liked that, so we're probably gonna watch the others as well. So I will I will pick the the Bourne trilogy because it's kind of a kind of a cool movie.
Dan Shappir [01:16:36]:
And She has sufficient context?
AJ O'Neil [01:16:41]:
Well, I when the movie started, I told her, okay. The the thing is this guy is basically James Bond, except he wakes up one day with amnesia and is trying to figure out what he's doing. And this is the 2nd movie, and we're starting with this one because it's it's better. And if we started with the first one and you didn't like it, you might not wanna watch the rest of them, but the other yeah. You know? They're they're all the kind of the same movie. It's kinda like Terminator and Terminator 2. It's the same movie. It's just way better production.
Dan Shappir [01:17:11]:
By the way by the way, I'm one of the few people I imagine who've actually read the Ludlam book before they even watched the first movie.
AJ O'Neil [01:17:20]:
So there's there's, like, 10 books. Aren't there?
Dan Shappir [01:17:24]:
To be honest, I don't remember. The problem with Ludlam is that all his books kind of are the same book.
AJ O'Neil [01:17:32]:
Well, the movies are the same movie, so that tracks. But, I mean, same thing with James Bond. Right?
Dan Shappir [01:17:39]:
Yeah. I guess.
AJ O'Neil [01:17:40]:
Yeah. So there's that. I'm still motorcycling. Still absolutely love it. And,
Dan Shappir [01:17:48]:
I'm trying
AJ O'Neil [01:17:48]:
to think if there's there's anything else worth worth picking. I do I do have to send a pick from earlier. I at one point, I'd picked silicon power drives. I've loved silicon power for micro SD cards. They have been amazing. However, I I had ordered about 16 of the silicon power SSDs. Actually, I don't think it was that many. Yeah.
AJ O'Neil [01:18:13]:
Well, it was about that many. 4 of them have failed over the course of the last year and a half. And this is in a server environment. And they told me you know, I got a business account with them. They told me they would, you know, warranty them for the server. They'll warranty them, but they fail. And we've also got 16 crucial MX 5 100, and not a single one of them has had a hiccup. So I guess my my pick would be crucial MX 5 100 if you're if you're putting together a server and you want the best value drives, I have to switch my pick on that to being crucial.
AJ O'Neil [01:18:46]:
Silicon power is, like, half the price, but you don't wanna be going to your data center replacing drives except for when you have to. So I'll, I'll pick those as my picks.
Charles Max Wood [01:18:58]:
Steve, what are your picks?
Steve Edwards [01:19:02]:
Well, before we get to the high point of every episode, came across an interesting, blog post or article, whatever you wanna call it, on Hacker News about OpenAI. And, you know, we've been using AI more and more in my work, but in a, you know, in a scope limited sort of capacity based on our own data. But the title is how does OpenAI survive? And it's a pretty detailed walk through the business model and what OpenAI would need, in terms of huge growth of money and just a bunch of unprecedented things to happen in order of them to survive over the next couple years. So, if you want something as a cure for insomnia, it's pretty good, I think, but it's also pretty interesting if you're into, reading about OpenAI. Says they seem to be on a lot of tips of everybody's tongues these days.
Dan Shappir [01:20:00]:
We kind of spoke about this subject when Steve Sewell was on the show. I think, I I kind of have tongue in cheek said that, like, the only company actually making money off of the AI revolution is NVIDIA.
Steve Edwards [01:20:15]:
Right. Because of the chips. Right? Yep.
AJ O'Neil [01:20:17]:
Well, I'm looking forward to where we could just download the model on you know, when when when OpenAI goes out of business and they and they open source the model, I'm happy to download that, you know, 40 gigabytes on my computer and run it off the power of my MacBook.
Dan Shappir [01:20:32]:
I think there's the Ollama model Ollama model that you can from Facebook, I think, where which you can already download.
AJ O'Neil [01:20:39]:
It's that's true. And it's it's better in some ways than chat GPT 3, but it's not better than chat GPT 4
Charles Max Wood [01:20:47]:
o. Yeah. The way the way that I understand it, and I'm still learning about this stuff. But, yeah, it it's good for a baseline if you're gonna train your own stuff on top of it, right, to give it better context. But, yeah, the GPT 4 models are much more comprehensive and give better answers.
AJ O'Neil [01:21:16]:
I mean, they do have access to every book that's ever been made in every journal and because they get asked questions like, so are you using copyrighted content that's, you know, like, paid content that you're just putting into the model and making available to everyone, and you're gonna face major lawsuits? And they're like, well, you know, it's hard to say because, I I don't know exactly where all the data comes from, but it's definitely data that's available online. So, you know, you your your is, like, basically Wikipedia, Stack Overflow. You know, it's it's the the big sites, but GPT 4 o is all of the content that humanity has ever created. There's not gonna be a GPT 5 because there's no more data left.
Steve Edwards [01:22:07]:
Alright. And then moving on to the highlighted Or
Dan Shappir [01:22:12]:
Unless they just to say, unless they start putting in pictures of cats because there are always new pictures of cats.
Steve Edwards [01:22:19]:
Always. Always. Some of those
Charles Max Wood [01:22:21]:
are gonna be AI generated too.
AJ O'Neil [01:22:23]:
That's why I'm paying the $20 a month.
Charles Max Wood [01:22:24]:
Except shit.
AJ O'Neil [01:22:25]:
Best cats. The best cats.
Dan Shappir [01:22:27]:
The cats with 6 fingers.
Yoav Weiss [01:22:31]:
So,
Steve Edwards [01:22:32]:
I am suing the doctor who delivered my baby. My son now has to grow up without a liver. Delivered. Anyway, sorry. Sometimes you gotta explain them. I was attacked by a flock of sheep yesterday, but luckily, I was only grazed. That one's sort of bad.
AJ O'Neil [01:22:56]:
We can see that there. We can see that.
Steve Edwards [01:22:59]:
Yeah. Right there. Right there. Grazed. And then, I love this one. I got I thought for sure I'd get shot down on this next one. People loved it. I was, I was gassing up my Honda Accord the other day at a gas station, and, a snarky Tesla owner asked me how much I spend on gas.
Steve Edwards [01:23:18]:
I said, about 5 minutes.
AJ O'Neil [01:23:23]:
That was that was well done. And I I I need to make a remark on Tesla, by the way. They are the number 2 per capita as in per Tesla owner versus per other car owner. They are number 2 and most likely to get into a wreck, and they are the number 1 motorcyclist killers. So if you own a Tesla, wake up, get your hands on the steering wheel, watch what's in front of you. Don't run over people. K. Thanks.
Dan Shappir [01:23:51]:
By the way, about the delivered, it kind of reminded me there was the scene from Monty Python, the meaning of life movie, where they knock on his door and they said, you're you're a registered organ donor. I said, yes. We've come to collect.
Steve Edwards [01:24:10]:
Oh, boy. Yes. That my favorite scene from that particular movie is the guy in the restaurant. Oh. Just a wafers in mid 3rd. That's all.
Dan Shappir [01:24:19]:
No. I think my best one and my favorite one is that that every sperm is sacred, song and dance routine.
Steve Edwards [01:24:28]:
Anyway, those are my picks.
Charles Max Wood [01:24:30]:
Dan, why don't you just keep us going? What are your picks?
Dan Shappir [01:24:34]:
Not exactly a pick. The 20 twenties have sucked so far, and, this year has not been different in any way, shape, or form. And, week and a half ago, our lovely and beloved my lovely and beloved mother-in-law passed away. So it's been a really tough week for us. So I would like to dedicate my part of this show to her memory. I miss her dearly. We all do. And that's all I have.
Charles Max Wood [01:25:13]:
Yeah. Yeah. Losing people's hard.
Dan Shappir [01:25:15]:
Yep.
Charles Max Wood [01:25:18]:
Alright. I'm gonna jump in with some picks. I usually do a board game, and so I'm gonna do a board game. We played this yesterday. What we've been doing with my family is, we we've been picking a game that we haven't played in a while out of our collection, and then, you know, we play it and we decide if we wanna keep it or not. And the one that we picked up was Imagine If, and this is more of a party game, which I have to say generally are not my favorite games. The I mean, this one's fun. I just sometimes when when I'm in the mood for a board game, I usually want something that's gonna make me kinda think and strategize and stuff.
Charles Max Wood [01:26:02]:
The, you know, the party games aren't that way, but this one's a fun one, especially if you're all part of the same group that know the same set of people. You just you write down names around the outside of the board. There's a marker. You roll the die. You move it that many spaces. You pull a card. You read the card, and let's imagine if, Betty were a type of shoe, which one would she be? Right? And then it's like a stiletto, a hiking boot, you know, a baby booty. Right? And so then you, everybody has 1 through not cards numbered 1 through 6 in their hand.
Charles Max Wood [01:26:39]:
They put 1 face down. You flip them over. If you're in the majority, then or if you're in the group that has the most, I guess, that doesn't mean you're in the majority. Then you move up 1. If you're the person who read the card, you move up 2, and then you do it again. There's a space for challenge, and that one, you pick another person that you think you're gonna match with, you roll the die again, you move the marker, You read the card. The 2 of you put down your numbers, and if your numbers match, you move 4. And if you don't, then you move back 2.
Charles Max Wood [01:27:11]:
And, my 8 year old sabotaged me by challenging me and then picking a number that she knew I wouldn't pick so that I wouldn't win. That's the way that game went last night. But overall, it's fun game. Board game, Geek, weights it at 1 point 22, which means it's super simple. I mean, I basically explained all the rules to you in less than a minute. But it is kind of a fun party game. And so, you know, we had all of our family members and then, you know, grandpa who wasn't there. So, anyway, I'll go ahead and link, to the, BoardGameGeek, listing in the the comments only show up on Twitch, YouTube, and Facebook.
Charles Max Wood [01:27:56]:
So if you're watching on Twitter, which is where most people are watching, you just have to go look it up. It's imagine if, drop the e at the end of imagine, put I f f at the end, you'll find it. And then other picks. So my my oldest son is 18, and his favorite movie is A Quiet Place. And so we went and saw A Quiet Place day 1. I mean, no spoilers. He said that some of the people are in the that are in A Quiet Place day 1 are in A Quiet Place part 2, which I haven't seen, but they're pretty minor characters. So I guess it's kind of an origin story for that group of people that you'll see in the A Quiet Place part 2, but it, it was good.
Charles Max Wood [01:28:45]:
It, you know, it's not it's not the best movie I've ever seen, but it wasn't something I regretted going to see in the theater. So I'm gonna pick that. And
AJ O'Neil [01:28:56]:
There's there's a Quiet Place day 1, then there's a Quiet Place, and then there's, like, still a Quiet Place.
Charles Max Wood [01:29:03]:
So A Quiet Place is the first movie they made, and then A Quiet Place part 2 apparent is the second movie, and then this one's a prequel that they made.
Dan Shappir [01:29:13]:
It's like the Star Wars prequels that came out.
Charles Max Wood [01:29:16]:
Yeah.
Dan Shappir [01:29:17]:
I Yeah.
AJ O'Neil [01:29:17]:
That's that doesn't sound like good.
Charles Max Wood [01:29:20]:
Yeah. Well, yeah. Anyway, so I I enjoyed those. So my I'm gonna pick that and then
Yoav Weiss [01:29:30]:
K.
AJ O'Neil [01:29:31]:
Okay. Yeah. I I was I was just confused about it. It actually is called part 2 because I did see those. Yes.
Yoav Weiss [01:29:37]:
But I
AJ O'Neil [01:29:37]:
didn't remember what the name of the segment. It literally is called part 2. Got it.
Charles Max Wood [01:29:40]:
Yep. Yep. So yeah. So I'm enjoying those. And then, one other TV show. So I'm I'm picking nothing technical, I guess, is I was browsing through Netflix, and I saw that they did a live action Avatar The Last Airbender. And, so I watched a few episodes of that with my same my 18 year old son. And we enjoyed those.
Charles Max Wood [01:30:04]:
So I'm gonna pick those. And that's that's it. That's it for my picks. Yoav, do you have some picks for us?
Yoav Weiss [01:30:12]:
Sure. So the first one, I guess, is, I mean, hiking or I don't know if I have more than that. But, like, basically, it took me, way too long to realize that I the So it's the like, hiking is the best. Almost everyone can do that. And even if you suck at it at first, you get better. And yeah. It's great for your health. It's great for your mind.
Yoav Weiss [01:30:51]:
And, yeah, everyone should hike more.
Dan Shappir [01:30:54]:
That's I can confirm and attest that you do live in a beautiful area, but given that you live in Southern France, that's not really surprising.
Yoav Weiss [01:31:03]:
Yeah. Yeah. But, at the same time, I think everyone I I don't know. Not everyone, but if you live next to a mountain of some sort, you should go up it once in a while. That's that's what I see.
Charles Max Wood [01:31:19]:
Yeah. It's it's interesting you bring that up because, AJ and I here, we live pretty close to the mountains here too, and, boy, there are some amazing hikes to go on. Yeah. Definitely, if you have the opportunity, get out and see it. Or get out and see the world.
Dan Shappir [01:31:39]:
Can you get that? You even go
AJ O'Neil [01:31:40]:
to Denver. Those are the best mountains, even better than Utah mountains.
Dan Shappir [01:31:47]:
You are. But you're the one
Charles Max Wood [01:31:48]:
on the plains, you're you wanna kinda get up toward the but, yeah, the mountains down
AJ O'Neil [01:31:52]:
there. I meant Colorado Springs. I meant I meant to say Colorado. I didn't mean to say Denver. I meant to say Colorado. But we were we took a weekend trip to to Colorado Springs area to see the Royal Gorge Bridge and the Garden of the Gods. And
Steve Edwards [01:32:06]:
Garden of the Gods is awesome.
Charles Max Wood [01:32:07]:
Is gorgeous.
Yoav Weiss [01:32:08]:
Yeah.
Steve Edwards [01:32:08]:
I went to college just a couple miles from there, so that was a popular place to go hang out, ride bikes out there and stuff.
Yoav Weiss [01:32:14]:
Yeah. Yeah.
AJ O'Neil [01:32:14]:
And we and we went white water rafting?
Steve Edwards [01:32:17]:
Yeah. I did that Friday too. Good times. Cool.
Yoav Weiss [01:32:21]:
Yeah. There's some gorgeous
Charles Max Wood [01:32:22]:
places up in Boulder too.
Yoav Weiss [01:32:24]:
Yeah. Never been to Utah or Colorado, so I should probably do that at some point.
Charles Max Wood [01:32:29]:
Come on out.
Steve Edwards [01:32:29]:
Well, Utah's awesome. My daughter and I did a sort of a loop around, Utah 2, 3 years ago. We met up with AJ and his family, when we were down there. And, you know, what did the loop come down through Canyon Lab through Moab, Canyonlands, and, we'll try across from Canyonlands. Can't even remember. And then down to Lake Powell and come up over to Bryce Canyon. Oh, Arches. Yeah.
Steve Edwards [01:32:57]:
Arches and Canyonlands and Bryce Canyon and Lake Powell, and, it's awesome. It's really pretty. Didn't hit Zion, which we would've hit Zion, but it's it's an amazing trip.
Dan Shappir [01:33:07]:
The only the only problem is kind of
Steve Edwards [01:33:09]:
on the
Charles Max Wood [01:33:09]:
other side of the state.
Dan Shappir [01:33:10]:
Mhmm. Yeah. The only problem is that the US is just so big. So getting from one place to the other requires so much driving.
AJ O'Neil [01:33:19]:
Isn't it around the same size as Europe though?
Dan Shappir [01:33:22]:
What? Oh, UK?
Yoav Weiss [01:33:25]:
Yeah. Utah is the same size as Europe. Not I'm not No. I'm not here.
Charles Max Wood [01:33:28]:
It's it's No. It's the same size as some of the European countries.
Yoav Weiss [01:33:34]:
Yeah. I I mean, it's it's I think it's big. Like yeah. It's a lot of a lot of driving involved.
Dan Shappir [01:33:41]:
I would concur that driving around all of Europe would also require a lot of driving. The thing about Europe is that it's, especially if if if you it's most it's less about the scenery in most cases. It's more about, like, you know, art and and architecture and stuff like that. And then things tend to be closer together.
Charles Max Wood [01:34:06]:
Mhmm.
Dan Shappir [01:34:07]:
Also, there are bet there are better railways.
AJ O'Neil [01:34:10]:
I stand correctly. The United States is twice the size of Europe.
Steve Edwards [01:34:15]:
Oh, wow.
AJ O'Neil [01:34:16]:
Or the European Union,
Dan Shappir [01:34:18]:
which is not all European. Like, half of Europe is Russia. So
Steve Edwards [01:34:23]:
Yeah. Yeah. It's interesting.
Yoav Weiss [01:34:26]:
Yeah. But when when I
Charles Max Wood [01:34:27]:
lived in Italy, Italy is basically if you took Arizona or Utah and you stretched it out to the length of California. Right? So so, anyway, you you get different geographic deals when you go to different countries. But, yeah, I mean, you can roughly say, you know, land size, you know, some of the western states are as big as some of the bigger European countries. So, anyway, I'm gonna go and wrap this up. Thanks for coming, Yol. This was really fascinating. And, hopefully, yeah, we get some more ideas coming your way, and we can see some of these things, you know, come come to fruition and make the Internet better.
Yoav Weiss [01:35:10]:
Thank you. Thanks for having me. It's been fun.
Dan Shappir [01:35:12]:
Yeah. Yeah. Whatever you can do to actually make the web platform and the web itself better is a literal win for
Charles Max Wood [01:35:21]:
everybody. Alright. Well, till next time, folks. Hack's app.
Overcoming JavaScript Load Issues: Import Maps and Performance Enhancements - JSJ 643
0:00
Playback Speed: