2

I have followed the tutorial to add webpack to Angular from here. If I understand correctly we feed the main module to webpack and then it traverses the whole tree and adds all the referenced files to the bundle. I have also read that we can optimize this by using tree-shaking.

What I don't understand here is why do we need tree-shaking if webpack already scans for only "used" modules (i.e. the ones we "import").

Does tree-shaking do something additional (like checking the classes from the modules that are not used and removing them from the module even though it's imported?) or I misunderstand the concept alltogether?

Ilya Chernomordik
  • 27,817
  • 27
  • 121
  • 207
  • 3
    Yes, we do. Tree-shaking is about shaking off unused parts of imported modules. Yes, it does 'something additional'. – Estus Flask Nov 06 '16 at 13:58
  • I see. so if module A imports module B with classes B1 and B2, but module A only uses B1, then tree-shaking "deletes" B2 from the output? – Ilya Chernomordik Nov 06 '16 at 14:03
  • @estus You can add the answer then, I'll accept it :) – Ilya Chernomordik Nov 06 '16 at 14:16
  • In theory, yes. In my own experience Webpack 2 did half-hearted job on tree-shaking (it depends on build config, and the feature is in beta also). – Estus Flask Nov 06 '16 at 16:24
  • Wondering how it does figure out it's not used? Stupid test search in a file? Since js is not statically compiled I am really wondering how they do it. – Ilya Chernomordik Nov 06 '16 at 16:26
  • `import` and `export` statements follow strict syntax exactly to let them be statically analyzed. If exported item isn't imported or isn't used, the export for this item won't be defined in bundled app, at least this is how it was in my builds. – Estus Flask Nov 06 '16 at 16:53

1 Answers1

1

As mentioned in the comments, the real benefit is that it can remove some code from the files, while without tree-shaking there will be the whole module in the result even if just one of the exported classed are used.

Example:

app.component.ts

export class AppComponent {

    test(): void {
        console.log("12345");
    }
}

export class AppComponentDeadCode {

    test(): void {
        console.log("54321");
    }
}

app.module.ts

import { AppComponent } from './app.component';

Now in this example we never import AppComponentDeadCode class.

  • Without tree-shaking both of the classes will be in the resulting module/bundle.
  • With tree-shaking the class AppComponentDeadCode will be removed from the resulting module/bundle (considering there are no other modules that import it).

P.S. Unfortunately the state of this shiny toy is quite "beta" and it's hard to achieve the result easily if at all with typescript/angular2. More information about it here.

Community
  • 1
  • 1
Ilya Chernomordik
  • 27,817
  • 27
  • 121
  • 207