uglify-esでの「ES6対応」の意味


UglifyESを使おうとしたら、ちょっと想定外だったことがありました。

uglify-jsuglify-es

JavaScriptをminifyするソフトウェアとしてUglifyJSが有名ですが、npmからuglify-jsとして入れると、ES5専用のものが入ってしまうので、ES6の構文があるとエラーになります。

従来のUglifyJSとは別ブランチで、ES6対応版の開発が進んでいますが、こちらはnpmにuglify-esという名前で登録されています。

Webpackからの利用

WebpackにもUglifyJSを使うプラグイン(webpack.optimize.UglifyJsPlugin)が標準で添付されていますが、Webpack 3の時点では、標準添付版はuglify-jsを呼び出す仕様となっています。uglify-esを使いたい場合、別にuglifyjs-webpack-pluginのVer.1系列を入れる必要があります(なお、Webpack 4では標準添付版もuglify-es使用に切り替える予定とのことです)。

バージョン対応の意味

そして、babelの設定もenv標準にしてES5への強制変換を止め(もっとも、IE11も対象なので、残るのはletconstぐらいでしょうが)、その他を色々書き換えながらチェックしていたところ、IE11でコードが動かなくなってしまいました。確認してみると、アロー関数がそのまま吐き出されてしまっていました。

「デフォルトではuglify-esの入力はES2017、出力はES5だったのにおかしいな」と思い、uglify-esのドキュメントを確認していたところで、真相が判明しました。

The ecma option will only change the output in direct control of the beautifier. Non-compatible features in the abstract syntax tree will still be output as is. For example: an ecma setting of 5 will not convert ES6+ code to ES5. (強調も原文ママ)

ということで、ES6で来たコードは、(uglify-esで圧縮変換されない限り)ES6のままで出力されてしまうのです。もちろん、事前にbabelで適切な形に変換してあれば問題はないのですが、ちょうどES6で書いてあったモジュールをimportしようとした(&node-modulesはbabelから除外していた)こともあって、そのまま出力まで素通りした、ということでした。

関連記事