Skip to content

Commit cccf156

Browse files
committed
Fix everything. it works.
1 parent 6ac2d2e commit cccf156

File tree

5 files changed

+92
-31
lines changed

5 files changed

+92
-31
lines changed

packages/webpack/src/loader.ts

Lines changed: 32 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -1,12 +1,37 @@
11
import * as ts from 'typescript';
2+
import {NgcWebpackPlugin} from './plugin';
23

34

45
// Super simple TS transpiler loader for testing / isolated usage. does not type check!
5-
export function ngcLoader(sourceFile: string) {
6-
return ts.transpileModule(sourceFile, {
7-
compilerOptions: {
8-
target: ts.ScriptTarget.ES5,
9-
module: ts.ModuleKind.ES2015,
10-
}
11-
}).outputText;
6+
export function ngcLoader(source: string) {
7+
const plugin = this._compilation._ngToolsWebpackPluginInstance as NgcWebpackPlugin;
8+
if (plugin && plugin instanceof NgcWebpackPlugin) {
9+
const cb: any = this.async();
10+
11+
plugin.done.then(() => {
12+
const result = ts.transpileModule(source, {
13+
compilerOptions: {
14+
target: ts.ScriptTarget.ES5,
15+
module: ts.ModuleKind.ES2015,
16+
}
17+
});
18+
19+
if (result.diagnostics && result.diagnostics.length) {
20+
let message = '';
21+
result.diagnostics.forEach(d => {
22+
message += d.messageText + '\n';
23+
});
24+
cb(new Error(message));
25+
}
26+
27+
cb(null, result.outputText, result.sourceMapText ? JSON.parse(result.sourceMapText) : null);
28+
});
29+
} else {
30+
return ts.transpileModule(source, {
31+
compilerOptions: {
32+
target: ts.ScriptTarget.ES5,
33+
module: ts.ModuleKind.ES2015,
34+
}
35+
}).outputText;
36+
}
1237
}

packages/webpack/src/plugin.ts

Lines changed: 32 additions & 21 deletions
Original file line numberDiff line numberDiff line change
@@ -1,9 +1,11 @@
1-
import {NgModule} from '@angular/core';
21
import * as ts from 'typescript';
2+
import * as path from 'path';
3+
4+
import {NgModule} from '@angular/core';
35
import * as ngCompiler from '@angular/compiler-cli';
46
import {tsc} from '@angular/tsc-wrapped/src/tsc';
5-
import * as path from 'path';
67

8+
import {patchReflectorHost} from './reflector_host';
79
import {WebpackResourceLoader} from './resource_loader';
810
import {createResolveDependenciesFromContextMap} from './utils';
911
import { AngularCompilerOptions } from '@angular/tsc-wrapped';
@@ -13,7 +15,10 @@ import { AngularCompilerOptions } from '@angular/tsc-wrapped';
1315
* Option Constants
1416
*/
1517
export type NgcCompilerMode = 'aot' | 'jit'
16-
18+
export interface EmittedFile {
19+
sourceMap: any,
20+
source: string
21+
}
1722

1823
export interface AngularWebpackPluginOptions {
1924
tsconfigPath?: string;
@@ -22,6 +27,8 @@ export interface AngularWebpackPluginOptions {
2227
entryModule?: string;
2328
project: string;
2429
baseDir: string;
30+
basePath: string;
31+
genDir: string;
2532
}
2633

2734

@@ -39,6 +46,7 @@ export class NgcWebpackPlugin {
3946
lazyRoutes: any;
4047
loader: any;
4148

49+
done: Promise<void>;
4250

4351
nmf: any = null;
4452
cmf: any = null;
@@ -61,12 +69,9 @@ export class NgcWebpackPlugin {
6169
this.projectPath = options.project;
6270
this.rootModule = rootModule;
6371
this.rootModuleName = rootNgModule;
64-
6572
this.compilerHost = ts.createCompilerHost(this.compilerOptions, true);
6673
this.program = ts.createProgram(this.files, this.compilerOptions, this.compilerHost);
67-
68-
this.reflectorHost = new ngCompiler.ReflectorHost(
69-
this.program, this.compilerHost, tsConfig.ngOptions);
74+
this.reflectorHost = new ngCompiler.ReflectorHost(this.program, this.compilerHost, this.angularCompilerOptions);
7075
this.reflector = new ngCompiler.StaticReflector(this.reflectorHost);
7176
}
7277

@@ -78,43 +83,50 @@ export class NgcWebpackPlugin {
7883
this.cmf = cmf;
7984
cmf.plugin('before-resolve', (request, callback) => {
8085
if (!request) {
81-
console.log(11);
8286
return callback();
8387
}
8488

8589
request.request = path.resolve(process.cwd(), 'app/ngfactory');
8690
request.recursive = true;
8791
request.dependencies.forEach(d => d.critical = false);
88-
console.log(1);
8992
return callback(null, request);
9093
});
9194
cmf.plugin('after-resolve', (result, callback) => {
9295
if (!result) {
93-
console.log(10);
9496
return callback();
9597
}
9698

9799
result.resource = path.resolve(process.cwd(), this.angularCompilerOptions.genDir + '/app');
98100
result.recursive = true;
99101
result.dependencies.forEach(d => d.critical = false);
100102
result.resolveDependencies = createResolveDependenciesFromContextMap((fs, cb) => {
101-
console.log(4);
102103
return cb(null, this.lazyRoutes);
103104
});
104105

105106
return callback(null, result);
106107
});
107108
});
108-
compiler.plugin('make', (compiler, cb) => this._make(compiler, cb));
109+
110+
compiler.plugin('make', (compilation, cb) => this._make(compilation, cb));
111+
compiler.plugin('after-emit', (compilation, cb) => {
112+
this.done = null;
113+
this.compilation = null;
114+
compilation._ngToolsWebpackPluginInstance = null;
115+
cb();
116+
});
109117
}
110118

111119
private _make(compilation, cb) {
112120
const rootModulePath = path.normalize(this.rootModule + '.ts');
113121
const rootModuleName = this.rootModuleName;
114122
this.compilation = compilation;
115-
this.loader = new WebpackResourceLoader(compilation);
116123

117-
const program = ts.createProgram(this.files, this.compilerOptions, this.compilerHost);
124+
if (this.compilation._ngToolsWebpackPluginInstance) {
125+
cb(new Error('A ngtools/webpack plugin already exist for this compilation.'));
126+
}
127+
this.compilation._ngToolsWebpackPluginInstance = this;
128+
129+
this.loader = new WebpackResourceLoader(compilation);
118130

119131
const i18nOptions = {
120132
i18nFile: undefined,
@@ -127,13 +139,16 @@ export class NgcWebpackPlugin {
127139
const codeGenerator = ngCompiler.CodeGenerator.create(
128140
this.angularCompilerOptions,
129141
i18nOptions,
130-
program,
142+
this.program,
131143
this.compilerHost,
132144
new ngCompiler.NodeReflectorHostContext(this.compilerHost),
133145
this.loader
134146
);
135147

136-
codeGenerator.codegen()
148+
// We need to temporarily patch the CodeGenerator until either it's patched or allows us
149+
// to pass in our own ReflectorHost.
150+
patchReflectorHost(codeGenerator);
151+
this.done = codeGenerator.codegen()
137152
.then(() => {
138153
// process the lazy routes
139154
const lazyModules = this._processNgModule(rootModulePath, rootModuleName, rootModulePath)
@@ -145,12 +160,8 @@ export class NgcWebpackPlugin {
145160
);
146161
return lazyRoutes;
147162
}, {});
148-
console.log(2, this.lazyRoutes);
149163
})
150-
.then(() => {
151-
console.log(3);
152-
cb()
153-
}, (err) => cb(err));
164+
.then(() => cb(), (err) => cb(err));
154165
}
155166

156167
private _processNgModule(mod: string, ngModuleName: string, containingFile: string): string[] {
Lines changed: 26 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,26 @@
1+
import {CodeGenerator} from '@angular/compiler-cli';
2+
3+
4+
/**
5+
* Patch the CodeGenerator instance to use a custom reflector host.
6+
*/
7+
export function patchReflectorHost(codeGenerator: CodeGenerator) {
8+
const reflectorHost = (codeGenerator as any).reflectorHost;
9+
const oldGIP = reflectorHost.getImportPath;
10+
11+
reflectorHost.getImportPath = function(containingFile: string, importedFile: string): string {
12+
// Hack together SCSS and LESS files URLs so that they match what the default ReflectorHost
13+
// is expected. We only do that for shimmed styles.
14+
const m = importedFile.match(/(.*)(\..+)(\.shim)(\..+)/);
15+
if (!m) {
16+
return oldGIP.call(this, containingFile, importedFile);
17+
}
18+
19+
// We call the original, with `css` in its name instead of the extension, and replace the
20+
// extension from the result.
21+
const [, baseDirAndName, styleExt, shim, ext] = m;
22+
const result = oldGIP.call(this, containingFile, baseDirAndName + '.css' + shim + ext);
23+
24+
return result.replace(/\.css\./, styleExt + '.');
25+
}
26+
}

packages/webpack/src/resource_loader.ts

Lines changed: 0 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -13,13 +13,11 @@ const SingleEntryPlugin = require('webpack/lib/SingleEntryPlugin');
1313

1414

1515
export class WebpackResourceLoader implements ResourceLoader {
16-
private _compilerName: string;
1716
private _context: string;
1817
private _uniqueId = 0;
1918

2019
constructor(private _compilation: any) {
2120
this._context = _compilation.context;
22-
this._compiler =
2321
}
2422

2523
private _compile(filePath: string, content: string): Promise<any> {

tests/e2e/assets/webpack/test-app/tsconfig.json

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -4,7 +4,8 @@
44
"moduleResolution": "node",
55
"target": "es5",
66
"noImplicitAny": false,
7-
"sourceMap": false,
7+
"sourceMap": true,
8+
"mapRoot": "",
89
"emitDecoratorMetadata": true,
910
"experimentalDecorators": true,
1011
"lib": [

0 commit comments

Comments
 (0)