Instantly share code, notes, and snippets.

Embed
What would you like to do?
Our 2 Webpack config files which we use to 1) Compile TypeScript files 2) Compile SASS files 3) ...and bundle them all up in a single `build.js` file
//
// webpack.dev.js
//
var loaders = require('./webpack.loaders');
var failPlugin = require('webpack-fail-plugin');
module.exports = {
entry: [
'./static/typescripts/index.ts',
],
output: {
filename: 'build.js',
path: 'static/dist',
},
plugins: [failPlugin],
resolve: {
root: __dirname,
extensions: ['', '.ts', '.js', '.json'],
},
resolveLoader: {
modulesDirectories: ['node_modules']
},
devtool: 'source-map',
module: {
loaders: loaders
},
};
//
// webpack.loaders.js
//
module.exports = [{
test: /\.tsx?$/,
loader: 'ng-annotate!awesome-typescript'
}, {
test: /\.jsx?$/,
loader: 'ng-annotate',
exclude: ['/node_modules/']
}, {
test: /\.html$/,
loader: 'html'
}, {
test: /\.css$/,
loader: 'style!css'
}, {
test: /\.scss$/,
loader: 'style!css!sass'
}, {
test: /\.png$/,
loader: "url?limit=10000"
}, {
test: /\.(jpg|ttf|eot|woff2?|svg)$/,
loader: "file"
}, ];
@sivabudh

This comment has been minimized.

Show comment
Hide comment
@sivabudh

sivabudh Jul 17, 2016

For what it's worth, this is our package.json.

{
  "name": "some-app",
  "version": "1.0",
  "description": "some description",
  "main": "index.js",
  "scripts": {
    "build": "webpack --config webpack/webpack.dev.js -p",
    "build:compose": "webpack --config webpack/webpack.compose.js -p",
    "postinstall": "typings install",
    "watch": "webpack --config webpack/webpack.dev.js --watch",
    "watch:compose": "webpack --config webpack/webpack.compose.js --watch"
  },
  "repository": {
    "type": "git",
    "url": "some-git-url"
  },
  "author": "some company",
  "license": "UNLICENSED",
  "bugs": {
    "url": "some-bugs-url"
  },
  "homepage": "some-home-age",
  "devDependencies": {
    "animate.css": "^3.5.1",
    "awesome-typescript-loader": "^1.1.1",
    "bootstrap": "^4.0.0-alpha.2",
    "css-loader": "^0.23.1",
    "file-loader": "^0.8.5",
    "html-loader": "^0.4.3",
    "ng-annotate-loader": "^0.1.0",
    "node-sass": "^3.7.0",
    "sass-loader": "^3.2.0",
    "style-loader": "^0.13.0",
    "webpack": "^1.13.1",
    "webpack-dev-server": "^1.14.1",
    "webpack-fail-plugin": "^1.0.4"
  },
  "dependencies": {
    "angular": "^1.5.7",
    "angular-chart.js": "^0.10.2",
    "angular-formly": "^8.2.1",
    "angular-ui-bootstrap": "^1.3.3",
    "angular-ui-router": "^1.0.0-alpha.5",
    "angular-xeditable": "^0.1.12",
    "api-check": "^7.5.5",
    "bootstrap-sidebar": "^0.2.2-retry",
    "font-awesome": "github:fortawesome/Font-Awesome",
    "jquery": "^2.2.1",
    "lodash": "^4.13.1",
    "moment": "^2.14.1",
    "ng-dialog": "^0.6.1",
    "ngstorage": "^0.3.10",
    "socket.io": "^1.4.5",
    "typescript": "^1.8.10",
    "typings": "^1.3.1"
  }
}
Owner

sivabudh commented Jul 17, 2016

For what it's worth, this is our package.json.

{
  "name": "some-app",
  "version": "1.0",
  "description": "some description",
  "main": "index.js",
  "scripts": {
    "build": "webpack --config webpack/webpack.dev.js -p",
    "build:compose": "webpack --config webpack/webpack.compose.js -p",
    "postinstall": "typings install",
    "watch": "webpack --config webpack/webpack.dev.js --watch",
    "watch:compose": "webpack --config webpack/webpack.compose.js --watch"
  },
  "repository": {
    "type": "git",
    "url": "some-git-url"
  },
  "author": "some company",
  "license": "UNLICENSED",
  "bugs": {
    "url": "some-bugs-url"
  },
  "homepage": "some-home-age",
  "devDependencies": {
    "animate.css": "^3.5.1",
    "awesome-typescript-loader": "^1.1.1",
    "bootstrap": "^4.0.0-alpha.2",
    "css-loader": "^0.23.1",
    "file-loader": "^0.8.5",
    "html-loader": "^0.4.3",
    "ng-annotate-loader": "^0.1.0",
    "node-sass": "^3.7.0",
    "sass-loader": "^3.2.0",
    "style-loader": "^0.13.0",
    "webpack": "^1.13.1",
    "webpack-dev-server": "^1.14.1",
    "webpack-fail-plugin": "^1.0.4"
  },
  "dependencies": {
    "angular": "^1.5.7",
    "angular-chart.js": "^0.10.2",
    "angular-formly": "^8.2.1",
    "angular-ui-bootstrap": "^1.3.3",
    "angular-ui-router": "^1.0.0-alpha.5",
    "angular-xeditable": "^0.1.12",
    "api-check": "^7.5.5",
    "bootstrap-sidebar": "^0.2.2-retry",
    "font-awesome": "github:fortawesome/Font-Awesome",
    "jquery": "^2.2.1",
    "lodash": "^4.13.1",
    "moment": "^2.14.1",
    "ng-dialog": "^0.6.1",
    "ngstorage": "^0.3.10",
    "socket.io": "^1.4.5",
    "typescript": "^1.8.10",
    "typings": "^1.3.1"
  }
}
@TheLarkInn

This comment has been minimized.

Show comment
Hide comment
@TheLarkInn

TheLarkInn Jul 17, 2016

So a few things I spot that I think could really help:

  • I noticed you are using full lodash and moment libraries. Lodash however has a webpack version of their libraries split up so that you only have to npm install the functions you use. Moment, I'm not sure if you can get a lighter version, however look into the noParse property. It speeds up performance by ignoring already built libs. May be useful to apply to angular and moment which can't really be broken apart.
  • Production builds are always going to be slower because of optimizations, but I would take a look at the -p flag and what it means in the webpack source. A lot of times personally I will roll without it and customize my sourcemap types manually.
  • The kind of sourcemaps you are generating right now are the slowest but most accurate kind. Maybe look into a cheap-eval-source-map for local development as well which will speed things up.
  • Since you use so many libs, take a look at the DllPlugin (and DllReferencePlugin). It allows you to create a vendor DLL bundle which is done in a separate build step (you would only have to build it once unless you change your vendors). Since this DLL bundle is pre-built, when you run your app build, all the time it would take to bundle and trace your vendor dependencies would be already taken care of. (I've heard this can drop build times by 70%).

TheLarkInn commented Jul 17, 2016

So a few things I spot that I think could really help:

  • I noticed you are using full lodash and moment libraries. Lodash however has a webpack version of their libraries split up so that you only have to npm install the functions you use. Moment, I'm not sure if you can get a lighter version, however look into the noParse property. It speeds up performance by ignoring already built libs. May be useful to apply to angular and moment which can't really be broken apart.
  • Production builds are always going to be slower because of optimizations, but I would take a look at the -p flag and what it means in the webpack source. A lot of times personally I will roll without it and customize my sourcemap types manually.
  • The kind of sourcemaps you are generating right now are the slowest but most accurate kind. Maybe look into a cheap-eval-source-map for local development as well which will speed things up.
  • Since you use so many libs, take a look at the DllPlugin (and DllReferencePlugin). It allows you to create a vendor DLL bundle which is done in a separate build step (you would only have to build it once unless you change your vendors). Since this DLL bundle is pre-built, when you run your app build, all the time it would take to bundle and trace your vendor dependencies would be already taken care of. (I've heard this can drop build times by 70%).
@skolsuper

This comment has been minimized.

Show comment
Hide comment
@skolsuper

skolsuper Jul 18, 2016

@TheLarkInn Thank you so much. I will run some benchmarks and let you know the improvement after these changes 👍

skolsuper commented Jul 18, 2016

@TheLarkInn Thank you so much. I will run some benchmarks and let you know the improvement after these changes 👍

@skolsuper

This comment has been minimized.

Show comment
Hide comment
@skolsuper

skolsuper Jul 18, 2016

Early results:
Baseline: webpack --config webpack/webpack.dev.js -p real 0m40.175s
Without -p: webpack --config webpack/webpack.dev.js real 0m12.080s
CheapEvalSourceMap: webpack --config webpack/webpack.dev.js real 0m9.467s

Since we're not using -p in development anyway, only the 2nd one really counts. Still a ~20% speed-up for almost zero effort.

Am now looking into DLLPlugin. FWIW, the docs and "example" on this are pretty spartan, is there a good writeup/blog post that explains this more for a beginner?

skolsuper commented Jul 18, 2016

Early results:
Baseline: webpack --config webpack/webpack.dev.js -p real 0m40.175s
Without -p: webpack --config webpack/webpack.dev.js real 0m12.080s
CheapEvalSourceMap: webpack --config webpack/webpack.dev.js real 0m9.467s

Since we're not using -p in development anyway, only the 2nd one really counts. Still a ~20% speed-up for almost zero effort.

Am now looking into DLLPlugin. FWIW, the docs and "example" on this are pretty spartan, is there a good writeup/blog post that explains this more for a beginner?

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment