diff --git a/lib/minify.js b/lib/minify.js index a827930a..8dd3e5aa 100644 --- a/lib/minify.js +++ b/lib/minify.js @@ -57,6 +57,7 @@ function minify(files, options) { keep_fnames: false, properties: false, reserved: [], + safari10: false, toplevel: false, }, true); } diff --git a/lib/scope.js b/lib/scope.js index fc63f51d..70ea879e 100644 --- a/lib/scope.js +++ b/lib/scope.js @@ -102,6 +102,7 @@ AST_Toplevel.DEFMETHOD("figure_out_scope", function(options){ options = defaults(options, { cache: null, ie8: false, + safari10: false, }); // pass 1: setup scope chaining and handle definitions @@ -112,6 +113,7 @@ AST_Toplevel.DEFMETHOD("figure_out_scope", function(options){ var in_destructuring = null; var in_export = false; var in_block = 0; + var for_scopes = []; var tw = new TreeWalker(function(node, descend){ if (node.is_block_scope()) { var save_scope = scope; @@ -122,6 +124,11 @@ AST_Toplevel.DEFMETHOD("figure_out_scope", function(options){ scope.uses_eval = save_scope.uses_eval; scope.directives = save_scope.directives; } + if (options.safari10) { + if (node instanceof AST_For || node instanceof AST_ForIn) { + for_scopes.push(scope); + } + } descend(); scope = save_scope; return true; @@ -303,6 +310,19 @@ AST_Toplevel.DEFMETHOD("figure_out_scope", function(options){ })); } + // pass 4: add symbol definitions to loop scopes + // Safari/Webkit bug workaround - loop init let variable shadowing argument. + // https://github.com/mishoo/UglifyJS2/issues/1753 + // https://bugs.webkit.org/show_bug.cgi?id=171041 + if (options.safari10) { + for (var i = 0; i < for_scopes.length; i++) { + var scope = for_scopes[i]; + scope.parent_scope.variables.each(function(def) { + push_uniq(scope.enclosed, def); + }); + } + } + if (options.cache) { this.cname = options.cache.cname; } diff --git a/test/compress/harmony.js b/test/compress/harmony.js index ca36d2ea..f921cfcf 100644 --- a/test/compress/harmony.js +++ b/test/compress/harmony.js @@ -424,3 +424,61 @@ issue_1898: { new Foo().bar(); } } + +issue_1753: { + mangle = { safari10: true }; + input: { + class SomeClass { + constructor(props) { + let pickedSets = []; + for (let i = 0; i < 6; i++) { + pickedSets.push({ + mainDrawNumbers: [], + extraDrawNumbers: [] + }); + } + } + } + } + expect: { + class SomeClass { + constructor(r) { + let a = []; + for (let s = 0; s < 6; s++) + a.push({ + mainDrawNumbers: [], + extraDrawNumbers: [] + }); + } + } + } +} + +issue_1753_disable: { + mangle = { safari10: false } + input: { + class SomeClass { + constructor(props) { + let pickedSets = []; + for (let i = 0; i < 6; i++) { + pickedSets.push({ + mainDrawNumbers: [], + extraDrawNumbers: [] + }); + } + } + } + } + expect: { + class SomeClass { + constructor(r) { + let a = []; + for (let r = 0; r < 6; r++) + a.push({ + mainDrawNumbers: [], + extraDrawNumbers: [] + }); + } + } + } +}