Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Add a Build Optimizer plugin to filter which files are processed #14998

Merged
merged 3 commits into from
Jul 10, 2019
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Jump to
Jump to file
Failed to load files.
Diff view
Diff view
6 changes: 6 additions & 0 deletions etc/api/angular_devkit/build_optimizer/src/_golden-api.d.ts
Original file line number Diff line number Diff line change
@@ -1,5 +1,11 @@
export declare function buildOptimizer(options: BuildOptimizerOptions): TransformJavascriptOutput;

export declare const buildOptimizerLoaderPath: string;

export declare class BuildOptimizerWebpackPlugin {
apply(compiler: Compiler): void;
}

export default function buildOptimizerLoader(this: webpack.loader.LoaderContext, content: string, previousSourceMap: RawSourceMap): void;

export declare function getFoldFileTransformer(program: ts.Program): ts.TransformerFactory<ts.SourceFile>;
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -5,6 +5,10 @@
* 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 {
BuildOptimizerWebpackPlugin,
buildOptimizerLoaderPath,
} from '@angular-devkit/build-optimizer';
import { tags } from '@angular-devkit/core';
import * as CopyWebpackPlugin from 'copy-webpack-plugin';
import * as path from 'path';
Expand Down Expand Up @@ -34,9 +38,6 @@ const TerserPlugin = require('terser-webpack-plugin');

// tslint:disable-next-line:no-any
const g: any = typeof global !== 'undefined' ? global : {};
export const buildOptimizerLoader: string = g['_DevKitIsLocal']
? require.resolve('@angular-devkit/build-optimizer/src/build-optimizer/webpack-loader')
: '@angular-devkit/build-optimizer/webpack-loader';

// tslint:disable-next-line:no-big-function
export function getCommonConfig(wco: WebpackConfigOptions): Configuration {
Expand Down Expand Up @@ -251,10 +252,11 @@ export function getCommonConfig(wco: WebpackConfigOptions): Configuration {

let buildOptimizerUseRule;
if (buildOptions.buildOptimizer) {
extraPlugins.push(new BuildOptimizerWebpackPlugin());
buildOptimizerUseRule = {
use: [
{
loader: buildOptimizerLoader,
loader: buildOptimizerLoaderPath,
options: { sourceMap: scriptsSourceMap },
},
],
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -7,14 +7,14 @@
*/
// tslint:disable
// TODO: cleanup this file, it's copied as is from Angular CLI.
import { buildOptimizerLoaderPath } from '@angular-devkit/build-optimizer';
import * as path from 'path';
import {
AngularCompilerPlugin,
AngularCompilerPluginOptions,
NgToolsLoader,
PLATFORM
} from '@ngtools/webpack';
import { buildOptimizerLoader } from './common';
import { WebpackConfigOptions, BuildOptions } from '../build-options';

function _pluginOptionsOverrides(
Expand Down Expand Up @@ -113,7 +113,7 @@ export function getAotConfig(wco: WebpackConfigOptions, i18nExtract = false) {
const loaders: any[] = [NgToolsLoader];
if (buildOptions.buildOptimizer) {
loaders.unshift({
loader: buildOptimizerLoader,
loader: buildOptimizerLoaderPath,
options: { sourceMap: buildOptions.sourceMap.scripts }
});
}
Expand Down
5 changes: 5 additions & 0 deletions packages/angular_devkit/build_optimizer/README.md
Original file line number Diff line number Diff line change
Expand Up @@ -186,7 +186,12 @@ export interface BuildOptimizerOptions {
## Webpack loader usage:

```typescript
import { BuildOptimizerWebpackPlugin } from '@angular-devkit/build-optimizer';

module.exports = {
plugins: [
new BuildOptimizerWebpackPlugin(),
]
module: {
rules: [
{
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -17,9 +17,33 @@ interface BuildOptimizerLoaderOptions {
sourceMap: boolean;
}

export const buildOptimizerLoaderPath = __filename;

const alwaysProcess = (path: string) =>
// Always process TS files.
path.endsWith('.ts') || path.endsWith('.tsx')
// Always process factory files.
|| path.endsWith('.ngfactory.js') || path.endsWith('.ngstyle.js');

export default function buildOptimizerLoader
(this: webpack.loader.LoaderContext, content: string, previousSourceMap: RawSourceMap) {
this.cacheable();

const skipBuildOptimizer = this._module
&& this._module.factoryMeta
&& this._module.factoryMeta.skipBuildOptimizer;

if (!alwaysProcess(this.resourcePath) && skipBuildOptimizer) {
// Skip loading processing this file with Build Optimizer if we determined in
// BuildOptimizerWebpackPlugin that we shouldn't.

// Webpack typings for previousSourceMap are wrong, they are JSON objects and not strings.
// tslint:disable-next-line:no-any
this.callback(null, content, previousSourceMap as any);

return;
}

const options: BuildOptimizerLoaderOptions = loaderUtils.getOptions(this) || {};

// Make up names of the intermediate files so we can chain the sourcemaps.
Expand All @@ -33,12 +57,11 @@ export default function buildOptimizerLoader
outputFilePath,
emitSourceMap: options.sourceMap,
isSideEffectFree: this._module
&& this._module.factoryMeta
&& this._module.factoryMeta.sideEffectFree,
&& this._module.factoryMeta
&& this._module.factoryMeta.sideEffectFree,
});

if (boOutput.emitSkipped || boOutput.content === null) {
// Webpack typings for previousSourceMap are wrong, they are JSON objects and not strings.
// tslint:disable-next-line:no-any
this.callback(null, content, previousSourceMap as any);

Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,33 @@

/**
* @license
* Copyright Google Inc. All Rights Reserved.
*
* 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 { Compiler } from 'webpack'; // tslint:disable-line:no-implicit-dependencies

export class BuildOptimizerWebpackPlugin {
apply(compiler: Compiler) {
compiler.hooks.normalModuleFactory.tap("BuildOptimizerWebpackPlugin", nmf => {
nmf.hooks.module.tap("BuildOptimizerWebpackPlugin", (module, data) => {
const resolveData = data.resourceResolveData;
if (resolveData && resolveData.descriptionFileData) {
// Only TS packages should use Build Optimizer.
const typings = resolveData.descriptionFileData.typings;
// Notes:
// - a TS package might not have defined typings but still use .d.ts files next to their
// .js files. We don't cover that case because the Angular Package Format (APF) calls for
// using the Typings field and Build Optimizer is geared towards APF. Maybe we could
// provide configuration options to the plugin to cover that case if there's demand.
// - a JS-only package that also happens to provides typings will also be flagged by this
// check. Not sure there's a good way to skip those.
module.factoryMeta.skipBuildOptimizer = !typings;
}

return module;
});
});
}
}
6 changes: 5 additions & 1 deletion packages/angular_devkit/build_optimizer/src/index.ts
Original file line number Diff line number Diff line change
Expand Up @@ -5,7 +5,11 @@
* 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
*/
export { default as buildOptimizerLoader } from './build-optimizer/webpack-loader';
export {
default as buildOptimizerLoader,
buildOptimizerLoaderPath,
} from './build-optimizer/webpack-loader';
export { BuildOptimizerWebpackPlugin } from './build-optimizer/webpack-plugin';
export { buildOptimizer } from './build-optimizer/build-optimizer';

export { transformJavascript } from './helpers/transform-javascript';
Expand Down