在需要时使用Native ES6和Transpiling

时间:2015-06-02 02:00:21

标签: javascript ecmascript-6 fallback

是否有某种方法(使用grunt,gulp,普通JS,节点模块等)来执行以下操作。

以JS文件为输入,根据浏览器当前对ES6功能的支持构建一系列特定于浏览器的文件,并转换尚未支持的功能。

我希望使用可用时可用的ES6功能,并将那些不属于ES5的功能转换为ES5。

另外,对于我们这些有幸处理旧版浏览器(例如IE9,IE10,很快就会成为IE11)的人来说,除了转换我永远写的所有JS之外,还需要一些处理它们的过程。最终:)。

1 个答案:

答案 0 :(得分:3)

你显然意味着为不同的浏览器提供单独的构建,根据某种用户代理嗅探,您可能会提供这些构建,或者在浏览器端功能检测后动态加载。这听起来很复杂且容易出错。随着新浏览器版本的推出,您还需要不断重建特定于浏览器的版本,例如支持胖箭头的Chrome版本。

您要解决的问题是什么?你相信原生实现会更快吗?这是可能的,但不一定如此,如果存在差异,则可能是最小的。您是否担心有效负载大小,因为ES6语法通常更简洁?一旦JS被缩小和压缩,这种差异也可能是微不足道的。我宁愿在所有浏览器中运行相同的ES5转换代码,并且避免必须追踪奇怪的错误,其中某个浏览器支持某个ES6功能,你认为这会让你避免转换,结果是不稳定的

我会给你一个具体的例子。假设您确定为节点编译的代码不需要转换胖箭头,因为您听说该节点使用--harmony标志支持它们。所以你写了

var foo = {
  x: 42,
  bar: function() { setTimeout(() => console.log(this.x)); }
};  
foo.bar();

但是你发现该节点不支持胖箭头函数中this的词汇化:

> node --harmony test.js
< undefined

难道你不想让像babel这样的转录器可靠地将其转换为正确的ES5吗?

var foo = {
  x: 42,
  g: function g() {
    var _this = this;
    setTimeout(function () {
      return console.log(_this.x);
    });
  }
};

> babel-node test.js
< 42

一旦您感到满意,您想要支持的所有浏览器都实现了特定的ES6功能,那么大多数浏览器都会提供逐个功能的标记,让您可以告诉它跳过它。

您的提案的修改版本将包含两个版本,一个完全转换,一个非转换为具有完整ES6支持的浏览器。这样可以避免在后一种情况下包含转换器的运行时(例如babel的browser-polyfill.js)。但是,它也会阻止你利用babel对ES7功能的支持,其中一些非常有用,例如异步功能。