如果你有在使用 babel 转换 ES6 代码或者使用了 @babel/preset-env,那么你可能会遇到一个问题——在转换后的代码中出现了“Promise 未定义”的错误。这篇文章将会逐步地介绍它出现的原因,并提供一个解决方案。
问题的来源
首先,我们需要了解 ES6 是在哪个版本中引入的 Promise。在 ES6 标准中,Promise 是被引入为原生对象的一个组件。但是在像 IE11 这样的一些旧浏览器中,并不支持 Promise,这就导致了一些问题。
在使用 @babel/preset-env 将代码转换为 ES5 的时候,它会将 Promise 转换为 ES5 格式的代码。但是我们需要注意的是,此时 Promise 是使用一个名为 babel-runtime 的库来实现的,而且使用了从 Promise A+ 提案中摘取出的 es6-promise 库来兼容旧浏览器。
问题就在这里,因为这里生成的 Promise 被定义在 @babel/polyfill 库的一个命名空间下(polyfill 是一个将新标准引入到旧环境中的库),所以在转换后的代码中,没有了 Promise 这个全局对象。
正因为这个原因,当我们使用文档中给出的代码示例时,会导致 Promise 的错误。下面是一个出现这个问题的代码示例:
const promise = new Promise(() => {});
解决方案
为了解决这个问题,我们需要在转换后的代码中引入 polyfill 库。这个库是一个依赖 babel-runtime 的库,它将定义在全局名称空间下的变量和函数引入到转换后的代码中。
我们可以使用 @babel/polyfill 这个库来引入我们所需的示例代码。我们可以通过 ES6 的 import 语句来引入这个库:
import '@babel/polyfill';
这个 import 语句会引入我们需要的库,并将它们添加到全局名称空间中。这样做之后,上面的代码就可以正常地运行了。
import '@babel/polyfill'; const promise = new Promise(() => {});
总结
在这篇文章中,我们发现了一个在使用 @babel/preset-env 转换代码时可能会遇到的问题——Promise 未定义。我们了解了这个问题的来源,也提供了一个解决方案。如果你是在编写需要支持旧浏览器的前端代码时,这个问题可能会经常出现,因此我们需要谨慎处理。
来源:JavaScript中文网 ,转载请注明来源 https://www.javascriptcn.com/post/64b2460148841e9894e8ae33