return new Compressor(options, false_by_default);
TreeTransformer.call(this, this.before, this.after);
this.options = defaults(options, {
- arguments : !false_by_default,
- booleans : !false_by_default,
- collapse_vars : !false_by_default,
- comparisons : !false_by_default,
- conditionals : !false_by_default,
- dead_code : !false_by_default,
- directives : !false_by_default,
- drop_console : false,
- drop_debugger : !false_by_default,
- evaluate : !false_by_default,
- expression : false,
- global_defs : false,
- hoist_funs : false,
- hoist_props : !false_by_default,
- hoist_vars : false,
- ie8 : false,
- if_return : !false_by_default,
- inline : !false_by_default,
- join_vars : !false_by_default,
- keep_fargs : true,
- keep_fnames : false,
- keep_infinity : false,
- loops : !false_by_default,
- negate_iife : !false_by_default,
- passes : 1,
- properties : !false_by_default,
- pure_getters : !false_by_default && "strict",
- pure_funcs : null,
- reduce_funcs : !false_by_default,
- reduce_vars : !false_by_default,
- sequences : !false_by_default,
- side_effects : !false_by_default,
- switches : !false_by_default,
- top_retain : null,
- toplevel : !!(options && options["top_retain"]),
- typeofs : !false_by_default,
- unsafe : false,
- unsafe_comps : false,
- unsafe_Function: false,
- unsafe_math : false,
- unsafe_proto : false,
- unsafe_regexp : false,
+ arguments : !false_by_default,
+ booleans : !false_by_default,
+ collapse_vars : !false_by_default,
+ comparisons : !false_by_default,
+ conditionals : !false_by_default,
+ dead_code : !false_by_default,
+ directives : !false_by_default,
+ drop_console : false,
+ drop_debugger : !false_by_default,
+ evaluate : !false_by_default,
+ expression : false,
+ global_defs : false,
+ hoist_funs : false,
+ hoist_props : !false_by_default,
+ hoist_vars : false,
+ ie8 : false,
+ if_return : !false_by_default,
+ inline : !false_by_default,
+ join_vars : !false_by_default,
+ keep_fargs : true,
+ keep_fnames : false,
+ keep_infinity : false,
+ loops : !false_by_default,
+ negate_iife : !false_by_default,
+ passes : 1,
+ properties : !false_by_default,
+ pure_getters : !false_by_default && "strict",
+ pure_funcs : null,
+ reduce_funcs : !false_by_default,
+ reduce_vars : !false_by_default,
+ sequences : !false_by_default,
+ side_effects : !false_by_default,
+ switches : !false_by_default,
+ top_retain : null,
+ toplevel : !!(options && options["top_retain"]),
+ typeofs : !false_by_default,
+ unsafe : false,
+ unsafe_comps : false,
+ unsafe_Function : false,
+ unsafe_math : false,
+ unsafe_proto : false,
+ unsafe_regexp : false,
unsafe_undefined: false,
- unused : !false_by_default,
- warnings : false,
+ unused : !false_by_default,
+ warnings : false,
}, true);
var global_defs = this.options["global_defs"];
if (typeof global_defs == "object") for (var key in global_defs) {
// a function expression needs parens around it when it's provably
// the first token to appear in a statement.
PARENS(AST_Function, function(output) {
- if (!output.has_parens() && first_in_statement(output)) {
- return true;
- }
-
+ if (!output.has_parens() && first_in_statement(output)) return true;
if (output.option('webkit')) {
var p = output.parent();
- if (p instanceof AST_PropAccess && p.expression === this) {
- return true;
- }
+ if (p instanceof AST_PropAccess && p.expression === this) return true;
}
-
if (output.option('wrap_iife')) {
var p = output.parent();
- return p instanceof AST_Call && p.expression === this;
+ if (p instanceof AST_Call && p.expression === this) return true;
}
-
- return false;
});
// same goes for an object literal, because otherwise it would be
});
PARENS(AST_Call, function(output) {
- var p = output.parent(), p1;
- if (p instanceof AST_New && p.expression === this)
- return true;
-
- // workaround for Safari bug.
+ var p = output.parent();
+ if (p instanceof AST_New && p.expression === this) return true;
// https://bugs.webkit.org/show_bug.cgi?id=123506
- return this.expression instanceof AST_Function
- && p instanceof AST_PropAccess
- && p.expression === this
- && (p1 = output.parent(1)) instanceof AST_Assign
- && p1.left === p;
+ if (output.option('webkit')) {
+ var g = output.parent(1);
+ return this.expression instanceof AST_Function
+ && p instanceof AST_PropAccess
+ && p.expression === this
+ && g instanceof AST_Assign
+ && g.left === p;
+ }
});
PARENS(AST_New, function(output) {
var in_use = names_in_use(scope, options);
var holes = scope.cname_holes;
var names = Object.create(null);
- // #179, #326
- // in Safari strict mode, something like (function x(x){...}) is a syntax error;
- // a function expression's argument cannot shadow the function expression's name
- if (scope instanceof AST_Function && scope.name && def.orig[0] instanceof AST_SymbolFunarg) {
- var tricky_def = scope.name.definition();
- // the function's mangled_name is null when keep_fnames is true
- names[tricky_def.mangled_name || tricky_def.name] = true;
- }
var scopes = [ scope ];
def.references.forEach(function(sym) {
var scope = sym.scope;
expect_stdout: "42"
}
-no_webkit: {
- beautify = {
- webkit: false,
- }
- input: {
- console.log(function() {
- 1 + 1;
- }.a = 1);
- }
- expect_exact: "console.log(function(){1+1}.a=1);"
- expect_stdout: "1"
-}
-
-webkit: {
- beautify = {
- webkit: true,
- }
- input: {
- console.log(function() {
- 1 + 1;
- }.a = 1);
- }
- expect_exact: "console.log((function(){1+1}).a=1);"
- expect_stdout: "1"
-}
-
issue_2084: {
options = {
collapse_vars: true,
--- /dev/null
+lambda_call_dot_assign: {
+ beautify = {
+ webkit: false,
+ }
+ input: {
+ console.log(function() {
+ return {};
+ }().a = 1);
+ }
+ expect_exact: "console.log(function(){return{}}().a=1);"
+ expect_stdout: "1"
+}
+
+lambda_call_dot_assign_webkit: {
+ beautify = {
+ webkit: true,
+ }
+ input: {
+ console.log(function() {
+ return {};
+ }().a = 1);
+ }
+ expect_exact: "console.log((function(){return{}}()).a=1);"
+ expect_stdout: "1"
+}
+
+lambda_dot_assign: {
+ beautify = {
+ webkit: false,
+ }
+ input: {
+ console.log(function() {
+ 1 + 1;
+ }.a = 1);
+ }
+ expect_exact: "console.log(function(){1+1}.a=1);"
+ expect_stdout: "1"
+}
+
+lambda_dot_assign_webkit: {
+ beautify = {
+ webkit: true,
+ }
+ input: {
+ console.log(function() {
+ 1 + 1;
+ }.a = 1);
+ }
+ expect_exact: "console.log((function(){1+1}).a=1);"
+ expect_stdout: "1"
+}
+
+lambda_name_mangle: {
+ mangle = {}
+ input: {
+ console.log(typeof function foo(bar) {});
+ }
+ expect_exact: "console.log(typeof function o(n){});"
+ expect_stdout: "function"
+}
var options = parse(url);
options.rejectUnauthorized = false;
require(options.protocol.slice(0, -1)).get(options, function(res) {
- if (res.statusCode !== 200) return callback(res);
- res.pipe(fs.createWriteStream(local(url)).on("close", function() {
- callback(null, read(url));
- }));
+ if (res.statusCode !== 200) return callback(res.statusCode);
+ res.pipe(fs.createWriteStream(local(url)));
+ callback(null, res);
});
}).on("open", function() {
callback(null, result);
request.resume();
var url = site + request.url;
fetch(url, function(err, res) {
- if (err) throw err;
- response.writeHead(200, {
- "Content-Type": {
- css: "text/css",
- js: "application/javascript",
- png: "image/png"
- }[url.slice(url.lastIndexOf(".") + 1)] || "text/html; charset=utf-8"
- });
- if (/\.js$/.test(url)) {
- var stderr = "";
- var uglifyjs = child_process.fork("bin/uglifyjs", args, {
- silent: true
- }).on("exit", function(code) {
- console.log("uglifyjs", url.slice(site.length + 1), args.join(" "));
- console.log(stderr);
- if (code) throw new Error("uglifyjs failed with code " + code);
- });
- uglifyjs.stderr.on("data", function(data) {
- stderr += data;
- }).setEncoding("utf8");
- uglifyjs.stdout.pipe(response);
- res.pipe(uglifyjs.stdin);
+ if (err) {
+ if (typeof err != "number") throw err;
+ response.writeHead(err);
+ response.end();
} else {
- res.pipe(response);
+ response.writeHead(200, {
+ "Content-Type": {
+ css: "text/css",
+ js: "application/javascript",
+ png: "image/png"
+ }[url.slice(url.lastIndexOf(".") + 1)] || "text/html; charset=utf-8"
+ });
+ if (/\.js$/.test(url)) {
+ var stderr = "";
+ var uglifyjs = child_process.fork("bin/uglifyjs", args, {
+ silent: true
+ }).on("exit", function(code) {
+ console.log("uglifyjs", url.slice(site.length + 1), args.join(" "));
+ console.log(stderr);
+ if (code) throw new Error("uglifyjs failed with code " + code);
+ });
+ uglifyjs.stderr.on("data", function(data) {
+ stderr += data;
+ }).setEncoding("utf8");
+ uglifyjs.stdout.pipe(response);
+ res.pipe(uglifyjs.stdin);
+ } else {
+ res.pipe(response);
+ }
}
});
}).listen();