From 48b9f0bdd50f50dfa0e75dc44f9f2d893a4c0f14 Mon Sep 17 00:00:00 2001 From: "Shlomi Assaf (shlassaf)" Date: Tue, 17 Jan 2017 21:03:54 +0200 Subject: [PATCH] feat: support import() spec Support the [Dynamic import proposal](https://github.com/tc39/proposal-dynamic-import) [TC39 Stage 3] as a loader (codegen). The import() construct is supported in webpack from 2.1.0-beta28 Also adds decprecation message then using async-system (System.import) as it will be removed from webpack 3+ BREAKING CHANGES: Typescript transform `import(...)` syntax into something. To use `ng-router-loader` with `async-import` code generator the `ng-router-loader` must run **AFTER** the TS compiler (e.g: awesome-typescript-loader), that is in a lower index in the loaders array. This also requires the code generators to emit ES5 code. SEE: https://github.com/Microsoft/TypeScript/issues/12364 --- package.json | 2 +- src/builtin_codegens.ts | 28 ++++++++++++++++++++++------ test/test.spec.ts | 15 ++++++++++++++- 3 files changed, 37 insertions(+), 8 deletions(-) diff --git a/package.json b/package.json index c12d01e..19f85b4 100644 --- a/package.json +++ b/package.json @@ -1,6 +1,6 @@ { "name": "ng-router-loader", - "version": "1.0.2", + "version": "2.0.0", "description": "Webpack loader for `NgModule` lazy loading using the angular router", "author": "Shlomi Assaf ", "license": "MIT", diff --git a/src/builtin_codegens.ts b/src/builtin_codegens.ts index 7019416..8d32b8b 100644 --- a/src/builtin_codegens.ts +++ b/src/builtin_codegens.ts @@ -6,7 +6,7 @@ function getRequireString(file: string, module: string): string { } export const syncCodeGen: LoaderCodeGen = - (file: string, module: string) => `loadChildren: () => ${getRequireString(file, module)}`; + (file: string, module: string) => `loadChildren: function() { return ${getRequireString(file, module)}; }`; export const ensureCodeGen: LoaderCodeGen = (file: string, module: string, loaderOptions: RouterLoaderOptions, @@ -15,27 +15,43 @@ export const ensureCodeGen: LoaderCodeGen = (file: string, module: string, const webpackChunkName = resourceOptions.chunkName ? `, '${resourceOptions.chunkName}'` : ''; const result = [ - `loadChildren: () => new Promise(function (resolve) {`, - ` (require as any).ensure([], function (require: any) {`, + `loadChildren: function() { return new Promise(function (resolve) {`, + ` require.ensure([], function (require) {`, ` resolve(${requireString});`, ` }${webpackChunkName});`, - `})` + `})}` ]; return loaderOptions.inline ? result.join('') : result.join('\n'); }; export const systemCodeGen: LoaderCodeGen = (file: string, module: string, opts: RouterLoaderOptions) => { + systemCodeGen['deprecated'](); const result = [ - `loadChildren: () => System.import('${file}')`, - ` .then( (module: any) => module['${module}'] )` + `loadChildren: function() { return System.import('${file}')`, + `.then( function(module) { return module['${module}']; } ); }` ]; return opts.inline ? result.join('') : result.join('\n'); }; +systemCodeGen['deprecated'] = () => { + console.warn('\nDEPRECATED: ng-router-loader "async-system" loader use the System.import construct which is deprecated in webpack 2 and will be removed in webpack 3, please use the "async-import" instead. (https://github.com/webpack/webpack/releases/tag/v2.1.0-beta.28)\n'); + systemCodeGen['deprecated'] = () => {}; +}; + +export const importCodeGen: LoaderCodeGen = (file: string, module: string, opts: RouterLoaderOptions) => { + const result = [ + `loadChildren: function() { return import('${file}')`, + ` .then( function(module) { return module['${module}']; } ); }` + ]; + + return opts.inline ? result.join('') : result.join('\n'); +}; + export const BUILT_IN_CODEGENS: Array<{ name: string, codeGen: LoaderCodeGen }> = [ { name: 'sync', codeGen: syncCodeGen }, { name: 'async-require', codeGen: ensureCodeGen }, + { name: 'async-import', codeGen: importCodeGen }, { name: 'async-system', codeGen: systemCodeGen } ]; diff --git a/test/test.spec.ts b/test/test.spec.ts index 03c78aa..104afe6 100644 --- a/test/test.spec.ts +++ b/test/test.spec.ts @@ -2,7 +2,7 @@ import * as Path from 'path'; import { expect } from 'chai'; import '../index'; // this will load the built in code generators. import * as options from '../src/options'; -import { syncCodeGen, ensureCodeGen, systemCodeGen } from '../src/builtin_codegens'; +import { syncCodeGen, ensureCodeGen, systemCodeGen, importCodeGen } from '../src/builtin_codegens'; import { Loader, ReplaceResult } from '../src/Loader'; import { wpFactory, WebpackMockFactory } from './testing/WebpackMock'; @@ -394,6 +394,19 @@ describe('Loader', () => { }); }); + it('should output async-import codegen', () => { + const loader = factory + .setOption('loader', 'async-import') + .toLoader(); + + return loader.replace(`loadChildren: 'app/module-container/child-module#ChildModule'`) + .then(mapToZero) + .then( (result: ReplaceResult) => { + expect(result.replacement).to.eql(importCodeGen(result.filePath, result.moduleName, loader.query, result.resourceQuery)); + }); + }); + + it('should output a custom codegen', () => { const loader = factory.toLoader(); function custom(file: string, module: string): string {