Skip to content

Commit

Permalink
fix(@angular-devkit/build-angular): fix budgets for any script with d…
Browse files Browse the repository at this point in the history
…ifferential loading enabled

Fixes angular#19849
  • Loading branch information
mattlewis92 committed Jan 27, 2021
1 parent c561e73 commit 95a270e
Show file tree
Hide file tree
Showing 2 changed files with 181 additions and 4 deletions.
Original file line number Diff line number Diff line change
Expand Up @@ -5,6 +5,7 @@
* Use of this source code is governed by an MIT-style license that can be
* found in the LICENSE file at https://angular.io/license
*/
import { basename } from 'path';
import * as webpack from 'webpack';
import { Budget, Type } from '../browser/schema';
import { ProcessBundleFile, ProcessBundleResult } from '../utils/process-bundle';
Expand Down Expand Up @@ -181,6 +182,18 @@ abstract class Calculator {
.reduce((l, r) => l + r, 0);
}
}

protected getAssetSize(asset: Asset): number {
if (asset.name.endsWith('.js')) {
const processResult = this.processResults
.find((processResult) => processResult.original && basename(processResult.original.filename) === asset.name);
if (processResult?.original) {
return processResult.original.size;
}
}

return asset.size;
}
}

/**
Expand Down Expand Up @@ -246,7 +259,7 @@ class AllScriptCalculator extends Calculator {
calculate() {
const size = this.assets
.filter(asset => asset.name.endsWith('.js'))
.map(asset => asset.size)
.map(asset => this.getAssetSize(asset))
.reduce((total: number, size: number) => total + size, 0);

return [{size, label: 'total scripts'}];
Expand All @@ -260,7 +273,7 @@ class AllCalculator extends Calculator {
calculate() {
const size = this.assets
.filter(asset => !asset.name.endsWith('.map'))
.map(asset => asset.size)
.map(asset => this.getAssetSize(asset))
.reduce((total: number, size: number) => total + size, 0);

return [{size, label: 'total'}];
Expand All @@ -275,7 +288,7 @@ class AnyScriptCalculator extends Calculator {
return this.assets
.filter(asset => asset.name.endsWith('.js'))
.map(asset => ({
size: asset.size,
size: this.getAssetSize(asset),
label: asset.name,
}));
}
Expand All @@ -289,7 +302,7 @@ class AnyCalculator extends Calculator {
return this.assets
.filter(asset => !asset.name.endsWith('.map'))
.map(asset => ({
size: asset.size,
size: this.getAssetSize(asset),
label: asset.name,
}));
}
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -464,5 +464,169 @@ describe('bundle-calculator', () => {
message: jasmine.stringMatching('foo.ext exceeded maximum budget.'),
});
});

it('does *not* yield a combined differential bundle budget for any script', () => {
const budgets: Budget[] = [{
type: Type.AnyScript,
maximumError: '1kb',
}];
const stats = {
chunks: [
{
initial: true,
files: [ 'foo.js' ],
},
],
assets: [
{
name: 'main-es2015.js',
size: 1.25 * KB,
},
],
} as unknown as webpack.Stats.ToJsonOutput;
const processResults: ProcessBundleResult[] = [
{
name: '0',
// Individual builds are under budget, but combined they are over.
original: {
filename: '/home/main-es2015.js',
size: 0.5 * KB,
},
downlevel: {
filename: '/home/main-es5.js',
size: 0.75 * KB,
},
},
];

const failures = Array.from(checkBudgets(budgets, stats, processResults));

// Because individual builds are under budget, they are acceptable. Should
// **not** yield a combined build which is over budget.
expect(failures.length).toBe(0);
});

it('does *not* yield a combined differential bundle budget for all script', () => {
const budgets: Budget[] = [{
type: Type.AllScript,
maximumError: '1kb',
}];
const stats = {
chunks: [
{
initial: true,
files: [ 'foo.js' ],
},
],
assets: [
{
name: 'main-es2015.js',
size: 1.25 * KB,
},
],
} as unknown as webpack.Stats.ToJsonOutput;
const processResults: ProcessBundleResult[] = [
{
name: '0',
// Individual builds are under budget, but combined they are over.
original: {
filename: '/home/main-es2015.js',
size: 0.5 * KB,
},
downlevel: {
filename: '/home/main-es5.js',
size: 0.75 * KB,
},
},
];

const failures = Array.from(checkBudgets(budgets, stats, processResults));

// Because individual builds are under budget, they are acceptable. Should
// **not** yield a combined build which is over budget.
expect(failures.length).toBe(0);
});

it('does *not* yield a combined differential bundle budget for total budget', () => {
const budgets: Budget[] = [{
type: Type.All,
maximumError: '1kb',
}];
const stats = {
chunks: [
{
initial: true,
files: [ 'foo.js' ],
},
],
assets: [
{
name: 'main-es2015.js',
size: 1.25 * KB,
},
],
} as unknown as webpack.Stats.ToJsonOutput;
const processResults: ProcessBundleResult[] = [
{
name: '0',
// Individual builds are under budget, but combined they are over.
original: {
filename: '/home/main-es2015.js',
size: 0.5 * KB,
},
downlevel: {
filename: '/home/main-es5.js',
size: 0.75 * KB,
},
},
];

const failures = Array.from(checkBudgets(budgets, stats, processResults));

// Because individual builds are under budget, they are acceptable. Should
// **not** yield a combined build which is over budget.
expect(failures.length).toBe(0);
});

it('does *not* yield a combined differential bundle budget for individual file budget', () => {
const budgets: Budget[] = [{
type: Type.Any,
maximumError: '1kb',
}];
const stats = {
chunks: [
{
initial: true,
files: [ 'foo.js' ],
},
],
assets: [
{
name: 'main-es2015.js',
size: 1.25 * KB,
},
],
} as unknown as webpack.Stats.ToJsonOutput;
const processResults: ProcessBundleResult[] = [
{
name: '0',
// Individual builds are under budget, but combined they are over.
original: {
filename: '/home/main-es2015.js',
size: 0.5 * KB,
},
downlevel: {
filename: '/home/main-es5.js',
size: 0.75 * KB,
},
},
];

const failures = Array.from(checkBudgets(budgets, stats, processResults));

// Because individual builds are under budget, they are acceptable. Should
// **not** yield a combined build which is over budget.
expect(failures.length).toBe(0);
});
});
});

0 comments on commit 95a270e

Please sign in to comment.