async/defer 执行顺序全解析:从面试坑到 MDN 标准

前言

之前面试问的比较细,问资源提示符,问到了async和defer的执行顺序的问题,被卡住了,今天专门查了下MDN和HTML标准文档,整理了一下,也分享出来,希望对大家有用

基本作用

简单带过一下基本作用

  • async: 让js在下载后立即执行,下载过程不阻塞HTML解析(下载过程是异步)
  • defer: 让js在下载后先不执行,在dom解析完成后,但在触发 DOMContentLoaded 事件之前执行。下载过程不阻塞HTML解析(下载过程是异步)

执行顺序

首先有个属性的覆盖问题

特殊属性

blocking: script 标签的 blocking 属性是 render 的时候,会让js下载完之后立即执行且下载和执行都可能会阻塞渲染但是不会阻塞HTML解析,因为需要等脚本执行了才能开始渲染

async和defer之间的属性优先级

(在当前浏览器支持async的情况下)

根据HTML标准文档 : 如果一个普通标签同时有async和defer,那么async会覆盖defer
(在当前浏览器只支持defer不支持async的情况下)

根据HTML标准文档 : 当前标签同时有defer和async,则会支持defer

内联脚本

内联脚本就是没有设置src的script标签,你写的内联的js

根据MDN描述:内联脚本对 async 和 defer 都不生效

正常情况下的执行顺序逻辑

我简化一下情况,好进行描述,正常情况就是没有上面说的这些情况:

1.无特殊属性;2.一个标签只有defer或者async;3.浏览器两个都支持;4.有src

经典脚本

根据MDN文档:

async因为都是并发的,所以执行相对顺序不确定 ,下载完就会立即执行

defer是下载是并发,但是执行是在DOMContentLoaded事件之前,defer标签之间相对顺序是按照标签的顺序 来的,所以defer标签之间可以有依赖

模块脚本

就是<script type="module"></script>

根据 HTML标准文档:

  • 在模块脚本中,defer没有用
  • 在模块脚本中,加了async,那么也是并行下载,但是不止是当前脚本,而是当前脚本依赖的其他js都会进行并行下载并在下载完成之后执行
相关推荐
之歆13 小时前
Day07_CSS盒子模型 · 样式继承 · 用户代理样式
前端·css
01漫游者13 小时前
JavaScript函数与对象增强知识
开发语言·javascript·ecmascript
DanCheOo14 小时前
AI 应用的安全架构:Prompt 注入、数据泄露、权限边界
前端·人工智能·prompt·安全架构
We་ct15 小时前
深度剖析浏览器跨域问题
开发语言·前端·浏览器·跨域·cors·同源·浏览器跨域
weixin_4277716115 小时前
前端调试隐藏元素
前端
threelab15 小时前
Three.js 代码云效果 | 三维可视化 / AI 提示词
开发语言·javascript·人工智能
爱上好庆祝16 小时前
学习js的第五天
前端·css·学习·html·css3·js
C澒16 小时前
IntelliPro 产研协作平台:基于 AI Agent 的低代码智能化配置方案设计与实现
前端·低代码·ai编程
一袋米扛几楼9816 小时前
【Git】规范化协作:详解 GitHub 工作流中的 Issue、Branch 与 Pull Request 最佳实践
前端·git·github·issue
网络点点滴17 小时前
前端与后端的区别与联系
前端