How to minimize web package size?

I am writing a web application using react and webpack as my module. My jsx code is really bright, the size of the entire folder is 25 kb.

My bundle.js created from webpack is 2.2 mb. After performing the optimization using the -p flag, it reduces the packet to 700 kB, which is still extremely large.

I looked at the react.min.js file and its size is 130kb.

Is it possible that the web package creates such large files, or am I doing something wrong?

webpack.config.js

 var path = require('path'); var webpack = require('webpack'); module.exports = { entry: './public/components/main.jsx', output: { path: __dirname + "/public", filename: 'bundle.js' }, module: { loaders: [{ test: /.jsx?$/, loader: 'babel-loader', exclude: /node_modules/, query: { presets: ['es2015', 'react'] } }, { test: /\.css$/, loader: "style!css" }] } }; 

EDIT

package.json:

 { "name": "XChange", "version": "0.0.0", "private": true, "scripts": { "start": "node ./bin/www" }, "main": "./bin/www", "devDependencies": { "body-parser": "~1.13.2", "cookie-parser": "~1.3.5", "debug": "~2.2.0", "express": "~4.13.1", "jade": "~1.11.0", "morgan": "~1.6.1", "serve-favicon": "~2.3.0", "react-dom": "~0.14.3", "react": "~0.14.3", "webpack": "~1.12.9", "babel-loader": "~6.2.0", "babel-core": "~6.2.1", "babel-preset-react": "~6.1.18", "babel-preset-es2015": "~6.1.18", "react-bootstrap": "~0.28.1", "material-ui": "~0.14.0-rc1", "history": "~1.13.1", "react-router": "~1.0.2", "style-loader": "~0.13.0", "css-loader": "~0.18.0" }, "dependencies": { "express-validator": "~2.18.0", "mongoose": "~4.2.9", "kerberos": "~0.0.17", "bcrypt": "~0.8.5" } } 
+47
reactjs webpack
Dec 12 '15 at 12:15
source share
4 answers

According to your comments, you are using material-ui and react-bootstrap . These dependencies are associated with the web package along with your react and react-dom packages. Each time you require or import package, it is included with your package.

And here I guess. You are probably importing react-bootstrap and material-ui components using the library path:

 import { Button } from 'react-bootstrap'; import { FlatButton } from 'material-ui'; 

It is convenient and convenient, but these are not only Button and FlatButton (and their dependencies), but the library as a whole .

One way to make this easier is to try only import or require , which is, say, a component method. Using the same example:

 import Button from 'react-bootstrap/lib/Button'; import FlatButton from 'material-ui/lib/flat-button'; 

This will only bind Button , FlatButton and their respective dependencies. But not the whole library. Therefore, I would try to get rid of all your import libraries and use the component method.

If you do not use many components, this should significantly reduce the size of your linked file.

As an additional explanation:

When you use the library method, you import all of these reaction bootstraps and all these ui materials , regardless of which one you are actually using.

+82
Dec 12 '15 at 2:48
source share
— -

01/2017 EDIT . Since then, I learned a little more about the different Webpack plugins and wanted to update it. It turns out that UglifyJS has a small configuration of options that do not seem to be very popular, but can have a dramatic effect on your batch size. This is my current configuration with some annotations (the documents on the site are great):

  new webpack.optimize.UglifyJsPlugin({ comments: false, // remove comments compress: { unused: true, dead_code: true, // big one--strip code that will never execute warnings: false, // good for prod apps so users can't peek behind curtain drop_debugger: true, conditionals: true, evaluate: true, drop_console: true, // strips console statements sequences: true, booleans: true, } }) 

Once I came across an obscure problem with the uglify unicode unicode screen element, so be careful if you use these transforms to make such cross-like things possible.

For more information on specific webpack options, see webpack docs with some subsequent links for further reading.




(sidenote: I think your .json package is messy ... at least some of these dev dependencies depend on every package. json I have seen (e.g. react-starter-kit )

If you are preparing for production, you must take a few more steps to reduce the size of your file. Here is a snapshot of my webpack.config.js:

  plugins: [ new webpack.optimize.UglifyJsPlugin(), new webpack.optimize.DedupePlugin(), new webpack.DefinePlugin({ 'process.env': { 'NODE_ENV': JSON.stringify('production') } }) ], 

1) minimizes / removes your code

2) replaces duplicate code to minimize file size

3) tells webpack that it uses the things it uses to build the node

Finally, if you are using the original map (which you probably need), you will want to add the appropriate line. Sentry wrote a good blog post about this .

In my build I use devtool: 'source-map' for production

+26
Mar 24 '16 at 0:19
source share

UPDATED 05/18: update UglifyJsPlugin setting to better minimize

I use the below configuration to minimize in production code.

  plugins: [ new webpack.DefinePlugin({ 'process.env': { // This has effect on the react lib size 'NODE_ENV': JSON.stringify('production'), } }), new ExtractTextPlugin("bundle.css", {allChunks: false}), new webpack.optimize.AggressiveMergingPlugin(), new webpack.optimize.OccurrenceOrderPlugin(), new webpack.optimize.DedupePlugin(), new webpack.optimize.UglifyJsPlugin({ mangle: true, compress: { warnings: false, // Suppress uglification warnings pure_getters: true, unsafe: true, unsafe_comps: true, screw_ie8: true, conditionals: true, unused: true, comparisons: true, sequences: true, dead_code: true, evaluate: true, if_return: true, join_vars: true }, output: { comments: false, }, exclude: [/\.min\.js$/gi] // skip pre-minified libs }), new webpack.IgnorePlugin(/^\.\/locale$/, [/moment$/]), new CompressionPlugin({ asset: "[path].gz[query]", algorithm: "gzip", test: /\.js$|\.css$|\.html$/, threshold: 10240, minRatio: 0 }) ], 
+12
Jan 03 '17 at 0:04
source share

You looked at how you send scripts over the wire ... I had very simple reaction components, which were about 300 kb each, and that was after optimizing the web package. After they were gzipped, they went down to 38kb. Still significant - but this is what we get to use the functions of tomorrowrows today. If you are using node / express to serve static resources, including your javascript, look at compression ( https://github.com/expressjs/compression ). I also suggest looking at the node best practice guide for production https://expressjs.com/en/advanced/best-practice-performance.html If you are not using files through node, then apache (or another web server) will have options to compress text files.

+1
Aug 07 '16 at 20:09
source share



All Articles