JavaScript ES 模块的使用


Posted in Javascript onNovember 12, 2020

自从 ES 模块被添加到规范中后,JavaScript 中的模块就更加简单了。模块按文件分开,异步加载。导出是用 export 关键字定义的;值可以用 import 关键字导入。

虽然导入和导出单个值的基础知识非常容易掌握和使用,但还有许多其他方法可以使用 ES 模块来使你的导入和导出按照你需要的方式工作。在本文中,我将介绍你可以在模块中导出和导入的所有方法。

需要记住的一点是,导出和静态导入只能发生在模块的最外层。你不能从函数、if 语句或任何其他块中导出或静态导入。另外,动态导入可以在函数中完成,我们将在本文最后讨论它。

导出

默认导出

每个模块都有一个 "默认 "导出,它代表了模块导出的主要值。可能会有更多的导出值,但默认导出值代表模块的定义。一个模块中只能有一个默认导出。

const fruitBasket = new FruitBasket()

export default fruitBasket

注意,在默认导出之前,我必须先定义该值。如果我想,我也可以立即导出我的值,而不把它分配给一个变量,但这样我就不能在导出的同时将其赋值给一个变量。

我们可以默认导出一个函数声明和一个类声明,而不需要先把它分配给一个变量。

export default function addToFruitBasket(fruit) {
 // ...
}

我们甚至可以将字面值作为默认导出。

export default 123

命名导出

任何变量声明都可以在创建时导出,这将创建一个 "命名导出",使用变量名作为导出名。

export const fruitBasket = new FruitBasket()

我们还可以立即导出函数和类的声明。

export function addToFruitBasket(fruit) {
 // ...
}
export class FruitBasket {
 // ...
}

如果我们想导出一个已经定义好的变量,我们可以通过大括号把变量名包装为对象来实现。

const fruitBasket = new FruitBasket()

export { fruitBasket }

我们甚至可以使用 as 关键字来重命名我们的导出,使之与变量名不同。如果需要,我们还可以同时导出其他变量。

const fruitBasket = new FruitBasket()
class Apple {}

export { fruitBasket as basketOfFruit, Apple }

聚合导出

我们还会经常遇到这种情况,就是从一个模块导入模块,然后立即导出这些值。比如这样:

import fruitBasket from './fruitBasket.js'

export { fruitBasket }

当你要同时导入和导出很多东西时,这可能会变得很繁琐。ES 模块允许我们同时导入和导出多个值。

export * from './fruitBasket.js'

这将把 ./fruitBasket.js 中所有命名导出重新包装在一起再导出,但它不会导出默认导出值,因为一个模块只能有一个默认导出值。如果我们要导入和导出多个具有默认导出的模块,哪个值将成为导出模块的默认导出值呢?

我们可以专门从其他文件中导出默认模块,或者在重新导出时为默认导出命名。

export { default } from './fruitBasket.js'

// 或者

export { default as fruitBasket } from './fruitBasket.js'

我们也可以有选择地从另一个模块导出不同的项目,而不是把所有的项目都重新导出。在这种情况下,我们也使用大括号。

export { fruitBasket as basketOfFruit, Apple } from './fruitBasket.js'

最后,我们可以使用 as 关键字将整个模块打包成一个单独的命名导出。假设我们有以下文件:

// fruits.js
export class Apple {}
export class Banana {}

现在我们可以将其打包成一个单独的导出对象,这个对象包含了所有命名导出和默认导出对象。

export * as fruits from './fruits.js'
// { Apple: class Apple, Banana: class Banana }

导入

默认导入

当导入一个默认值时,我们需要给它指定一个名字。既然是默认值,我们给它取什么名字并不重要。

import fruitBasketList from './fruitBasket.js'

我们也可以同时导入所有的导出,包括命名导出和默认导出。这将会把所有的导出放到一个对象中,而默认导出将被赋予 "default "的属性名。

import * as fruitBasket from './fruitBasket.js'
// { default: fruitBasket }

命名导入

我们可以通过用大括号包装导出的名称来导入任何命名导出。

import { fruitBasket, Apple } from './fruitBasket.js'

我们也可以在导入时使用 as 关键字重命名导入。

import {fruitBasket as basketOfFruit, Apple} from './fruitBasket.js'

我们也可以在同一个导入语句中混合命名导出和默认导出。默认导出的内容会先列出,然后是大括号内的命名导出内容。

import fruitBasket, { Apple } from './fruitBasket.js'

副作用导入

有时候一个模块并没有导出值,我们只希望把该模块导入进来立即执行。导入这样的一个模块时,不需要在文件中列出任何导出值。这被称为”副作用(side-effect)“导入,它将直接执行模块中的代码而不提供任何导出值。

import './fruitBasket.js'

动态导入

有时我们在导入文件之前并不知道文件的名称。或者我们在执行代码到一半的时候才需要导入一个文件,我们可以使用动态导入在代码中的任何位置导入模块。之所以称之为 "动态",是因为导入的路径可能是不确定的,可以是字符串变量也可以是字符串表达式,而不像静态导入那样必须是一个字符串字面量。

由于 ES 模块是异步的,所以模块不会立即可用。我们必须等待它被加载后才能对它做事情。正因为如此,动态导入会返回一个解析模块的 Promise。

async function createFruit(fruitName) {
 try {
  const FruitClass = await import(`./${fruitName}.js`)
 } catch {
  console.error('Error getting fruit class module:', fruitName)
 }
 return new FruitClass()
}

总结

ES 导出的内容可以是值(包括变量和字面量)也可以是类和函数的声明,从导出方式上可以分为默认导出、命名导出和聚合导出。根据不同的导出方式,导入可以分为默认导入、命名导入、副作用导入和动态导入。命名导出和导入均可以使用 as 指定别名。​导出和静态导入必须在文件的最外层,动态导入可以在代码的函数中异步完成。

以上就是JavaScript ES 模块的使用的详细内容,更多关于JavaScript ES 模块的资料请关注三水点靠木其它相关文章!

Javascript 相关文章推荐
range 标准化之获取
Aug 28 Javascript
jquery使用jquery.zclip插件复制对象的实例教程
Dec 04 Javascript
jQuery中clone()方法用法实例
Jan 16 Javascript
js实现文本框宽度自适应文本宽度的方法
Aug 13 Javascript
js带缩略图的图片轮播效果代码分享
Sep 14 Javascript
基于javascript实现九宫格大转盘效果
May 28 Javascript
javascript HTML5文件上传FileReader API
Mar 27 Javascript
Bootstrap实现带动画过渡的弹出框
Aug 09 Javascript
详解Node项目部署到云服务器上
Jul 12 Javascript
AngularJS 打开新的标签页实现代码
Sep 07 Javascript
详解js实时获取并显示当前时间的方法
May 10 Javascript
swiper自定义分页器的样式
Sep 14 Javascript
在vue中给后台接口传的值为数组的格式代码
Nov 12 #Javascript
vue 解决provide和inject响应的问题
Nov 12 #Javascript
vue的$http的get请求要加上params操作
Nov 12 #Javascript
vue 获取url参数、get参数返回数组的操作
Nov 12 #Javascript
Vue+Spring Boot简单用户登录(附Demo)
Nov 12 #Javascript
vue 获取url里参数的两种方法小结
Nov 12 #Javascript
带你使用webpack快速构建web项目的方法
Nov 12 #Javascript
You might like
Apache2 httpd.conf 中文版
2006/12/06 PHP
字符串长度函数strlen和mb_strlen的区别示例介绍
2014/09/09 PHP
php从数组中随机选择若干不重复元素的方法
2015/03/14 PHP
php实现按天数、星期、月份查询的搜索框
2016/05/02 PHP
php版微信开发Token验证失败或请求URL超时问题的解决方法
2016/09/23 PHP
详解laravel安装使用Passport(Api认证)
2018/07/27 PHP
dojo 之基础篇(二)之从服务器读取数据
2007/03/24 Javascript
jQuery学习笔记(1)--用jQuery实现异步通信(用json传值)具体思路
2013/04/08 Javascript
JS禁用浏览器退格键实现思路及代码
2013/10/29 Javascript
JavaScript异步回调的Promise模式封装实例
2014/06/07 Javascript
DeviceOne 让你一见钟情的App快速开发平台
2016/02/17 Javascript
ASP.NET jquery ajax传递参数的实例
2016/11/02 Javascript
详解照片瀑布流效果(js,jquery分别实现与知识点总结)
2017/01/01 Javascript
JavaScript实现简单的树形菜单效果
2017/06/23 Javascript
JavaScript学习笔记之函数记忆
2017/09/06 Javascript
AngularJS 应用模块化的使用
2018/04/04 Javascript
微信小程序中限制激励式视频广告位显示次数(实现思路)
2019/12/06 Javascript
详解JavaScript自定义函数
2020/07/29 Javascript
Python编程修改MP3文件名称的方法
2017/04/19 Python
python ipset管理 增删白名单的方法
2019/01/14 Python
Python深拷贝与浅拷贝用法实例分析
2019/05/05 Python
详解pandas中MultiIndex和对象实际索引不一致问题
2019/07/23 Python
TensorFlow的环境配置与安装教程详解(win10+GeForce GTX1060+CUDA 9.0+cuDNN7.3+tensorflow-gpu 1.12.0+python3.5.5)
2020/06/22 Python
python 基于UDP协议套接字通信的实现
2021/01/22 Python
HTML5 通信API 跨域门槛将不再高、数据推送也不再是梦
2013/04/25 HTML / CSS
通过canvas转换颜色为RGBA格式及性能问题的解决
2019/11/22 HTML / CSS
工地资料员岗位职责
2013/12/31 职场文书
股权转让协议书
2014/04/12 职场文书
党员领导干部承诺书
2014/05/28 职场文书
小学学校门卫岗位职责
2014/08/03 职场文书
法人委托书范本格式
2014/09/15 职场文书
2014年工作总结及2015工作计划
2014/12/12 职场文书
Python+uiautomator2实现自动刷抖音视频功能
2021/04/29 Python
python+opencv实现视频抽帧示例代码
2021/06/11 Python
nginx共享内存的机制详解
2022/03/21 Servers
GoFrame基于性能测试得知grpool使用场景
2022/06/21 Golang