aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorAlex Lam S.L <alexlamsl@gmail.com>2020-12-24 23:31:34 +0000
committerGitHub <noreply@github.com>2020-12-25 07:31:34 +0800
commitced32f9bd87e3fdc693412d1bdc924a99ecc9712 (patch)
treebc4123b8e75613971375c7bcd4d6bda348abed7c
parentdfc3ec9cef2f8dad08471cf636f52387045b342d (diff)
downloadtracifyjs-ced32f9bd87e3fdc693412d1bdc924a99ecc9712.tar.gz
tracifyjs-ced32f9bd87e3fdc693412d1bdc924a99ecc9712.zip
enhance `default_values` (#4450)
-rw-r--r--lib/compress.js157
-rw-r--r--test/compress/default-values.js64
2 files changed, 154 insertions, 67 deletions
diff --git a/lib/compress.js b/lib/compress.js
index 2c1f87d1..a6615773 100644
--- a/lib/compress.js
+++ b/lib/compress.js
@@ -3361,6 +3361,7 @@ merge(Compressor.prototype, {
return this.consequent.is_defined(compressor) && this.alternative.is_defined(compressor);
});
def(AST_Constant, return_true);
+ def(AST_Hole, return_false);
def(AST_Lambda, return_true);
def(AST_Object, return_true);
def(AST_Sequence, function(compressor) {
@@ -5566,71 +5567,7 @@ merge(Compressor.prototype, {
node.definitions.forEach(function(def) {
if (def.value) def.value = def.value.transform(tt);
if (def.name instanceof AST_Destructured) {
- var value = def.value;
- var trimmer = new TreeTransformer(function(node) {
- if (node instanceof AST_DefaultValue) return trim_default(tt, trimmer, node);
- if (node instanceof AST_DestructuredArray) {
- var save = value;
- if (value instanceof AST_SymbolRef) value = value.fixed_value();
- var values = value instanceof AST_Array && value.elements;
- var elements = [];
- node.elements.forEach(function(element, index) {
- if (element instanceof AST_Hole) return;
- value = values && values[index];
- element = element.transform(trimmer);
- if (element) elements[index] = element;
- });
- value = save;
- if (values && elements.length == 0) return null;
- for (var i = elements.length; --i >= 0;) {
- if (!elements[i]) elements[i] = make_node(AST_Hole, node.elements[i] || node);
- }
- node.elements = elements;
- return node;
- }
- if (node instanceof AST_DestructuredObject) {
- var save = value;
- if (value instanceof AST_SymbolRef) value = value.fixed_value();
- var values;
- if (value instanceof AST_Object) {
- values = Object.create(null);
- for (var i = 0; i < value.properties.length; i++) {
- var prop = value.properties[i];
- if (typeof prop.key != "string") {
- values = null;
- break;
- }
- values[prop.key] = prop.value;
- }
- }
- var properties = [];
- node.properties.forEach(function(prop) {
- var retain;
- if (prop.key instanceof AST_Node) {
- prop.key = prop.key.transform(tt);
- value = null;
- retain = prop.key.has_side_effects(compressor);
- } else {
- value = values && values[prop.key];
- retain = false;
- }
- if (retain && is_decl(prop.value)) {
- properties.push(prop);
- } else {
- var newValue = prop.value.transform(trimmer);
- if (newValue) {
- prop.value = newValue;
- properties.push(prop);
- }
- }
- });
- value = save;
- if (properties.length == 0 && value && !value.may_throw_on_access(compressor)) {
- return null;
- }
- node.properties = properties;
- return node;
- }
+ var name = trim_destructured(def.name, def.value, function(node) {
if (node instanceof AST_SymbolDeclaration) {
if (!drop_vars) return node;
if (node.definition().id in in_use_ids) return node;
@@ -5639,11 +5576,10 @@ merge(Compressor.prototype, {
return null;
}
});
- var name = def.name.transform(trimmer);
if (name) {
flush();
} else {
- value = value.drop_side_effect_free(compressor);
+ var value = def.value.drop_side_effect_free(compressor);
if (value) side_effects.push(value);
}
return;
@@ -5807,6 +5743,17 @@ merge(Compressor.prototype, {
}
return insert_statements(body, node, in_list);
}
+ if (node instanceof AST_Assign) {
+ descend(node, tt);
+ if (node.left instanceof AST_Destructured) {
+ var lhs = trim_destructured(node.left, node.right, function(node) {
+ if (node instanceof AST_SymbolRef) return node;
+ });
+ if (!lhs) return node.right;
+ node.left = lhs;
+ }
+ return node;
+ }
if (node instanceof AST_LabeledStatement && node.body instanceof AST_For) {
// Certain combination of unused name + side effect leads to invalid AST:
// https://github.com/mishoo/UglifyJS/issues/1830
@@ -6094,6 +6041,82 @@ merge(Compressor.prototype, {
}
return node;
}
+
+ function trim_destructured(node, value, process) {
+ var trimmer = new TreeTransformer(function(node) {
+ if (node instanceof AST_DefaultValue) {
+ if (compressor.option("default_values") && value && value.is_defined(compressor)) {
+ node = node.name;
+ } else {
+ return trim_default(tt, trimmer, node);
+ }
+ }
+ if (node instanceof AST_DestructuredArray) {
+ var save = value;
+ if (value instanceof AST_SymbolRef) value = value.fixed_value();
+ var values = value instanceof AST_Array && value.elements;
+ var elements = [];
+ node.elements.forEach(function(element, index) {
+ if (element instanceof AST_Hole) return;
+ value = values && values[index];
+ element = element.transform(trimmer);
+ if (element) elements[index] = element;
+ });
+ value = save;
+ if (values && elements.length == 0) return null;
+ for (var i = elements.length; --i >= 0;) {
+ if (!elements[i]) elements[i] = make_node(AST_Hole, node.elements[i] || node);
+ }
+ node.elements = elements;
+ return node;
+ }
+ if (node instanceof AST_DestructuredObject) {
+ var save = value;
+ if (value instanceof AST_SymbolRef) value = value.fixed_value();
+ var values;
+ if (value instanceof AST_Object) {
+ values = Object.create(null);
+ for (var i = 0; i < value.properties.length; i++) {
+ var prop = value.properties[i];
+ if (typeof prop.key != "string") {
+ values = null;
+ break;
+ }
+ values[prop.key] = prop.value;
+ }
+ }
+ var properties = [];
+ node.properties.forEach(function(prop) {
+ var retain;
+ if (prop.key instanceof AST_Node) {
+ prop.key = prop.key.transform(tt);
+ value = null;
+ retain = prop.key.has_side_effects(compressor);
+ } else {
+ value = values && values[prop.key];
+ retain = false;
+ }
+ if (retain && is_decl(prop.value)) {
+ properties.push(prop);
+ } else {
+ var newValue = prop.value.transform(trimmer);
+ if (newValue) {
+ prop.value = newValue;
+ properties.push(prop);
+ }
+ }
+ });
+ value = save;
+ if (properties.length == 0 && value && !value.may_throw_on_access(compressor)) {
+ return null;
+ }
+ node.properties = properties;
+ return node;
+ }
+ return process(node);
+ });
+ return node.transform(trimmer);
+ }
});
AST_Scope.DEFMETHOD("hoist_declarations", function(compressor) {
diff --git a/test/compress/default-values.js b/test/compress/default-values.js
index 8b9b3a95..bda32c1b 100644
--- a/test/compress/default-values.js
+++ b/test/compress/default-values.js
@@ -543,6 +543,70 @@ unused_var_2: {
node_version: ">=6"
}
+unused_value_assign_1: {
+ options = {
+ default_values: true,
+ unused: true,
+ }
+ input: {
+ [] = [ console.log("PASS") ];
+ }
+ expect: {
+ [ console.log("PASS") ];
+ }
+ expect_stdout: "PASS"
+ node_version: ">=6"
+}
+
+unused_value_assign_2: {
+ options = {
+ default_values: true,
+ unused: true,
+ }
+ input: {
+ [ a = console.log("FAIL") ] = [ "PASS" ];
+ console.log(a);
+ }
+ expect: {
+ [ a ] = [ "PASS" ];
+ console.log(a);
+ }
+ expect_stdout: "PASS"
+ node_version: ">=6"
+}
+
+unused_value_var_1: {
+ options = {
+ default_values: true,
+ unused: true,
+ }
+ input: {
+ var [] = [ console.log("PASS") ];
+ }
+ expect: {
+ console.log("PASS");
+ }
+ expect_stdout: "PASS"
+ node_version: ">=6"
+}
+
+unused_value_var_2: {
+ options = {
+ default_values: true,
+ unused: true,
+ }
+ input: {
+ var [ a = console.log("FAIL") ] = [ "PASS" ];
+ console.log(a);
+ }
+ expect: {
+ var [ a ] = [ "PASS" ];
+ console.log(a);
+ }
+ expect_stdout: "PASS"
+ node_version: ">=6"
+}
+
mangle_var_1: {
mangle = {
toplevel: false,