1UglifyJS 2
2==========
3[![Build Status](https://travis-ci.org/mishoo/UglifyJS2.svg)](https://travis-ci.org/mishoo/UglifyJS2)
4
5UglifyJS is a JavaScript parser, minifier, compressor or beautifier toolkit.
6
7This page documents the command line utility.  For
8[API and internals documentation see my website](http://lisperator.net/uglifyjs/).
9There's also an
10[in-browser online demo](http://lisperator.net/uglifyjs/#demo) (for Firefox,
11Chrome and probably Safari).
12
13#### Note:
14- `uglify-js` only supports ECMAScript 5 (ES5).
15- Support for `const` is [present but incomplete](#support-for-const), and may not be
16  transformed properly.
17- Those wishing to minify ES2015+ (ES6+) should use the `npm` package [**uglify-es**](https://github.com/mishoo/UglifyJS2/tree/harmony).
18
19Install
20-------
21
22First make sure you have installed the latest version of [node.js](http://nodejs.org/)
23(You may need to restart your computer after this step).
24
25From NPM for use as a command line app:
26
27    npm install uglify-js -g
28
29From NPM for programmatic use:
30
31    npm install uglify-js
32
33Usage
34-----
35
36    uglifyjs [input files] [options]
37
38UglifyJS2 can take multiple input files.  It's recommended that you pass the
39input files first, then pass the options.  UglifyJS will parse input files
40in sequence and apply any compression options.  The files are parsed in the
41same global scope, that is, a reference from a file to some
42variable/function declared in another file will be matched properly.
43
44If you want to read from STDIN instead, pass a single dash instead of input
45files.
46
47If you wish to pass your options before the input files, separate the two with
48a double dash to prevent input files being used as option arguments:
49
50    uglifyjs --compress --mangle -- input.js
51
52The available options are:
53
54```
55  --source-map                  Specify an output file where to generate source
56                                map.
57  --source-map-root             The path to the original source to be included
58                                in the source map.
59  --source-map-url              The path to the source map to be added in //#
60                                sourceMappingURL.  Defaults to the value passed
61                                with --source-map.
62  --source-map-include-sources  Pass this flag if you want to include the
63                                content of source files in the source map as
64                                sourcesContent property.
65  --source-map-inline           Write base64-encoded source map to the end of js output.
66  --in-source-map               Input source map, useful if you're compressing
67                                JS that was generated from some other original
68                                code. Specify "inline" if the source map is included
69                                inline with the sources.
70  --screw-ie8                   Use this flag if you don't wish to support
71                                Internet Explorer 6/7/8.
72                                By default UglifyJS will not try to be IE-proof.
73  --support-ie8                 Use this flag to support Internet Explorer 6/7/8.
74                                Equivalent to setting `screw_ie8: false` in `minify()`
75                                for `compress`, `mangle` and `output` options.
76  --expr                        Parse a single expression, rather than a
77                                program (for parsing JSON)
78  -p, --prefix                  Skip prefix for original filenames that appear
79                                in source maps. For example -p 3 will drop 3
80                                directories from file names and ensure they are
81                                relative paths. You can also specify -p
82                                relative, which will make UglifyJS figure out
83                                itself the relative paths between original
84                                sources, the source map and the output file.
85  -o, --output                  Output file (default STDOUT).
86  -b, --beautify                Beautify output/specify output options.
87  -m, --mangle                  Mangle names/pass mangler options.
88  -r, --reserved                Reserved names to exclude from mangling.
89  -c, --compress                Enable compressor/pass compressor options, e.g.
90                                `-c 'if_return=false,pure_funcs=["Math.pow","console.log"]'`
91                                Use `-c` with no argument to enable default compression
92                                options.
93  -d, --define                  Global definitions
94  -e, --enclose                 Embed everything in a big function, with a
95                                configurable parameter/argument list.
96  --comments                    Preserve copyright comments in the output. By
97                                default this works like Google Closure, keeping
98                                JSDoc-style comments that contain "@license" or
99                                "@preserve". You can optionally pass one of the
100                                following arguments to this flag:
101                                - "all" to keep all comments
102                                - a valid JS RegExp like `/foo/` or `/^!/` to
103                                keep only matching comments.
104                                Note that currently not *all* comments can be
105                                kept when compression is on, because of dead
106                                code removal or cascading statements into
107                                sequences.
108  --preamble                    Preamble to prepend to the output.  You can use
109                                this to insert a comment, for example for
110                                licensing information.  This will not be
111                                parsed, but the source map will adjust for its
112                                presence.
113  --stats                       Display operations run time on STDERR.
114  --acorn                       Use Acorn for parsing.
115  --spidermonkey                Assume input files are SpiderMonkey AST format
116                                (as JSON).
117  --self                        Build itself (UglifyJS2) as a library (implies
118                                --wrap=UglifyJS --export-all)
119  --wrap                        Embed everything in a big function, making the
120                                “exports” and “global” variables available. You
121                                need to pass an argument to this option to
122                                specify the name that your module will take
123                                when included in, say, a browser.
124  --export-all                  Only used when --wrap, this tells UglifyJS to
125                                add code to automatically export all globals.
126  --lint                        Display some scope warnings
127  -v, --verbose                 Verbose
128  -V, --version                 Print version number and exit.
129  --noerr                       Don't throw an error for unknown options in -c,
130                                -b or -m.
131  --bare-returns                Allow return outside of functions.  Useful when
132                                minifying CommonJS modules and Userscripts that
133                                may be anonymous function wrapped (IIFE) by the
134                                .user.js engine `caller`.
135  --keep-fnames                 Do not mangle/drop function names.  Useful for
136                                code relying on Function.prototype.name.
137  --reserved-file               File containing reserved names
138  --reserve-domprops            Make (most?) DOM properties reserved for
139                                --mangle-props
140  --mangle-props                Mangle property names (default `0`). Set to
141                                `true` or `1` to mangle all property names. Set
142                                to `unquoted` or `2` to only mangle unquoted
143                                property names. Mode `2` also enables the
144                                `keep_quoted_props` beautifier option to
145                                preserve the quotes around property names and
146                                disables the `properties` compressor option to
147                                prevent rewriting quoted properties with dot
148                                notation. You can override these by setting
149                                them explicitly on the command line.
150  --mangle-regex                Only mangle property names matching the regex
151  --name-cache                  File to hold mangled names mappings
152  --pure-funcs                  Functions that can be safely removed if their
153                                return value is not used, e.g.
154                                `--pure-funcs Math.floor console.info`
155                                (requires `--compress`)
156```
157
158Specify `--output` (`-o`) to declare the output file.  Otherwise the output
159goes to STDOUT.
160
161## Source map options
162
163UglifyJS2 can generate a source map file, which is highly useful for
164debugging your compressed JavaScript.  To get a source map, pass
165`--source-map output.js.map` (full path to the file where you want the
166source map dumped).
167
168Additionally you might need `--source-map-root` to pass the URL where the
169original files can be found.  In case you are passing full paths to input
170files to UglifyJS, you can use `--prefix` (`-p`) to specify the number of
171directories to drop from the path prefix when declaring files in the source
172map.
173
174For example:
175
176    uglifyjs /home/doe/work/foo/src/js/file1.js \
177             /home/doe/work/foo/src/js/file2.js \
178             -o foo.min.js \
179             --source-map foo.min.js.map \
180             --source-map-root http://foo.com/src \
181             -p 5 -c -m
182
183The above will compress and mangle `file1.js` and `file2.js`, will drop the
184output in `foo.min.js` and the source map in `foo.min.js.map`.  The source
185mapping will refer to `http://foo.com/src/js/file1.js` and
186`http://foo.com/src/js/file2.js` (in fact it will list `http://foo.com/src`
187as the source map root, and the original files as `js/file1.js` and
188`js/file2.js`).
189
190### Composed source map
191
192When you're compressing JS code that was output by a compiler such as
193CoffeeScript, mapping to the JS code won't be too helpful.  Instead, you'd
194like to map back to the original code (i.e. CoffeeScript).  UglifyJS has an
195option to take an input source map.  Assuming you have a mapping from
196CoffeeScript → compiled JS, UglifyJS can generate a map from CoffeeScript →
197compressed JS by mapping every token in the compiled JS to its original
198location.
199
200To use this feature you need to pass `--in-source-map
201/path/to/input/source.map` or `--in-source-map inline` if the source map is
202included inline with the sources. Normally the input source map should also
203point to the file containing the generated JS, so if that's correct you can
204omit input files from the command line.
205
206## Mangler options
207
208To enable the mangler you need to pass `--mangle` (`-m`).  The following
209(comma-separated) options are supported:
210
211- `toplevel` — mangle names declared in the toplevel scope (disabled by
212  default).
213
214- `eval` — mangle names visible in scopes where `eval` or `with` are used
215  (disabled by default).
216
217When mangling is enabled but you want to prevent certain names from being
218mangled, you can declare those names with `--reserved` (`-r`) — pass a
219comma-separated list of names.  For example:
220
221    uglifyjs ... -m -r '$,require,exports'
222
223to prevent the `require`, `exports` and `$` names from being changed.
224
225### Mangling property names (`--mangle-props`)
226
227**Note:** this will probably break your code.  Mangling property names is a
228separate step, different from variable name mangling.  Pass
229`--mangle-props`.  It will mangle all properties that are seen in some
230object literal, or that are assigned to.  For example:
231
232```js
233var x = {
234  foo: 1
235};
236
237x.bar = 2;
238x["baz"] = 3;
239x[condition ? "moo" : "boo"] = 4;
240console.log(x.something());
241```
242
243In the above code, `foo`, `bar`, `baz`, `moo` and `boo` will be replaced
244with single characters, while `something()` will be left as is.
245
246In order for this to be of any use, we should avoid mangling standard JS
247names.  For instance, if your code would contain `x.length = 10`, then
248`length` becomes a candidate for mangling and it will be mangled throughout
249the code, regardless if it's being used as part of your own objects or
250accessing an array's length.  To avoid that, you can use `--reserved-file`
251to pass a filename that should contain the names to be excluded from
252mangling.  This file can be used both for excluding variable names and
253property names.  It could look like this, for example:
254
255```js
256{
257  "vars": [ "define", "require", ... ],
258  "props": [ "length", "prototype", ... ]
259}
260```
261
262`--reserved-file` can be an array of file names (either a single
263comma-separated argument, or you can pass multiple `--reserved-file`
264arguments) — in this case it will exclude names from all those files.
265
266A default exclusion file is provided in `tools/domprops.json` which should
267cover most standard JS and DOM properties defined in various browsers.  Pass
268`--reserve-domprops` to read that in.
269
270You can also use a regular expression to define which property names should be
271mangled.  For example, `--mangle-regex="/^_/"` will only mangle property names
272that start with an underscore.
273
274When you compress multiple files using this option, in order for them to
275work together in the end we need to ensure somehow that one property gets
276mangled to the same name in all of them.  For this, pass `--name-cache
277filename.json` and UglifyJS will maintain these mappings in a file which can
278then be reused.  It should be initially empty.  Example:
279
280```
281rm -f /tmp/cache.json  # start fresh
282uglifyjs file1.js file2.js --mangle-props --name-cache /tmp/cache.json -o part1.js
283uglifyjs file3.js file4.js --mangle-props --name-cache /tmp/cache.json -o part2.js
284```
285
286Now, `part1.js` and `part2.js` will be consistent with each other in terms
287of mangled property names.
288
289Using the name cache is not necessary if you compress all your files in a
290single call to UglifyJS.
291
292#### Mangling unquoted names (`--mangle-props=unquoted` or `--mangle-props=2`)
293
294Using quoted property name (`o["foo"]`) reserves the property name (`foo`)
295so that it is not mangled throughout the entire script even when used in an
296unquoted style (`o.foo`). Example:
297
298```
299$ echo 'var o={"foo":1, bar:3}; o.foo += o.bar; console.log(o.foo);' | uglifyjs --mangle-props=2 -mc
300var o={"foo":1,a:3};o.foo+=o.a,console.log(o.foo);
301```
302
303#### Debugging property name mangling
304
305You can also pass `--mangle-props-debug` in order to mangle property names
306without completely obscuring them. For example the property `o.foo`
307would mangle to `o._$foo$_` with this option. This allows property mangling
308of a large codebase while still being able to debug the code and identify
309where mangling is breaking things.
310
311You can also pass a custom suffix using `--mangle-props-debug=XYZ`. This would then
312mangle `o.foo` to `o._$foo$XYZ_`. You can change this each time you compile a
313script to identify how a property got mangled. One technique is to pass a
314random number on every compile to simulate mangling changing with different
315inputs (e.g. as you update the input script with new properties), and to help
316identify mistakes like writing mangled keys to storage.
317
318## Compressor options
319
320You need to pass `--compress` (`-c`) to enable the compressor.  Optionally
321you can pass a comma-separated list of options.  Options are in the form
322`foo=bar`, or just `foo` (the latter implies a boolean option that you want
323to set `true`; it's effectively a shortcut for `foo=true`).
324
325- `sequences` (default: true) -- join consecutive simple statements using the
326  comma operator.  May be set to a positive integer to specify the maximum number
327  of consecutive comma sequences that will be generated. If this option is set to
328  `true` then the default `sequences` limit is `200`. Set option to `false` or `0`
329  to disable. The smallest `sequences` length is `2`. A `sequences` value of `1`
330  is grandfathered to be equivalent to `true` and as such means `200`. On rare
331  occasions the default sequences limit leads to very slow compress times in which
332  case a value of `20` or less is recommended.
333
334- `properties` -- rewrite property access using the dot notation, for
335  example `foo["bar"] → foo.bar`
336
337- `dead_code` -- remove unreachable code
338
339- `drop_debugger` -- remove `debugger;` statements
340
341- `unsafe` (default: false) -- apply "unsafe" transformations (discussion below)
342
343- `unsafe_comps` (default: false) -- Reverse `<` and `<=` to `>` and `>=` to
344  allow improved compression. This might be unsafe when an at least one of two
345  operands is an object with computed values due the use of methods like `get`,
346  or `valueOf`. This could cause change in execution order after operands in the
347  comparison are switching. Compression only works if both `comparisons` and
348  `unsafe_comps` are both set to true.
349
350- `unsafe_math` (default: false) -- optimize numerical expressions like
351  `2 * x * 3` into `6 * x`, which may give imprecise floating point results.
352
353- `unsafe_proto` (default: false) -- optimize expressions like
354  `Array.prototype.slice.call(a)` into `[].slice.call(a)`
355
356- `unsafe_regexp` (default: false) -- enable substitutions of variables with
357  `RegExp` values the same way as if they are constants.
358
359- `conditionals` -- apply optimizations for `if`-s and conditional
360  expressions
361
362- `comparisons` -- apply certain optimizations to binary nodes, for example:
363  `!(a <= b) → a > b` (only when `unsafe_comps`), attempts to negate binary
364  nodes, e.g. `a = !b && !c && !d && !e → a=!(b||c||d||e)` etc.
365
366- `evaluate` -- attempt to evaluate constant expressions
367
368- `booleans` -- various optimizations for boolean context, for example `!!a
369  ? b : c → a ? b : c`
370
371- `loops` -- optimizations for `do`, `while` and `for` loops when we can
372  statically determine the condition
373
374- `unused` -- drop unreferenced functions and variables (simple direct variable
375  assignments do not count as references unless set to `"keep_assign"`)
376
377- `toplevel` -- drop unreferenced functions (`"funcs"`) and/or variables (`"vars"`)
378  in the toplevel scope (`false` by default, `true` to drop both unreferenced
379  functions and variables)
380
381- `top_retain` -- prevent specific toplevel functions and variables from `unused`
382  removal (can be array, comma-separated, RegExp or function. Implies `toplevel`)
383
384- `hoist_funs` -- hoist function declarations
385
386- `hoist_vars` (default: false) -- hoist `var` declarations (this is `false`
387  by default because it seems to increase the size of the output in general)
388
389- `if_return` -- optimizations for if/return and if/continue
390
391- `join_vars` -- join consecutive `var` statements
392
393- `cascade` -- small optimization for sequences, transform `x, x` into `x`
394  and `x = something(), x` into `x = something()`
395
396- `collapse_vars` -- Collapse single-use `var` and `const` definitions
397  when possible.
398
399- `reduce_vars` -- Improve optimization on variables assigned with and
400  used as constant values.
401
402- `warnings` -- display warnings when dropping unreachable code or unused
403  declarations etc.
404
405- `negate_iife` -- negate "Immediately-Called Function Expressions"
406  where the return value is discarded, to avoid the parens that the
407  code generator would insert.
408
409- `pure_getters` -- the default is `false`.  If you pass `true` for
410  this, UglifyJS will assume that object property access
411  (e.g. `foo.bar` or `foo["bar"]`) doesn't have any side effects.
412  Specify `"strict"` to treat `foo.bar` as side-effect-free only when
413  `foo` is certain to not throw, i.e. not `null` or `undefined`.
414
415- `pure_funcs` -- default `null`.  You can pass an array of names and
416  UglifyJS will assume that those functions do not produce side
417  effects.  DANGER: will not check if the name is redefined in scope.
418  An example case here, for instance `var q = Math.floor(a/b)`.  If
419  variable `q` is not used elsewhere, UglifyJS will drop it, but will
420  still keep the `Math.floor(a/b)`, not knowing what it does.  You can
421  pass `pure_funcs: [ 'Math.floor' ]` to let it know that this
422  function won't produce any side effect, in which case the whole
423  statement would get discarded.  The current implementation adds some
424  overhead (compression will be slower).
425
426- `drop_console` -- default `false`.  Pass `true` to discard calls to
427  `console.*` functions. If you wish to drop a specific function call
428  such as `console.info` and/or retain side effects from function arguments
429  after dropping the function call then use `pure_funcs` instead.
430
431- `expression` -- default `false`.  Pass `true` to preserve completion values
432  from terminal statements without `return`, e.g. in bookmarklets.
433
434- `keep_fargs` -- default `true`.  Prevents the
435  compressor from discarding unused function arguments.  You need this
436  for code which relies on `Function.length`.
437
438- `keep_fnames` -- default `false`.  Pass `true` to prevent the
439  compressor from discarding function names.  Useful for code relying on
440  `Function.prototype.name`. See also: the `keep_fnames` [mangle option](#mangle).
441
442- `passes` -- default `1`. Number of times to run compress with a maximum of 3.
443  In some cases more than one pass leads to further compressed code.  Keep in
444  mind more passes will take more time.
445
446- `keep_infinity` -- default `false`. Pass `true` to prevent `Infinity` from
447  being compressed into `1/0`, which may cause performance issues on Chrome.
448
449- `side_effects` -- default `true`. Pass `false` to disable potentially dropping
450  functions marked as "pure".  A function call is marked as "pure" if a comment
451  annotation `/*@__PURE__*/` or `/*#__PURE__*/` immediately precedes the call. For
452  example: `/*@__PURE__*/foo();`
453
454
455### The `unsafe` option
456
457It enables some transformations that *might* break code logic in certain
458contrived cases, but should be fine for most code.  You might want to try it
459on your own code, it should reduce the minified size.  Here's what happens
460when this flag is on:
461
462- `new Array(1, 2, 3)` or `Array(1, 2, 3)` → `[ 1, 2, 3 ]`
463- `new Object()` → `{}`
464- `String(exp)` or `exp.toString()` → `"" + exp`
465- `new Object/RegExp/Function/Error/Array (...)` → we discard the `new`
466- `typeof foo == "undefined"` → `foo === void 0`
467- `void 0` → `undefined` (if there is a variable named "undefined" in
468  scope; we do it because the variable name will be mangled, typically
469  reduced to a single character)
470
471### Conditional compilation
472
473You can use the `--define` (`-d`) switch in order to declare global
474variables that UglifyJS will assume to be constants (unless defined in
475scope).  For example if you pass `--define DEBUG=false` then, coupled with
476dead code removal UglifyJS will discard the following from the output:
477```javascript
478if (DEBUG) {
479	console.log("debug stuff");
480}
481```
482
483You can specify nested constants in the form of `--define env.DEBUG=false`.
484
485UglifyJS will warn about the condition being always false and about dropping
486unreachable code; for now there is no option to turn off only this specific
487warning, you can pass `warnings=false` to turn off *all* warnings.
488
489Another way of doing that is to declare your globals as constants in a
490separate file and include it into the build.  For example you can have a
491`build/defines.js` file with the following:
492```javascript
493const DEBUG = false;
494const PRODUCTION = true;
495// etc.
496```
497
498and build your code like this:
499
500    uglifyjs build/defines.js js/foo.js js/bar.js... -c
501
502UglifyJS will notice the constants and, since they cannot be altered, it
503will evaluate references to them to the value itself and drop unreachable
504code as usual.  The build will contain the `const` declarations if you use
505them. If you are targeting < ES6 environments which does not support `const`,
506using `var` with `reduce_vars` (enabled by default) should suffice.
507
508<a name="codegen-options"></a>
509
510#### Conditional compilation, API
511You can also use conditional compilation via the programmatic API. With the difference that the
512property name is `global_defs` and is a compressor property:
513
514```js
515uglifyJS.minify([ "input.js"], {
516    compress: {
517        dead_code: true,
518        global_defs: {
519            DEBUG: false
520        }
521    }
522});
523```
524
525## Beautifier options
526
527The code generator tries to output shortest code possible by default.  In
528case you want beautified output, pass `--beautify` (`-b`).  Optionally you
529can pass additional arguments that control the code output:
530
531- `beautify` (default `true`) -- whether to actually beautify the output.
532  Passing `-b` will set this to true, but you might need to pass `-b` even
533  when you want to generate minified code, in order to specify additional
534  arguments, so you can use `-b beautify=false` to override it.
535- `indent-level` (default 4)
536- `indent-start` (default 0) -- prefix all lines by that many spaces
537- `quote-keys` (default `false`) -- pass `true` to quote all keys in literal
538  objects
539- `space-colon` (default `true`) -- insert a space after the colon signs
540- `ascii-only` (default `false`) -- escape Unicode characters in strings and
541  regexps (affects directives with non-ascii characters becoming invalid)
542- `inline-script` (default `false`) -- escape the slash in occurrences of
543  `</script` in strings
544- `width` (default 80) -- only takes effect when beautification is on, this
545  specifies an (orientative) line width that the beautifier will try to
546  obey.  It refers to the width of the line text (excluding indentation).
547  It doesn't work very well currently, but it does make the code generated
548  by UglifyJS more readable.
549- `max-line-len` (default 32000) -- maximum line length (for uglified code)
550- `bracketize` (default `false`) -- always insert brackets in `if`, `for`,
551  `do`, `while` or `with` statements, even if their body is a single
552  statement.
553- `semicolons` (default `true`) -- separate statements with semicolons.  If
554  you pass `false` then whenever possible we will use a newline instead of a
555  semicolon, leading to more readable output of uglified code (size before
556  gzip could be smaller; size after gzip insignificantly larger).
557- `preamble` (default `null`) -- when passed it must be a string and
558  it will be prepended to the output literally.  The source map will
559  adjust for this text.  Can be used to insert a comment containing
560  licensing information, for example.
561- `quote_style` (default `0`) -- preferred quote style for strings (affects
562  quoted property names and directives as well):
563  - `0` -- prefers double quotes, switches to single quotes when there are
564    more double quotes in the string itself.
565  - `1` -- always use single quotes
566  - `2` -- always use double quotes
567  - `3` -- always use the original quotes
568- `keep_quoted_props` (default `false`) -- when turned on, prevents stripping
569  quotes from property names in object literals.
570
571### Keeping copyright notices or other comments
572
573You can pass `--comments` to retain certain comments in the output.  By
574default it will keep JSDoc-style comments that contain "@preserve",
575"@license" or "@cc_on" (conditional compilation for IE).  You can pass
576`--comments all` to keep all the comments, or a valid JavaScript regexp to
577keep only comments that match this regexp.  For example `--comments
578'/foo|bar/'` will keep only comments that contain "foo" or "bar".
579
580Note, however, that there might be situations where comments are lost.  For
581example:
582```javascript
583function f() {
584	/** @preserve Foo Bar */
585	function g() {
586	  // this function is never called
587	}
588	return something();
589}
590```
591
592Even though it has "@preserve", the comment will be lost because the inner
593function `g` (which is the AST node to which the comment is attached to) is
594discarded by the compressor as not referenced.
595
596The safest comments where to place copyright information (or other info that
597needs to be kept in the output) are comments attached to toplevel nodes.
598
599## Support for the SpiderMonkey AST
600
601UglifyJS2 has its own abstract syntax tree format; for
602[practical reasons](http://lisperator.net/blog/uglifyjs-why-not-switching-to-spidermonkey-ast/)
603we can't easily change to using the SpiderMonkey AST internally.  However,
604UglifyJS now has a converter which can import a SpiderMonkey AST.
605
606For example [Acorn][acorn] is a super-fast parser that produces a
607SpiderMonkey AST.  It has a small CLI utility that parses one file and dumps
608the AST in JSON on the standard output.  To use UglifyJS to mangle and
609compress that:
610
611    acorn file.js | uglifyjs --spidermonkey -m -c
612
613The `--spidermonkey` option tells UglifyJS that all input files are not
614JavaScript, but JS code described in SpiderMonkey AST in JSON.  Therefore we
615don't use our own parser in this case, but just transform that AST into our
616internal AST.
617
618### Use Acorn for parsing
619
620More for fun, I added the `--acorn` option which will use Acorn to do all
621the parsing.  If you pass this option, UglifyJS will `require("acorn")`.
622
623Acorn is really fast (e.g. 250ms instead of 380ms on some 650K code), but
624converting the SpiderMonkey tree that Acorn produces takes another 150ms so
625in total it's a bit more than just using UglifyJS's own parser.
626
627### Using UglifyJS to transform SpiderMonkey AST
628
629Now you can use UglifyJS as any other intermediate tool for transforming
630JavaScript ASTs in SpiderMonkey format.
631
632Example:
633
634```javascript
635function uglify(ast, options, mangle) {
636  // Conversion from SpiderMonkey AST to internal format
637  var uAST = UglifyJS.AST_Node.from_mozilla_ast(ast);
638
639  // Compression
640  uAST.figure_out_scope();
641  uAST = UglifyJS.Compressor(options).compress(uAST);
642
643  // Mangling (optional)
644  if (mangle) {
645    uAST.figure_out_scope();
646    uAST.compute_char_frequency();
647    uAST.mangle_names();
648  }
649
650  // Back-conversion to SpiderMonkey AST
651  return uAST.to_mozilla_ast();
652}
653```
654
655Check out
656[original blog post](http://rreverser.com/using-mozilla-ast-with-uglifyjs/)
657for details.
658
659API Reference
660-------------
661
662Assuming installation via NPM, you can load UglifyJS in your application
663like this:
664```javascript
665var UglifyJS = require("uglify-js");
666```
667
668It exports a lot of names, but I'll discuss here the basics that are needed
669for parsing, mangling and compressing a piece of code.  The sequence is (1)
670parse, (2) compress, (3) mangle, (4) generate output code.
671
672### The simple way
673
674There's a single toplevel function which combines all the steps.  If you
675don't need additional customization, you might want to go with `minify`.
676Example:
677```javascript
678var result = UglifyJS.minify("/path/to/file.js");
679console.log(result.code); // minified output
680// if you need to pass code instead of file name
681var result = UglifyJS.minify("var b = function () {};", {fromString: true});
682```
683
684You can also compress multiple files:
685```javascript
686var result = UglifyJS.minify([ "file1.js", "file2.js", "file3.js" ]);
687console.log(result.code);
688```
689
690To generate a source map:
691```javascript
692var result = UglifyJS.minify([ "file1.js", "file2.js", "file3.js" ], {
693	outSourceMap: "out.js.map"
694});
695console.log(result.code); // minified output
696console.log(result.map);
697```
698
699To generate a source map with the fromString option, you can also use an object:
700```javascript
701var result = UglifyJS.minify({"file1.js": "var a = function () {};"}, {
702  outSourceMap: "out.js.map",
703  outFileName: "out.js",
704  fromString: true
705});
706```
707
708Note that the source map is not saved in a file, it's just returned in
709`result.map`.  The value passed for `outSourceMap` is only used to set
710`//# sourceMappingURL=out.js.map` in `result.code`. The value of
711`outFileName` is only used to set `file` attribute in source map file.
712
713The `file` attribute in the source map (see [the spec][sm-spec]) will
714use `outFileName` firstly, if it's falsy, then will be deduced from
715`outSourceMap` (by removing `'.map'`).
716
717You can set option `sourceMapInline` to be `true` and source map will
718be appended to code.
719
720You can also specify sourceRoot property to be included in source map:
721```javascript
722var result = UglifyJS.minify([ "file1.js", "file2.js", "file3.js" ], {
723	outSourceMap: "out.js.map",
724	sourceRoot: "http://example.com/src"
725});
726```
727
728If you're compressing compiled JavaScript and have a source map for it, you
729can use the `inSourceMap` argument:
730```javascript
731var result = UglifyJS.minify("compiled.js", {
732	inSourceMap: "compiled.js.map",
733	outSourceMap: "minified.js.map"
734});
735// same as before, it returns `code` and `map`
736```
737
738If your input source map is not in a file, you can pass it in as an object
739using the `inSourceMap` argument:
740
741```javascript
742var result = UglifyJS.minify("compiled.js", {
743	inSourceMap: JSON.parse(my_source_map_string),
744	outSourceMap: "minified.js.map"
745});
746```
747
748The `inSourceMap` is only used if you also request `outSourceMap` (it makes
749no sense otherwise).
750
751To set the source map url, use the `sourceMapUrl` option.
752If you're using the X-SourceMap header instead, you can just set the `sourceMapUrl` option to false.
753Defaults to outSourceMap:
754
755```javascript
756var result = UglifyJS.minify([ "file1.js" ], {
757  outSourceMap: "out.js.map",
758  sourceMapUrl: "localhost/out.js.map"
759});
760```
761
762Other options:
763
764- `warnings` (default `false`) — pass `true` to display compressor warnings.
765
766- `fromString` (default `false`) — if you pass `true` then you can pass
767  JavaScript source code, rather than file names.
768
769- `mangle` (default `true`) — pass `false` to skip mangling names, or pass
770  an object to specify mangling options (see below).
771
772- `mangleProperties` (default `false`) — pass an object to specify custom
773  mangle property options.
774
775- `output` (default `null`) — pass an object if you wish to specify
776  additional [output options][codegen].  The defaults are optimized
777  for best compression.
778
779- `compress` (default `{}`) — pass `false` to skip compressing entirely.
780  Pass an object to specify custom [compressor options][compressor].
781
782- `parse` (default {}) — pass an object if you wish to specify some
783  additional [parser options][parser]. (not all options available... see below)
784
785##### mangle
786
787 - `except` - pass an array of identifiers that should be excluded from mangling
788
789 - `toplevel` — mangle names declared in the toplevel scope (disabled by
790  default).
791
792 - `eval` — mangle names visible in scopes where eval or with are used
793  (disabled by default).
794
795 - `keep_fnames` -- default `false`.  Pass `true` to not mangle
796  function names.  Useful for code relying on `Function.prototype.name`.
797  See also: the `keep_fnames` [compress option](#compressor-options).
798
799  Examples:
800
801  ```javascript
802  //tst.js
803  var globalVar;
804  function funcName(firstLongName, anotherLongName)
805  {
806    var myVariable = firstLongName +  anotherLongName;
807  }
808
809  UglifyJS.minify("tst.js").code;
810  // 'function funcName(a,n){}var globalVar;'
811
812  UglifyJS.minify("tst.js", { mangle: { except: ['firstLongName'] } }).code;
813  // 'function funcName(firstLongName,a){}var globalVar;'
814
815  UglifyJS.minify("tst.js", { mangle: { toplevel: true } }).code;
816  // 'function n(n,a){}var a;'
817  ```
818
819##### mangleProperties options
820
821 - `regex` — Pass a RegExp to only mangle certain names (maps to the `--mangle-regex` CLI arguments option)
822 - `ignore_quoted` – Only mangle unquoted property names (maps to the `--mangle-props 2` CLI arguments option)
823 - `debug` – Mangle names with the original name still present (maps to the `--mangle-props-debug` CLI arguments option). Defaults to `false`. Pass an empty string to enable, or a non-empty string to set the suffix.
824
825We could add more options to `UglifyJS.minify` — if you need additional
826functionality please suggest!
827
828### The hard way
829
830Following there's more detailed API info, in case the `minify` function is
831too simple for your needs.
832
833#### The parser
834```javascript
835var toplevel_ast = UglifyJS.parse(code, options);
836```
837
838`options` is optional and if present it must be an object.  The following
839properties are available:
840
841- `strict` — disable automatic semicolon insertion and support for trailing
842  comma in arrays and objects
843- `bare_returns` — Allow return outside of functions. (maps to the
844  `--bare-returns` CLI arguments option and available to `minify` `parse`
845  other options object)
846- `filename` — the name of the file where this code is coming from
847- `toplevel` — a `toplevel` node (as returned by a previous invocation of
848  `parse`)
849
850The last two options are useful when you'd like to minify multiple files and
851get a single file as the output and a proper source map.  Our CLI tool does
852something like this:
853```javascript
854var toplevel = null;
855files.forEach(function(file){
856	var code = fs.readFileSync(file, "utf8");
857	toplevel = UglifyJS.parse(code, {
858		filename: file,
859		toplevel: toplevel
860	});
861});
862```
863
864After this, we have in `toplevel` a big AST containing all our files, with
865each token having proper information about where it came from.
866
867#### Scope information
868
869UglifyJS contains a scope analyzer that you need to call manually before
870compressing or mangling.  Basically it augments various nodes in the AST
871with information about where is a name defined, how many times is a name
872referenced, if it is a global or not, if a function is using `eval` or the
873`with` statement etc.  I will discuss this some place else, for now what's
874important to know is that you need to call the following before doing
875anything with the tree:
876```javascript
877toplevel.figure_out_scope()
878```
879
880#### Compression
881
882Like this:
883```javascript
884var compressor = UglifyJS.Compressor(options);
885var compressed_ast = compressor.compress(toplevel);
886```
887
888The `options` can be missing.  Available options are discussed above in
889“Compressor options”.  Defaults should lead to best compression in most
890scripts.
891
892The compressor is destructive, so don't rely that `toplevel` remains the
893original tree.
894
895#### Mangling
896
897After compression it is a good idea to call again `figure_out_scope` (since
898the compressor might drop unused variables / unreachable code and this might
899change the number of identifiers or their position).  Optionally, you can
900call a trick that helps after Gzip (counting character frequency in
901non-mangleable words).  Example:
902```javascript
903compressed_ast.figure_out_scope();
904compressed_ast.compute_char_frequency();
905compressed_ast.mangle_names();
906```
907
908#### Generating output
909
910AST nodes have a `print` method that takes an output stream.  Essentially,
911to generate code you do this:
912```javascript
913var stream = UglifyJS.OutputStream(options);
914compressed_ast.print(stream);
915var code = stream.toString(); // this is your minified code
916```
917
918or, for a shortcut you can do:
919```javascript
920var code = compressed_ast.print_to_string(options);
921```
922
923As usual, `options` is optional.  The output stream accepts a lot of options,
924most of them documented above in section “Beautifier options”.  The two
925which we care about here are `source_map` and `comments`.
926
927#### Keeping comments in the output
928
929In order to keep certain comments in the output you need to pass the
930`comments` option.  Pass a RegExp (as string starting and closing with `/`
931or pass a RegExp object), a boolean or a function.  Stringified options
932`all` and `some` can be passed too, where `some` behaves like it's cli
933equivalent `--comments` without passing a value. If you pass a RegExp,
934only those comments whose body matches the RegExp will be kept.  Note that body
935means without the initial `//` or `/*`.  If you pass a function, it will be
936called for every comment in the tree and will receive two arguments: the
937node that the comment is attached to, and the comment token itself.
938
939The comment token has these properties:
940
941- `type`: "comment1" for single-line comments or "comment2" for multi-line
942  comments
943- `value`: the comment body
944- `pos` and `endpos`: the start/end positions (zero-based indexes) in the
945  original code where this comment appears
946- `line` and `col`: the line and column where this comment appears in the
947  original code
948- `file` — the file name of the original file
949- `nlb` — true if there was a newline before this comment in the original
950  code, or if this comment contains a newline.
951
952Your function should return `true` to keep the comment, or a falsy value
953otherwise.
954
955#### Generating a source mapping
956
957You need to pass the `source_map` argument when calling `print`.  It needs
958to be a `SourceMap` object (which is a thin wrapper on top of the
959[source-map][source-map] library).
960
961Example:
962```javascript
963var source_map = UglifyJS.SourceMap(source_map_options);
964var stream = UglifyJS.OutputStream({
965	...
966	source_map: source_map
967});
968compressed_ast.print(stream);
969
970var code = stream.toString();
971var map = source_map.toString(); // json output for your source map
972```
973
974The `source_map_options` (optional) can contain the following properties:
975
976- `file`: the name of the JavaScript output file that this mapping refers to
977- `root`: the `sourceRoot` property (see the [spec][sm-spec])
978- `orig`: the "original source map", handy when you compress generated JS
979  and want to map the minified output back to the original code where it
980  came from.  It can be simply a string in JSON, or a JSON object containing
981  the original source map.
982
983  [acorn]: https://github.com/ternjs/acorn
984  [source-map]: https://github.com/mozilla/source-map
985  [sm-spec]: https://docs.google.com/document/d/1U1RGAehQwRypUTovF1KRlpiOFze0b-_2gc6fAH0KY0k/edit
986  [codegen]: http://lisperator.net/uglifyjs/codegen
987  [compressor]: http://lisperator.net/uglifyjs/compress
988  [parser]: http://lisperator.net/uglifyjs/parser
989
990#### Support for `const`
991
992`const` in `uglify-js@2.x` has function scope and as such behaves much like
993`var` - unlike `const` in ES2015 (ES6) which has block scope. It is recommended
994to avoid using `const` for this reason as it will have undefined behavior when
995run on an ES2015 compatible browser.
996