From 2686f47baad44fc17a8526ef38946159dc677749 Mon Sep 17 00:00:00 2001 From: Frankie Dintino Date: Thu, 23 Aug 2018 02:56:01 -0400 Subject: [PATCH] Use uglify-es to support minification of more permissive babel presets Currently, only ES5 javascript can be minified, due to the reliance on uglify-js. With uglify-es (the harmony branch of UglifyJS2) it is possible to support a broader range of javascript syntax. The API changed between uglify-js@2 and uglify-js@3 / uglify-es, but the translation to the new API was fairly straightforward. It hews more closely to the original code than #815, and consequently I think it avoids regressing any features (for instance, the ability to include sourceContents in source maps or to control the comment stripping. As browsers continue to support more features beyond ES5, and because babel recommends use of the 'env' preset, it will become increasingly likely that users' babel transpilation settings will cause errors when trying to minify with jspm and friends. refs #815, #726 --- lib/output.js | 39 ++++++++++++++++++++++----------------- package.json | 2 +- test/test-sfx.html | 3 +-- 3 files changed, 24 insertions(+), 20 deletions(-) diff --git a/lib/output.js b/lib/output.js index 777ee3e..32b2c75 100644 --- a/lib/output.js +++ b/lib/output.js @@ -8,6 +8,17 @@ var extend = require('./utils').extend; var fromFileURL = require('./utils').fromFileURL; var toFileURL = require('./utils').toFileURL; +// Ugly hack (no pun intended) to get around uglify-js strange code loading +// and export system, and the fact that their SourceMap wrapper is no longer +// exported in uglify-js@3 / uglify-es +var UglifySourceMap = new Function('MOZ_SourceMap', function() { + var code = ['uglify-es/lib/utils.js', 'uglify-es/lib/sourcemap.js'].map(function(file) { + return fs.readFileSync(require.resolve(file), 'utf8'); + }); + code.push('return SourceMap;'); + return code.join('\n'); +}())(require('source-map')); + function countLines(str) { return str.split(/\r\n|\r|\n/).length; } @@ -72,36 +83,30 @@ function createOutput(outFile, outputs, basePath, sourceMaps, sourceMapContents) } function minify(output, fileName, mangle, uglifyOpts) { - var uglify = require('uglify-js'); + var uglify = require('uglify-es'); + var files = {}; + files[fileName] = output.source; var ast; try{ - ast = uglify.parse(output.source, { filename: fileName }); + ast = uglify.minify(files, { + parse: {}, + compress: false, + mangle: mangle, + output: { ast: true, code: false } + }).ast; } catch(e){ throw new Error(e); } - ast.figure_out_scope(); - - ast = ast.transform(uglify.Compressor(uglifyOpts.compress)); - ast.figure_out_scope(); - if (mangle !== false) - ast.mangle_names(); var sourceMap; if (output.sourceMap) { if (typeof output.sourceMap === 'string') output.sourceMap = JSON.parse(output.sourceMap); - var sourceMapIn = output.sourceMap; - sourceMap = uglify.SourceMap({ + sourceMap = UglifySourceMap({ file: fileName, - orig: sourceMapIn + orig: output.sourceMap }); - - if (uglifyOpts.sourceMapIncludeSources && sourceMapIn && Array.isArray(sourceMapIn.sourcesContent)) { - sourceMapIn.sourcesContent.forEach(function(content, idx) { - sourceMap.get().setSourceContent(sourceMapIn.sources[idx], content); - }); - } } var outputOptions = uglifyOpts.beautify; diff --git a/package.json b/package.json index 14e7360..7aba5a1 100644 --- a/package.json +++ b/package.json @@ -20,7 +20,7 @@ "source-map": "^0.5.3", "systemjs": "^0.19.46", "traceur": "0.0.105", - "uglify-js": "^2.6.1" + "uglify-es": "^3.3.9" }, "devDependencies": { "babel": "^5.8.38", diff --git a/test/test-sfx.html b/test/test-sfx.html index 36f4f84..2374570 100644 --- a/test/test-sfx.html +++ b/test/test-sfx.html @@ -6,13 +6,12 @@