在浏览器上推迟脚本和执行顺序 [英] defer scripts and execution order on browsers

查看:116
本文介绍了在浏览器上推迟脚本和执行顺序的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我一直在为我的一个项目的HEAD部分中使用的外部脚本添加defer属性。我有一个查询多个延期脚本标签的执行顺序。



以下是我的观察结果,这将有助于我们更好地理解我的查询:

根据 http://www.w3.org/TR/html5/脚本1.html


defer属性存在,然后当页面完成解析时执行脚本

p>

defer属性确实有效。但是,我对执行顺序持怀疑态度。它看起来像FF和Chrome上的不同。



按照我的项目:

 < script defer =defersrc ={SERVER_PATH} /deps.js?1441452359>< / script> 
< script defer =defersrc ={SERVER_PATH} /script1.js?1440067073>< / script>
< script defer =defersrc ={SERVER_PATH} /script2.js?1441451916>< / script>

这里,deps.js是大约120kb的大文件(gzipped),而script1-3是(gzipped)。

在Firefox上,执行延期脚本确实按照外观顺序启动,但不完全相同订购。因为,除非前面的脚本完成执行,否则在Chrome上,下一个脚本的执行无法启动。它看起来像Chrome是有道理的。为了测试执行顺序,我在每个脚本的第一行和最后一行插入了console.log,例如, in deps.js

  console.log(Execution Start:deps); 
//缩小代码脚本内容。
console.log(Execution End:deps);

在Firefox的控制台输出之下:

 执行开始:deps 
执行开始:script1
执行开始:script2
// Script脚本错误,因为script1需要deps才能完全呈现。
//脚本错误,因为script2需要完全渲染。
执行结束:deps

在Chrome上的控制台输出之下:

$ b执行开始:deps
执行结束:deps
执行开始:script1
执行结束:脚本1
执行开始:开始
执行开始:开始
执行开始:执行开始:script2
执行结束:script2

然而,FF上的行为并不总是如上所示。有时它确实像Chrome一样工作。它看起来像一个只有Firefox的问题。或者,可能是因为deps.js文件很重并且缩小了,并且需要时间来渲染。



任何具有推迟的类似经验的人能帮助我吗?请让我知道,如果有任何其他信息是必要的。



PS:其他解决方案,如移动页面底部的脚本不是我在看这个。

解决方案

HTML5.0规范说明了这一点:


如果元素具有src属性,并且元素具有defer属性,并且该元素已被标记为解析器插入的,并且该元素没有async属性



必须将元素添加到脚本列表的末尾,当文档完成与创建该元素的解析器的Document关联的解析时,脚本列表将执行。



网络任务源放置在任务队列中的任务一旦完成获取算法,必须设置元素的准备好解析器执行标志。解析器将处理执行脚本。


所以它确实表示它延迟脚本执行,直到关联的 Document 被解析,它也表示它被推入列表中。因此,列表的顺序应该是脚本顺序正在被解析 - 插入。



然而,第二部分有点担心我。它基本上说它只会被标记为执行,直到网络任务完成下载脚本。然后......解析器将处理执行脚本。



在规范中找不到的是覆盖文档解析后脚本执行的情况。当它们准备好解析器执行时,它是否按照列表顺序执行脚本?或者等到列表中的所有脚本准备好解析器执行然后执行它们。



规格(步骤15): http://www.w3.org/TR/html5/scripting-1。 html#script-processing-src-prepare


I have been working on adding defer attribute for external scripts used in HEAD section of one of my projects. I had a query on execution order of multiple defer'ed script tags.

Below are my observation which will help us understand my query better:

As per http://www.w3.org/TR/html5/scripting-1.html

the defer attribute is present, then the script is executed when the page has finished parsing

The defer attribute does work. But, I am doubtful on the execution order. It looks like it is different on FF and Chrome.

As per my porject:

<script defer="defer" src="{SERVER_PATH}/deps.js?1441452359"></script>
<script defer="defer" src="{SERVER_PATH}/script1.js?1440067073"></script>
<script defer="defer" src="{SERVER_PATH}/script2.js?1441451916"></script>

Here, deps.js is huge file of around 120kb (gzipped), whereas, script1-3 are of regular size of 20-50kb (gzipped).

On Firefox, execution of defer'ed script does start in order of appearance, but doesn't complete in the same order. Where'as, on chrome unless the previous script completes execution, the next script's execution doesn't start. It looks like Chrome makes sense.

To test the execution order, I had inserted console.log at the first and last line of each scripts, for e.g. in deps.js

console.log("Execution Start: deps");
// minified deps script content.
console.log("Execution End: deps");

Below the console output on Firefox:

Execution Start: deps
Execution Start: script1
Execution Start: script2
// Script Error as script1 needs deps to render completely.
// Script Error as script2 needs deps to render completely.
Execution End: deps

Below the console output on Chrome:

Execution Start: deps
Execution End: deps
Execution Start: script1
Execution End: script1
Execution Start: script2
Execution End: script2

However, behavior on FF is not always as shown above. Sometimes it does work like Chrome. It look like an issue which is Firefox only. Or, may be is it because of the deps.js file being heavy and minified and takes time to render.

Can anyone of similar experience with defer help me? Please let me know, if any other information is needed.

PS: Other solutions like, moving the scripts at the bottom of the page is not something I am looking at this moment.

解决方案

HTML5.0 spec says this:

If the element has a src attribute, and the element has a defer attribute, and the element has been flagged as "parser-inserted", and the element does not have an async attribute

The element must be added to the end of the list of scripts that will execute when the document has finished parsing associated with the Document of the parser that created the element.

The task that the networking task source places on the task queue once the fetching algorithm has completed must set the element's "ready to be parser-executed" flag. The parser will handle executing the script.

So it does say it defers script execution until the associated Document is parsed, it also says it's pushed into the list. So the order of the list should be as the script order is being parsed-inserted.

However, the second part kind of worries me. It basically says that it will only be marked for execution until the network task finsihed downloading the script. Then... "parser will handle executing the script".

What I couldn't find in the spec is the case covering script execution after document parsing. Does it keep executing scripts in the list order as they become "ready to be parser-executed"? Or will it wait until all scripts in the list are "ready to be parser executed" then execute them.

Spec (step 15): http://www.w3.org/TR/html5/scripting-1.html#script-processing-src-prepare

这篇关于在浏览器上推迟脚本和执行顺序的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆