I am writing some JavaScript which uses Moment.js and Handlebars. Moment.js is supposed to be 30 KB gzipped and Handlebars is supposed to be less than 10 KB gzipped. But when I use Webpack to bundle my code, I get a resulting file which is 271 KB!
I installed webpack-bundle-size-analyzer to investigate and found much larger files than expected:
$ webpack --json | webpack-bundle-size-analyzer
moment: 454.54 KB (74.1%)
handlebars: 94.39 KB (15.4%)
twitter-text: 62.3 KB (10.2%)
<self>: 1.94 KB (0.317%)
I have a feeling I am doing something which is causing a lot of unnecessary things to be loaded since I was expecting a final file size <100 KB.
main.js
var template = require('./template.handlebars')
var Handlebars = require('handlebars/runtime')
var twitter = require('twitter-text')
var moment = require('moment')
webpack.config.js
var path = require('path')
var webpack = require('webpack')
module.exports = {
entry: './src/main.js',
output: {
path: path.resolve(__dirname, './dist'),
publicPath: '/dist/',
filename: 'bundle.min.js'
},
resolveLoader: {
root: path.join(__dirname, 'node_modules')
},
module: {
loaders: [
{
test: /\.handlebars$/,
loader: 'handlebars-loader'
}
]
},
plugins: [
new webpack.optimize.UglifyJsPlugin({
compress: {
warnings: false
}
})
]
}
Using Production Mode in Webpack. Running your project in production mode reduces the bundle sizes compared to the development mode. Webpack provides a separate flag ( -p ) to enable this feature and removes all the white spaces and newlines in the code.
We recommend restricting pages to a maximum of < 300kb of script (compressed). Where possible, use code splitting to break up your code into small chunks of 50KB or less. That way, browsers can download JS resources in parallel, making full use of HTTP 2 multiplexing.
Every React developer should add compression to their bundling process. One of the most impactful techniques to reduce the bundle size of a React application is compression. compression is a process in which the size of a file is reduced by re-encoding the file data to use fewer bits of storage than the original file.
You may refer to this issue on github/moment. Basically you can eliminate out all other locales which you don't need.
Extract from the comments:
plugins: [
new webpack.ContextReplacementPlugin(/moment[\\\/]locale$/, /^\.\/(en|zh-tw)$/)
]
I think the webpack did its best already. When you look into the files in node_modules/moment/min/
You will see these:
220K moment-with-locales.min.js
57K moment.min.js
So, if you include the moment with locales, 2XXKB is making sense. To further reduce the size, you may try
include the moment without locales explicitly
var moment = require('moment/min/moment.min')
// if you dun need the locale support
Or you can try to compress your output with gz manually with this plugin compression-webpack-plugin.
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With