在底部呈现阻塞延迟与移动脚本

Render blocking defer vs moving script at bottom

I assume moving script at bottom is same as using defer or async attribute. Since defer and async are not fully legacy browser compliant, I gone with loading script at the bottom of the page.

<html>
<body>
<!-- whole block of html -->
<script type='text/javascript' src='app.js'></script>
</body>
</html>

Before doing this, I ran performance benchmark tools like GTmetrix and Google PageSpeed insight. Both shown 'render blocking' parameter as the main problem. I am bit confused now, as even after I moving these scripts at the bottom to allow content/html to load first; these tools still report render blocking as a main problem.

我确实看过其他 Whosebug 帖子,强调尽管在 底部加载的脚本必须具有 'defer' 属性。

我有几个问题:

  1. 以上是真的吗?
  2. 这些工具是否专门寻找 'defer' 或 'async' 属性?
  3. 如果我必须提供回退 w.r.t 延迟(专门针对 IE 浏览器),我是否需要使用条件语句来加载 IE 的非延迟脚本?

请提出最佳方法。提前谢谢你。

而不是 async,也许是这样的(感谢 @guest271314 的想法)

<!DOCTYPE html>
<html>
<body>
<!-- whole block of  html -->

<!-- inline scripts can't have async -->
<script type='text/javascript'>
function addScript(url){
document.open();
document.write("<scrip" + "t src = \"" + url + "\"></scr" + "ipt>");//weird quotes to avoid confusing the HTML parser
document.close();
}
//add your app.js last to ensure all libraries are loaded
addScript("jquery.js");
addScript("lodash.js");
addScript("app.js");
</script>
</body>
</html>

这是你想要的吗?如果需要,您可以在 document.write 调用中添加 asyncdefer 属性。

根据 HTML 规范 1.1 html 页面中的脚本块将阻止页面呈现,直到 url 中的 javascript 文件被下载并处理。

在页面末尾添加脚本:允许浏览器继续页面渲染,因此用户将能够尽快看到页面渲染。

[Preferred] 添加 defer 到脚本标签:向浏览器承诺该脚本不包含任何 document.write 或文档更改代码,因此允许它继续渲染。

之前的帖子可能对您有用

Is it necessary to put scripts at the bottom of a page when using the "defer" attribute?

  1. 是的,即使在底部加载的脚本也必须具有 defere 属性,如果在您的网站设计和要求中可能的话

  2. 不是,那些工具寻找解析完成

  3. 取决于你要支持的IE版本,他们会有不同的推荐

现在简单解释一下scriptdeferasync,帮助大家理解原因:

脚本 简单 <script> 标记将在该点停止解析,直到脚本 downloadexecutes.

异步 如果您将使用 async,那么脚本将不会停止解析下载,因为它将继续与其余 html 内容并行下载。但是,脚本将停止对 执行 的解析,然后 html 的解析才会继续或完成

推迟 如果您使用 defer,脚本将不会停止解析 html 数据以下载或执行脚本。因此,这是避免任何时间增加网页加载时间的最佳方法。

请注意,延迟有利于减少 html 的解析时间,但并不总是适合每个网页设计流程,因此在使用时要小心。

为什么最后提到的脚本一定要有defer属性?

答案是,通过向最后一个脚本添加延迟,您实际上减少了在绘制页面之前需要加载的关键资源的数量,从而减少了关键渲染路径。

是的,当你到达最后一个时你是正确的 DOM 被解析但是浏览器还没有开始绘制 DOM 因此 domContentLoadedEvent 被阻止直到它完成绘画和渲染 activity.

通过添加 async/defer,我们告诉浏览器该资源对于呈现并不重要,可以在 dom 内容加载后加载和执行。 这将更早地触发 domContentLoaded 事件,并且 domContentLoaded 事件越早触发,其他应用程序逻辑就可以越早开始执行。

参考下面的google link,它清楚地展示了这个概念。 https://developers.google.com/web/fundamentals/performance/critical-rendering-path/analyzing-crp