✂️ An ES6+ aware minifier based on the Babel toolchain (beta)
JavaScript Python Shell
Latest commit 2b98b98 Jan 19, 2017 @boopathi boopathi committed with kangax Add mark eval scopes helper and deopt DCE fn unused params (#371)
* Add mark eval scopes

* Fix readme bug as a result of copy-pasting

* Add more tests

* Use Symbol for EVAL_SCOPE_MARKER

* Fix lint

README.md

babili (babel-minify)

An ES6+ aware minifier based on the Babel toolchain.

Travis Status Slack Status NPM Downloads

Table of Contents

Requirements

  • node >= 4
  • babel >= 6.20.0

Why

Current tools don't support targeting the latest version of ECMAScript. (yet)

  • Babili can because it is just a set of Babel plugins, and Babel already understands new syntax with our parser Babylon.
  • When it's possible to only target browsers that support newer ES features, code sizes can be smaller because you don't have to transpile and then minify.

Check out our blog post for more info!

// Example ES2015 Code
class Mangler {
  constructor(program) {
    this.program = program;
  }
}
new Mangler(); // without this it would just output nothing since Mangler isn't used

Before

// ES2015+ code -> Babel -> Babili/Uglify -> Minified ES5 Code
var a=function a(b){_classCallCheck(this,a),this.program=b};new a;

After

// ES2015+ code -> Babili -> Minified ES2015+ Code
class a{constructor(b){this.program=b}}new a;

CLI

Package Version Dependencies
babili npm Dependency Status

This is simple wrapper around the regular babel-cli and thus takes in the same cli options as running babel on its own. You can use this if you don't already use babel or want to run it standalone.

Install

npm install babili --save-dev

Usage

babili src -d lib

Equivalent to:

babel src -d lib --presets=babili --no-babelrc

Babel preset

Package Version Dependencies
babel-preset-babili npm Dependency Status

Install

npm install babel-preset-babili --save-dev

Usage

You'll most likely want to use it only in the production environment. Check out the env docs for more help.

Options specific to a certain environment are merged into and overwrite non-env specific options.

.babelrc:

{
  "presets": ["es2015"],
  "env": {
    "production": {
      "presets": ["babili"]
    }
  }
}

Then you'll need to set the env variable which could be something like BABEL_ENV=production npm run build

Individual Plugins

The babili repo is comprised of many npm packages. It is a lerna monorepo similar to babel itself.

The npm package babel-preset-babili is at the path packages/babel-preset-babili

Package Version Dependencies
babel-plugin-minify-constant-folding npm Dependency Status
babel-plugin-minify-dead-code-elimination npm Dependency Status
babel-plugin-minify-flip-comparisons npm Dependency Status
babel-plugin-minify-guarded-expressions npm Dependency Status
babel-plugin-minify-infinity npm Dependency Status
babel-plugin-minify-mangle-names npm Dependency Status
babel-plugin-minify-replace npm Dependency Status
babel-plugin-minify-simplify npm Dependency Status
babel-plugin-minify-type-constructors npm Dependency Status
babel-plugin-transform-member-expression-literals npm Dependency Status
babel-plugin-transform-merge-sibling-variables npm Dependency Status
babel-plugin-transform-minify-booleans npm Dependency Status
babel-plugin-transform-property-literals npm Dependency Status
babel-plugin-transform-simplify-comparison-operators npm Dependency Status
babel-plugin-transform-undefined-to-void npm Dependency Status

Usage

Normally you wouldn't be consuming the plugins directly since the preset is available.

Add to your .babelrc's plugins array.

{
  "plugins": ["babel-plugin-transform-undefined-to-void"]
}

Other

Package Version Dependencies
babel-plugin-minify-empty-function npm Dependency Status
babel-plugin-transform-inline-environment-variables npm Dependency Status
babel-plugin-transform-node-env-inline npm Dependency Status
babel-plugin-transform-remove-console npm Dependency Status
babel-plugin-transform-remove-debugger npm Dependency Status

Benchmarks

Bootstrap: npm run bootstrap Build: npm run build

Running the benchmarks: ./scripts/benchmark.js <package>[@version] [relative-path/file.js] - defaults to the package's main file if no file provided.

Backbone.js v1.2.3:

           raw     raw win gzip   gzip win parse time run
uglify              21.68kB 222%    7.26kB 170%     2ms        231ms
closure             21.57kB 223%    7.33kB 168%     2ms        1230ms
babili (best speed) 21.81kB 220%    7.44kB 163%     2ms        747ms
babili (best size)  21.81kB 220%    7.44kB 163%     2ms        600ms
closure js          23.9kB  192%    8kB    145%     2ms        2128ms

Run with: ./scripts/benchmark.js backbone@1.2.3

React v0.14.3:

          raw      raw win gzip    gzip win parse time run
closure             171.46kB 265%    52.97kB 168%     13ms       2637ms
uglify              176.36kB 255%    53.13kB 167%     11ms       1148ms
babili (best speed) 176.67kB 255%    55.1kB  157%     12ms       4139ms
babili (best size)  176.67kB 255%    55.1kB  157%     15ms       3683ms
closure js          312.64kB 100%    70.86kB 100%     14ms       1363ms

Run with: ./scripts/benchmark.js react@0.14.3 react/dist/react.js

jQuery v1.11.3:

           raw      raw win gzip    gzip win parse time run
uglify              94.27kB  195%    32.78kB 153%     8ms        850ms
closure             94.14kB  195%    33.38kB 148%     10ms       1905ms
closure js          95.64kB  190%    33.78kB 146%     7ms        6934ms
babili (best speed) 102.78kB 170%    35.32kB 135%     8ms        4563ms
babili (best size)  102.78kB 170%    35.32kB 135%     7ms        4261ms

Run with: ./scripts/benchmark.js jquery@1.11.3

Three.js:

           raw      raw win gzip     gzip win parse time run
closure             472.57kB 107%    122.22kB 61%      34ms       4767ms
uglify              478.79kB 104%    122.53kB 61%      34ms       2781ms
closure js          480.11kB 104%    123.44kB 60%      32ms       65423ms
babili (best speed) 506.99kB 93%     128.22kB 54%      39ms       13503ms
babili (best size)  506.99kB 93%     128.22kB 54%      32ms       12605ms

Run with: ./scripts/benchmark.js three@0.82.1 three/build/three.js

Browser support

Babili is best at targeting latest browsers (with full ES6+ support) but can also be used with the usual Babel es2015 preset to transpile down the code first.

Team

Amjad Masad Boopathi Rajaa Juriy Zaytsev Henry Zhu
Amjad Masad Boopathi Rajaa Juriy Zaytsev Henry Zhu
@amasad @boopathi @kangax @hzoo
@amasad @heisenbugger @kangax @left_pad