什么是模块
一个模块就是一个文件,一个脚本就是一个模块 模块之间可以相互加载
export 关键字标记了可以从当前模块外部访问的变量和函数。 import 关键字允许从其他模块导入功能。
export function sayHi ( user) {
alert ( `Hello, ${ user} !` ) ;
}
// 📁 main.html
<!doctype html>
< script type = " module" >
import { sayHi} from './say.js' ;
document. body. innerHTML = sayHi ( 'John' ) ;
</ script>
核心模块功能
始终使用"use strict" 模块级作用域:每个模块都有自己独立的作用域 hello.js 尝试使用在 user.js 中声明的变量 user,失败了:
#index.html
<!doctype html>
< script type = " module" src = " user.js" > </ script>
< script type = " module" src = " hello.js" > </ script>
let user = "John" ;
alert ( user) ;
在浏览器中,每个 <script type="module">
也存在独立的顶级作用域
< script type= "module" >
let user = "John" ;
< / script>
< script type= "module" >
alert ( user) ;
< / script>
模块代码仅在第一次导入时被解析 如果在某个位置修改了导入的代码,那么其它的模块也可以看到就这个修改(包含源文件)
alert ( "Module is evaluated!" ) ;
import `./alert.js` ;
import `./alert.js` ;
import.meta
对象包含关于当前模块的信息 它的内容取决于其所在的环境。在浏览器环境中,它包含当前脚本的 URL,或者如果它是在 HTML 中的话,则包含当前页面的 URL。
< script type= "module" >
alert ( import . meta. url) ;
< / script>
< script>
alert ( this ) ;
< / script>
< script type= "module" >
alert ( this ) ;
< / script>
浏览器特定功能
下载外部模块脚本 <script type="module" src="...">
不会阻塞 HTML 的处理,它们会与其他资源并行加载。 模块脚本会等到 HTML
文档完全准备就绪(即使它们很小并且比 HTML
加载速度更快),然后才会运行。 保持脚本的相对顺序:在文档中排在前面的脚本先执行。
< script type= "module" >
alert ( typeof button) ;
< / script>
< script>
alert ( typeof button) ;
< / script>
< button id= "button" > Button< / button>
< ! -- 所有依赖都获取完成(analytics. js)然后脚本开始运行 -- >
< ! -- 不会等待 HTML 文档或者其他 < script> 标签 -- >
< script async type= "module" >
import { counter} from './analytics.js' ;
counter. count ( ) ;
< / script>
具有相同 src 的外部脚本仅运行一次
< ! -- 脚本 my. js 被加载完成(fetched)并只被运行一次 -- >
< script type= "module" src= "my.js" > < / script>
< script type= "module" src= "my.js" > < / script>
从另一个源(例如另一个网站)获取的外部脚本需要 CORS header,如我们在 Fetch:跨源请求 一章中所讲的那样。换句话说,如果一个模块脚本是从另一个源获取的,则远程服务器必须提供表示允许获取的 header Access-Control-Allow-Origin
< ! -- another- site. com 必须提供 Access- Control- Allow- Origin -- >
< ! -- 否则,脚本将无法执行 -- >
< script type= "module" src= "http://another-site.com/their.js" > < / script>
不允许裸模块 在浏览器中,import 必须给出相对或绝对的 URL 路径
import { sayHi} from 'sayHi' ;
< script type= "module" >
alert ( "Runs in modern browsers" ) ;
< / script>
< script nomodule>
alert ( "Modern browsers know both type=module and nomodule, so skip this" )
alert ( "Old browsers ignore script with unknown type=module, but execute this." ) ;
< / script>