import函数
- 通过import加载一个模块,是不可以在其放到逻辑代码中的,比如:
- 为什么会出现这个情况呢?
- 这是因为ES Module在被JS引擎解析时,就必须知道它的依赖关系;
- 由于这个时候js代码没有任何的运行,所以无法在进行类似于if判断中根据代码的执行情况;
- 甚至下面的这种写法也是错误的:因为我们必须到运行时能确定path的值;
- 但是某些情况下,我们确确实实希望动态的来加载某一个模块:
- 如果根据不懂的条件,动态来选择加载模块的路径;
- 这个时候我们需要使用 import() 函数来动态加载;
import meta
- import.meta是一个给JavaScript模块暴露特定上下文的元数据属性的对象。
- 它包含了这个模块的信息,比如说这个模块的URL;
- 在ES11(ES2020)中新增的特性;
代码演示
// import { name, age, foo } from './foo.js' // console.log(name) // import函数返回的结果是一个Promise import("./foo.js").then(res => { console.log("res:", res.name) }) console.log("后续的代码都是不会运行的~") // ES11新增的特性 // meta属性本身也是一个对象: { url: "当前模块所在的路径" } console.log(import.meta)
ES Module的解析流程
- ES Module的解析过程可以划分为三个阶段:
- 阶段一:构建(Construction),根据地址查找js文件,并且下载,将其解析成模块记录(Module Record);
- 阶段二:实例化(Instantiation),对模块记录进行实例化,并且分配内存空间,解析模块的导入和导出语句,把模块指向 对应的内存地址。
- 阶段三:运行(Evaluation),运行代码,计算值,并且将值填充到内存地址中;
代码演示
// foo.js let name = "why" let age = 18 setTimeout(() => { name = "kobe" age = 40 }, 100) export { name, age } // main.js import { name, age } from './foo.js' console.log(name, age) setTimeout(() => { console.log(name, age) }, 2000) // index.html <html lang="en"><head> <meta charset="UTF-8"> <title>Document</title> </head> <body> <script src="./main.js" type="module"></script> </body></html>
执行结果为:why 18