When I wrote about “To use Angular CLI or not?”, I claimed that there was not much risk involved in starting a project with Angular CLI, since ng eject allowed you to change your mind later and jump to a vanilla Webpack setup.

This has changed since AngularCLI 6: the eject command is now disabled.

Relying on Angular CLI has just become a much bigger risk for your project.

When I wrote about “Angular vs. React: The CLI” I claimed that I have not yet had a mandatory reason to eject . In the meantime I have come across several cases where the is a need to modify the webpack config of an Angular CLI project, which could be achieved with eject … but not any more.

One reasons is an integration with three.js. Many three.js extension rely on the global variable THREE . The typical solution in a webpack build is to expose THREE globally via webpack config… bad luck, with Angular CLI v6 you don’t have that option any more.

Other solutions are much more hacky …

Another nasty example where you typically need access to the webpack configuration is when you want to use the popular library Moment.js.

Let me illustrate the problem:

npx @angular/cli@6.1 new my-project

cd my-project

npm i moment @types/moment

Now use Moment.js in your project, i.e. in main.ts :

import * as moment from 'moment'

console.log(moment());

Now run the build and have look at the bundle:

npm run build -- --prod --stats-json

npx webpack-bundle-analyzer dist/my-project/stats.json

You get the following scary picture:

The main bundle of your application has a size of 498 KB of which Moment.js is 329 KB! The biggest part of Moment.js consists of a bunch of locales, which you most probably do not need!

Of course this is a shortcoming of Moment.js in combination with webpack. This is not inherently a problem of the Angular CLI. However Moment.js is a very popular library, many Angular projects want/need to use it. Maybe only because some other library depends on Moment.js (many do!).

There is an easy fix for the problem: how-to-optimize-momentjs-with-webpack.

However you need to modify the webpack config… which is not possible in a plain Angular CLI project! Bummer!

The answer of the Angular CLI is: that this is unfortunate, but they can’t deal with such special cases… bummer again!

Note: create-react-app accepts that Moment.js, as a very common library, deserves special handling and solves the problem out of the box.

At this point your project has a problem…

Of course the JavaScript ecosystem has a solution for everything:

… but I don’t like that a “state-of-the-art” framework forces me into hacks like this.

A solution (sort of …)

With ngx-build-plus you can change the webpack configuration in an Angular CLI project without ejecting.

(Note: The section below was updated on 2018–12–29 for Angular CLI 7.1.4)

In the example from above you can do the following:

ng add ngx-build-plus

Add a file webpack.extra.js in the root of your project:

const webpack = require('webpack'); module.exports = {

plugins: [

new webpack.IgnorePlugin(/^\.\/locale$/, /moment$/),

]

}

And run:

npm run build -- --prod --stats-json --extra-webpack-config webpack.extra.js npx webpack-bundle-analyzer dist/my-project/stats.json

Yay! All the locales have disappeared from the bundle:

You have now solved the problem! … But did you consider the price of the solution?

At best I can congratulate someone for quickly and simply solving a problem on top of the shit that they are given. The only software that I like is one that I can easily understand and solves my problems.

- Ryan Dahl on Software

Yup, ngx-build-plus is yet another “arcane” library you now depend on. Are you prepared to maintain that library yourself?

For Angular CLI v7.1.4 using ngx-build-plus is a working solution.

… but ngx-build-plus is was broken for Angular CLI 6.2:

… bummer!

Note: There are other projects similar to ngx-build-plus, maybe they make you happy:

https://github.com/meltedspark/angular-cli-builders

https://github.com/Angular-RU/angular-cli-webpack

The source code for the above example is available here: https://github.com/jbandi/ng-moment-problem