[whatwg] Proposal for separating script downloads and execution

On Tue, May 24, 2011 at 12:34 PM, Nicholas Zakas <nzakas at yahoo-inc.com> wrote:
> Moving parsing and compilation to a background thread solves part of the problem, the problem where doing so freezes the UI currently. It doesn't solve what I consider to be the important part of the problem, and that is the inability to have a JavaScript resource downloaded but not applied to the page. The best next experience can only be achieved when the resources are ready and then applied at the right moment.

Consider this hypothetical scenario: when you add a <script async> to
the DOM, browsers all download it and parse it in the background,
without blocking the main thread.  Then they execute it on the main
thread, but the execution can take negligible time if you write it as
a function that does nothing until called.  Would you need any further
features if this hypothetical scenario were real life?  If so, what
features, and why?  If not, the specs already say everything they need
to, and you should take the issue up with browser implementers.

On Tue, May 24, 2011 at 7:12 PM, Steve Souders <steve at souders.org> wrote:
> In many (all?) cases below the term "execution" is meant to include parsing
> and compilation. I know that's what Nicholas and Kyle have in mind, and is
> the motivation behind Gmail's comment hack and my ControlJS library.

There's a big conceptual difference between parsing the script and
executing it.  We need to be careful not to conflate the two, even if
browsers don't *currently* separate them.

> If browsers processed (parsed & compiled) scripts in a background thread it
> would mitigate the problem, but not solve it. Suppose I have 100K of JS I
> need right now to generate the DOM for the initial page, and I have another
> 500K of JS that's only needed if the user clicks on FeatureX. Assuming
> there's only one background thread, I want to prioritize the first 100K of
> JS on that thread, and not have it blocked by the unnecessary processing of
> the second script.

If browsers parsed async scripts on a background thread, it would be
natural to assign the thread a low OS priority so that it doesn't
interfere with operation on the main thread, which would necessarily
include synchronous scripts.  Are you worried that even low-priority
background parsing would significantly hurt performance?

I did a test on my home Linux machine, which has two cores.  I ran
four copies of "python -c 'while True: pass'", two with nice 19 and
two at regular priority.  On top, I observed that the two copies with
nice 19 never used more than 2% CPU each, usually 1%.  The ones with
regular priority used 80-100% CPU, and it would have been higher
except that other processes were running.  And incidentally, I noticed
no UI lag in any of the other programs I had open (browser, IRC
clients, terminals) -- even the regular-priority processes using 100%
CPU didn't interfere with the UI.

OSes have got CPU prioritization down pretty well these days.  I don't
think we want to add features to work around bad OS thread scheduling
unless there's very specific and compelling evidence that it's an
issue.

> Also, I only want to do the processing on the second
> script if the user activates the feature. This is important on mobile now to
> reduce power consumption but is also important on desktops as CPUs become
> more power sensitive and JS payloads grow.

How much power would it take, in absolute terms, to parse and compile
even 1 MB of script?  Surely not enough to be noticeable if you're
only doing it a handful of times per day?  We aren't talking about a
scenario where people are downloading a megabyte of script every
minute or anything.  This would only be on large, complicated sites,
and if they're even slightly performance-optimized, it will only be
the first time you visit between cache clearing.  That shouldn't be
more than once or twice a day per site in the worst case, even with
small cache or aggressive cache-clearing.  I'd be very surprised if
this were a noticeable power drain, but I'd be interested to hear any
data you might have.

2011/5/25 Nicholas Zakas <nzakas at yahoo-inc.com>:
> I already explained that in my previous email. Parsing and compilation on a background thread removes some of the problem but not all of it. Ultimately, even if the script is just a function waiting to be called, the browser still executes it in a blocking fashion after parsing and compilation. It's the execution that is troublesome part because it interferes with the UI. The fact that the script isn't doing much is helpful, but once again, there will be a non-zero interrupt that can affect user experience.

What do you mean by "execution" here?  If the script is already
compiled, and you write it so that all it does is define a function,
then executing it should not take any measurable amount of time
(<1ms).  Currently this might not be observable, since if I understand
correctly, browsers don't separate compilation from execution.  But
with <script async> that's compiled on a background thread and
executed on the main thread, the execution itself should not be an
issue if all it does is expose a function.  Am I misunderstanding
something?

Received on Wednesday, 25 May 2011 17:05:40 UTC