Tree Shaking simplified with Webpack!
Writing simple, clean, and efficient code is the most desirable quality that every developer seeks. Most of the time, there is an unused code that floats around when you import and export modules in JavaScript. The concept of tree shaking, or dead code elimination, plays a great role as it avoids a largely created bundle-size unused module that hampers the performance during the build procedure. Tree shaking is seen as one of the best practices followed by front-end developers that focuses on size and performance factors. Not limited to front-end, tree shaking can be followed as a go-to practice by all. Let’s see what the exact idea behind tree shaking is.
Principles behind Tree Shaking:
- Declare all your imports and exports for each of your modules.
- The bundler (Webpack, Rollup, etc.) will analyze the dependency tree during your compilation step.
- Any unused code that can be proved is automatically dropped from your final bundle or tree shook.
To carry out the tree shaking, do not forget to use the ES6 style for importing and exporting. Also, disable the transformation of ES modules syntax to another module type. Just set the value to false, as it will preserve the ES modules.
"amd" | "umd" | "systemjs" | "commonjs" | "cjs" | "auto" | false, defaults to "auto"
You can use Babel, which is a free and open-source JavaScript transcompiler, to transpile code. All your import and export statements are, by default, transpired down to CommonJS. This forces the webpack to de-optimize, and some trees may be left unshaken.
Tree Shaking with Webpack
To configure tree shaking in React, you should have a module bundler that will help you to bundle the entire codebase. Webpack is the most used module bundler, and its main purpose is to bundle JS files for usage in the browser.
Webpack supports tree-shaking, and it uses the babel-preset-env package. This package bundles the files and transforms them back into CommonJS modules. This makes it difficult to bundle using tree-shaking. To achieve tree-shaking while bundling the application, you will need some configurations that will enable tree-shaking with webpack. Let’s have a look at them -
// webpack.config.js const HtmlWebPackPlugin = require('html-webpack-plugin');
module.exports = { module: { rules: [ { test: /\.(js|jsx)$/, exclude: /node_modules/, use: { loader: babel-loader, /* This configuration aids babel-preset-env to disable transpiling of import or export modules to commonJS */ options: { presets: [ [ 'es2015', { modules: false }] ] } } } ] }, plugin: [ new HtmlWebPackPlugin ({ template: './src/index.html', fileName: './index.html' }); }
That's pretty simple, isn't it? However, before you go on to shake trees with webpack, there is another important concept that you should consider, and that is configuring the side effect. It is only visible when a function or expression modifies a state outside its context. Common examples of side effects include making a call to API, manipulating the DOM, or writing to a DB.
So, to make webpack aware of the state of the files, it’ll transpile, you should configure a change in either the package.json file or within the webpack.cofig.json. Here is how you can do that -
// package.json { "name": "Tree Shaking Project", "side-effects": false }
The following code snippet is in case if you specifically want to apply side effects -
// package.json { "name": "Tree Shaking Project", "side-effects": false, // when you want to notify webpack of files with side-effects. "side-effects": [ "name-of-file.js" ] }
Similarly, you can configure in webpack.config.json as follows -
// webpack.config.json module.exports = { modules: { rules: [ { test: /\.(js|jsx)$/, exclude: /node_modules/, use: { loader: babel-loader, side-effects: false } } ] } }
There are certain thumb rules that one should keep in mind in order to derive the advantage of tree-shaking with webpack, which are as follows -
- Configure the webpack option to ignore transpiling modules to CommonJS.
- Use ES2015 module syntax (i.e., import and export).
- Configure the side effects property option in package.json file of the project.
Tree-shaking is an efficient way to make your bundle lighter and more efficient. Although, there are some important aspects to tree shaking. You should always make sure that no compilers are able to transform your ES2015 module into CommonJS modules as this would be the default behavior of the Babel preset @babel/preset-env. Also, do not forget to add a side effects property to your package.json project’s file. Lastly, to enable various optimizations like minification and tree shaking, use the production mode configuration option. So, what are you waiting for? Try this procedure and share your experience in the comments section below. Till then, happy coding!