Skip to content

Commit 56deef3

Browse files
committed
feat(@angular/cli): name lazy chunks
Before: ``` $ ng build --no-progress Hash: ff03df269349b817eef4 Time: 11202ms chunk {0} 0.chunk.js, 0.chunk.js.map 1.61 kB {1} {3} [rendered] chunk {1} 1.chunk.js, 1.chunk.js.map 1.46 kB {0} {3} [rendered] chunk {2} polyfills.bundle.js, polyfills.bundle.js.map (polyfills) 160 kB {6} [initial] [rendered] chunk {3} main.bundle.js, main.bundle.js.map (main) 6.38 kB {5} [initial] [rendered] chunk {4} styles.bundle.js, styles.bundle.js.map (styles) 10.5 kB {6} [initial] [rendered] chunk {5} vendor.bundle.js, vendor.bundle.js.map (vendor) 2.16 MB [initial] [rendered] chunk {6} inline.bundle.js, inline.bundle.js.map (inline) 0 bytes [entry] [rendered] ``` After: ``` $ ng build --no-progress Hash: 2bc12a89f40f3b4818b5 Time: 9613ms chunk {feature.module} feature.module.chunk.js, feature.module.chunk.js.map 1.46 kB {lazy.module} {main} [rendered] chunk {inline} inline.bundle.js, inline.bundle.js.map (inline) 0 bytes [entry] [rendered] chunk {lazy.module} lazy.module.chunk.js, lazy.module.chunk.js.map 1.61 kB {feature.module} {main} [rendered] chunk {main} main.bundle.js, main.bundle.js.map (main) 6.38 kB {vendor} [initial] [rendered] chunk {polyfills} polyfills.bundle.js, polyfills.bundle.js.map (polyfills) 160 kB {inline} [initial] [rendered] chunk {styles} styles.bundle.js, styles.bundle.js.map (styles) 10.5 kB {inline} [initial] [rendered] chunk {vendor} vendor.bundle.js, vendor.bundle.js.map (vendor) 2.16 MB [initial] [rendered] ``` Fix #6700
1 parent 64e6b94 commit 56deef3

File tree

7 files changed

+64
-4
lines changed

7 files changed

+64
-4
lines changed

packages/@angular/cli/models/webpack-configs/common.ts

+3-1
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,7 @@
11
import * as webpack from 'webpack';
22
import * as path from 'path';
33
import { GlobCopyWebpackPlugin } from '../../plugins/glob-copy-webpack-plugin';
4+
import { NamedLazyChunksWebpackPlugin } from '../../plugins/named-lazy-chunks-webpack-plugin';
45
import { extraEntryParser, getOutputHashFormat } from './utils';
56
import { WebpackConfigOptions } from '../webpack-config';
67

@@ -109,7 +110,8 @@ export function getCommonConfig(wco: WebpackConfigOptions) {
109110
].concat(extraRules)
110111
},
111112
plugins: [
112-
new webpack.NoEmitOnErrorsPlugin()
113+
new webpack.NoEmitOnErrorsPlugin(),
114+
new NamedLazyChunksWebpackPlugin(),
113115
].concat(extraPlugins),
114116
node: {
115117
fs: 'empty',

packages/@angular/cli/models/webpack-configs/production.ts

+1-1
Original file line numberDiff line numberDiff line change
@@ -97,7 +97,7 @@ export const getProdConfig = function (wco: WebpackConfigOptions) {
9797
new webpack.EnvironmentPlugin({
9898
'NODE_ENV': 'production'
9999
}),
100-
new (<any>webpack).HashedModuleIdsPlugin(),
100+
new webpack.HashedModuleIdsPlugin(),
101101
new webpack.optimize.UglifyJsPlugin(<any>{
102102
mangle: { screw_ie8: true },
103103
compress: { screw_ie8: true, warnings: buildOptions.verbose },
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,41 @@
1+
import * as webpack from 'webpack';
2+
3+
4+
// This just extends webpack.NamedChunksPlugin to prevent name collisions.
5+
export class NamedLazyChunksWebpackPlugin extends webpack.NamedChunksPlugin {
6+
constructor() {
7+
const nameMap = new Map();
8+
// Append a dot and number if the name already exists.
9+
const getNextName = (baseName: string) => {
10+
let num: number | null = null;
11+
const name = () => num !== null ? `${baseName}.${num}` : baseName;
12+
while (nameMap.has(name())) {
13+
num = num ? num++ : 0;
14+
}
15+
nameMap.set(name(), true);
16+
return name();
17+
};
18+
19+
const nameResolver = (chunk: any) => {
20+
// Entry chunks have a name already, use it.
21+
if (chunk.name) {
22+
return chunk.name;
23+
}
24+
25+
// Try to figure out if it's a lazy loaded route.
26+
if (chunk.blocks
27+
&& chunk.blocks.length > 0
28+
&& chunk.blocks[0].dependencies
29+
&& chunk.blocks[0].dependencies.length > 0
30+
&& chunk.blocks[0].dependencies[0].lazyRouteChunkName
31+
) {
32+
// lazyRouteChunkName was added by @ngtools/webpack.
33+
return getNextName(chunk.blocks[0].dependencies[0].lazyRouteChunkName);
34+
}
35+
36+
return null;
37+
};
38+
39+
super(nameResolver);
40+
}
41+
}

packages/@angular/cli/plugins/webpack.js

+3-1
Original file line numberDiff line numberDiff line change
@@ -6,5 +6,7 @@ module.exports = {
66
GlobCopyWebpackPlugin: require('../plugins/glob-copy-webpack-plugin').GlobCopyWebpackPlugin,
77
SuppressExtractedTextChunksWebpackPlugin:
88
require('../plugins/suppress-entry-chunks-webpack-plugin')
9-
.SuppressExtractedTextChunksWebpackPlugin
9+
.SuppressExtractedTextChunksWebpackPlugin,
10+
NamedLazyChunksWebpackPlugin:
11+
require('../plugins/named-lazy-chunks-webpack-plugin').NamedLazyChunksWebpackPlugin
1012
};

packages/@angular/cli/tasks/eject.ts

+1
Original file line numberDiff line numberDiff line change
@@ -175,6 +175,7 @@ class JsonWebpackSerializer {
175175
this._addImport('webpack.optimize', 'UglifyJsPlugin');
176176
break;
177177
case angularCliPlugins.BaseHrefWebpackPlugin:
178+
case angularCliPlugins.NamedLazyChunksWebpackPlugin:
178179
case angularCliPlugins.SuppressExtractedTextChunksWebpackPlugin:
179180
this._addImport('@angular/cli/plugins/webpack', plugin.constructor.name);
180181
break;
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,10 @@
1+
import * as webpack from 'webpack';
2+
3+
declare module 'webpack' {
4+
export class NamedChunksPlugin {
5+
constructor(nameResolver: (chunk: any) => string | null);
6+
}
7+
export class HashedModuleIdsPlugin {
8+
constructor();
9+
}
10+
}

packages/@ngtools/webpack/src/plugin.ts

+5-1
Original file line numberDiff line numberDiff line change
@@ -310,7 +310,11 @@ export class AotPlugin implements Tapable {
310310
.map((key) => {
311311
const value = this._lazyRoutes[key];
312312
if (value !== null) {
313-
return new ContextElementDependency(value, key);
313+
const dep = new ContextElementDependency(value, key);
314+
// lazyRouteChunkName is used by webpack.NamedChunksPlugin to give the
315+
// lazy loaded chunk a name.
316+
dep.lazyRouteChunkName = path.basename(key, '.ts');
317+
return dep;
314318
} else {
315319
return null;
316320
}

0 commit comments

Comments
 (0)