2017-06-14 119 views
1

我已經設置了一個新的Angular CLI項目,以瞭解如何使用Angular Universal啓用服務器端呈現。Angular 4通用延遲加載錯誤

我已經設置好了,一切都很好,但我決定延遲加載一個名爲「lazy」的模塊。我在使用ng serve的時候使用了它,但是當Universal運行(使用AOT)時,當我進入懶惰路由並刷新頁面時,雖然我在瀏覽器中看到了懶惰組件:

ERROR { Error: Uncaught (in promise): ReferenceError: System is not defined 
ReferenceError: System is not defined 
    at SystemJsNgModuleLoader.loadFactory (C:\Users\shachar\Desktop\universal\packages\core\src\linker\system_js_ng_module_factory_loader.ts:67:1) 
    at SystemJsNgModuleLoader.load (C:\Users\shachar\Desktop\universal\node_modules\@angular\core\bundles\core.umd.js:5724:35) 
    at RouterConfigLoader.loadModuleFactory (C:\Users\shachar\Desktop\universal\packages\router\src\router_config_loader.ts:71:1) 
    at RouterConfigLoader.load (C:\Users\shachar\Desktop\universal\node_modules\@angular\router\bundles\router.umd.js:3402:52) 
    at MergeMapSubscriber.project (C:\Users\shachar\Desktop\universal\node_modules\@angular\router\bundles\router.umd.js:1570:74) 
    at MergeMapSubscriber._tryNext (C:\Users\shachar\Desktop\universal\node_modules\rxjs\src\operator\mergeMap.ts:125:21) 
    at MergeMapSubscriber._next (C:\Users\shachar\Desktop\universal\node_modules\rxjs\src\operator\mergeMap.ts:115:12) 
    at MergeMapSubscriber.Subscriber.next (C:\Users\shachar\Desktop\universal\node_modules\rxjs\src\Subscriber.ts:95:12) 
    at ScalarObservable._subscribe (C:\Users\shachar\Desktop\universal\node_modules\rxjs\src\observable\ScalarObservable.ts:51:18) 
    at ScalarObservable.Observable._trySubscribe (C:\Users\shachar\Desktop\universal\node_modules\rxjs\src\Observable.ts:113:19) 
    at resolvePromise (C:\Users\shachar\Desktop\universal\node_modules\zone.js\dist\zone-node.js:770:31) 
    at resolvePromise (C:\Users\shachar\Desktop\universal\node_modules\zone.js\dist\zone-node.js:741:17) 
    at C:\Users\shachar\Desktop\universal\node_modules\zone.js\dist\zone-node.js:818:17 
    at ZoneDelegate.invokeTask (C:\Users\shachar\Desktop\universal\node_modules\zone.js\dist\zone-node.js:424:31) 
    at Object.onInvokeTask (C:\Users\shachar\Desktop\universal\packages\core\src\zone\ng_zone.ts:257:1) 
    at ZoneDelegate.invokeTask (C:\Users\shachar\Desktop\universal\node_modules\zone.js\dist\zone-node.js:423:36) 
    at Zone.runTask (C:\Users\shachar\Desktop\universal\node_modules\zone.js\dist\zone-node.js:191:47) 
    at drainMicroTaskQueue (C:\Users\shachar\Desktop\universal\node_modules\zone.js\dist\zone-node.js:584:35) 
    at Server.ZoneTask.invoke (C:\Users\shachar\Desktop\universal\node_modules\zone.js\dist\zone-node.js:490:25) 
    at emitTwo (events.js:106:13) 
    rejection: 
    { ReferenceError: System is not defined 
     at SystemJsNgModuleLoader.loadFactory (C:\Users\shachar\Desktop\universal\packages\core\src\linker\system_js_ng_module_factory_loader.ts:67:1) 
     at SystemJsNgModuleLoader.load (C:\Users\shachar\Desktop\universal\node_modules\@angular\core\bundles\core.umd.js:5724:35) 
     at RouterConfigLoader.loadModuleFactory (C:\Users\shachar\Desktop\universal\packages\router\src\router_config_loader.ts:71:1) 
     at RouterConfigLoader.load (C:\Users\shachar\Desktop\universal\node_modules\@angular\router\bundles\router.umd.js:3402:52) 
     at MergeMapSubscriber.project (C:\Users\shachar\Desktop\universal\node_modules\@angular\router\bundles\router.umd.js:1570:74) 
     at MergeMapSubscriber._tryNext (C:\Users\shachar\Desktop\universal\node_modules\rxjs\src\operator\mergeMap.ts:125:21) 
     at MergeMapSubscriber._next (C:\Users\shachar\Desktop\universal\node_modules\rxjs\src\operator\mergeMap.ts:115:12) 
     at MergeMapSubscriber.Subscriber.next (C:\Users\shachar\Desktop\universal\node_modules\rxjs\src\Subscriber.ts:95:12) 
     at ScalarObservable._subscribe (C:\Users\shachar\Desktop\universal\node_modules\rxjs\src\observable\ScalarObservable.ts:51:18) 
     at ScalarObservable.Observable._trySubscribe (C:\Users\shachar\Desktop\universal\node_modules\rxjs\src\Observable.ts:113:19) 
    __zone_symbol__currentTask: 
     ZoneTask { 
     _zone: [Object], 
     runCount: 0, 
     _zoneDelegates: null, 
     _state: 'notScheduled', 
     type: 'microTask', 
     source: 'Promise.then', 
     data: undefined, 
     scheduleFn: undefined, 
     cancelFn: null, 
     callback: [Function], 
     invoke: [Function] } }, 
    promise: 
    ZoneAwarePromise { 
    __zone_symbol__state: 0, 
    __zone_symbol__value: 
     { ReferenceError: System is not defined 
      at SystemJsNgModuleLoader.loadFactory (C:\Users\shachar\Desktop\universal\packages\core\src\linker\system_js_ng_module_factory_loader.ts:67:1) 
      at SystemJsNgModuleLoader.load (C:\Users\shachar\Desktop\universal\node_modules\@angular\core\bundles\core.umd.js:5724:35) 
      at RouterConfigLoader.loadModuleFactory (C:\Users\shachar\Desktop\universal\packages\router\src\router_config_loader.ts:71:1) 
      at RouterConfigLoader.load (C:\Users\shachar\Desktop\universal\node_modules\@angular\router\bundles\router.umd.js:3402:52) 
      at MergeMapSubscriber.project (C:\Users\shachar\Desktop\universal\node_modules\@angular\router\bundles\router.umd.js:1570:74) 
      at MergeMapSubscriber._tryNext (C:\Users\shachar\Desktop\universal\node_modules\rxjs\src\operator\mergeMap.ts:125:21) 
      at MergeMapSubscriber._next (C:\Users\shachar\Desktop\universal\node_modules\rxjs\src\operator\mergeMap.ts:115:12) 
      at MergeMapSubscriber.Subscriber.next (C:\Users\shachar\Desktop\universal\node_modules\rxjs\src\Subscriber.ts:95:12) 
      at ScalarObservable._subscribe (C:\Users\shachar\Desktop\universal\node_modules\rxjs\src\observable\ScalarObservable.ts:51:18) 
      at ScalarObservable.Observable._trySubscribe (C:\Users\shachar\Desktop\universal\node_modules\rxjs\src\Observable.ts:113:19) __zone_symbol__currentTask: [Object] } }, 
    zone: 
    Zone { 
    _properties: { isAngularZone: true }, 
    _parent: 
     Zone { 
     _properties: {}, 
     _parent: null, 
     _name: '<root>', 
     _zoneDelegate: [Object] }, 
    _name: 'angular', 
    _zoneDelegate: 
     ZoneDelegate { 
     _taskCounts: [Object], 
     zone: [Circular], 
     _parentDelegate: [Object], 
     _forkZS: null, 
     _forkDlgt: null, 
     _forkCurrZone: [Object], 
     _interceptZS: null, 
     _interceptDlgt: null, 
     _interceptCurrZone: [Object], 
     _invokeZS: [Object], 
     _invokeDlgt: [Object], 
     _invokeCurrZone: [Circular], 
     _handleErrorZS: [Object], 
     _handleErrorDlgt: [Object], 
     _handleErrorCurrZone: [Circular], 
     _scheduleTaskZS: [Object], 
     _scheduleTaskDlgt: [Object], 
     _scheduleTaskCurrZone: [Circular], 
     _invokeTaskZS: [Object], 
     _invokeTaskDlgt: [Object], 
     _invokeTaskCurrZone: [Circular], 
     _cancelTaskZS: [Object], 
     _cancelTaskDlgt: [Object], 
     _cancelTaskCurrZone: [Circular], 
     _hasTaskZS: [Object], 
     _hasTaskDlgt: [Object], 
     _hasTaskDlgtOwner: [Circular], 
     _hasTaskCurrZone: [Circular] } }, 
    task: 
    ZoneTask { 
    _zone: 
     Zone { 
     _properties: [Object], 
     _parent: [Object], 
     _name: 'angular', 
     _zoneDelegate: [Object] }, 
    runCount: 0, 
    _zoneDelegates: null, 
    _state: 'notScheduled', 
    type: 'microTask', 
    source: 'Promise.then', 
    data: undefined, 
    scheduleFn: undefined, 
    cancelFn: null, 
    callback: [Function], 
    invoke: [Function] } } 

不,我根本沒有使用SystemJS。

app.module.ts:

import { BrowserModule } from '@angular/platform-browser'; 
import { NgModule } from '@angular/core'; 
import { APP_BASE_HREF } from '@angular/common'; 
import { RouterModule } from '@angular/router'; 

import { AppComponent } from './app.component'; 
import { LazyModule } from './lazy/lazy.module'; 
import { HomeComponent } from './home/home.component'; 

@NgModule({ 
    declarations: [ 
    AppComponent, 
    HomeComponent 
    ], 
    imports: [ 
    BrowserModule.withServerTransition({ appId: 'universal' }), 
    RouterModule.forRoot([ 
     { 
     path: '', 
     component: HomeComponent 
     }, 
     { 
     path: 'lazy', 
     loadChildren: './lazy/lazy.module#LazyModule' 
     } 
    ]) 
    ], 
    providers: [{ provide: APP_BASE_HREF, useValue: '/' }], 
    bootstrap: [AppComponent] 
}) 
export class AppModule { } 

lazy.module.ts:

import { NgModule } from '@angular/core'; 
import { CommonModule } from '@angular/common'; 
import { RouterModule } from '@angular/router'; 

import { LazyComponent } from './lazy.component'; 

@NgModule({ 
    imports: [ 
    CommonModule, 
    RouterModule.forChild([ 
     { path: '', component: LazyComponent } 
    ]) 
    ], 
    declarations: [LazyComponent] 
}) 
export class LazyModule { } 

import { NgModule } from '@angular/core'; 
import { ServerModule } from '@angular/platform-server'; 
import { AppModule } from './app.module'; 
import { AppComponent } from './app.component'; 

@NgModule({ 
    imports: [ 
    ServerModule, 
    AppModule 
    ], 
    bootstrap: [AppComponent] 
}) 
export class AppServerModule { } 

server.ts:(快遞)

import 'reflect-metadata'; 
import 'zone.js/dist/zone-node'; 

import * as Express from 'express'; 
import { join } from 'path'; 
import { readFileSync } from 'fs'; 
import { renderModuleFactory } from '@angular/platform-server'; 
import { enableProdMode } from '@angular/core'; 

const { AppServerModuleNgFactory } = require('../dist/ngfactory/src/app/app.server.module.ngfactory'); 

const app = Express(); 

enableProdMode(); 

const PORT = 4000; 

const template = readFileSync(join(__dirname, '..', 'dist', 'index.html')).toString(); 

app.engine('html', (_, options, callback) => { 
    const opts = { document: template, url: options.req.url }; 

    renderModuleFactory(AppServerModuleNgFactory, opts) 
    .then(html => callback(null, html)); 
}); 

app.set('views', join(__dirname, '..', 'dist')); 
app.set('view engine', 'html'); 

app.get('*.*', Express.static(join(__dirname, '..', 'dist'))); 

app.get('*', (req, res) => { 
    res.render('index', { req }); 
}); 

app.listen(PORT,() => { 
    console.log(`Listening on port ${PORT}`); 
}); 

我很高興的是通用正在工作,但每次刷新都會收到此錯誤消息很糟糕。

+0

任何想法傢伙? – shabenda

回答

0

在服務器端呈現中存在Angular AOT CLI延遲加載問題。服務器不知道「系統」是角度的默認加載器。所以在這種情況下,需要通過webpack配置爲服務器端的模板加載添加angular2-template-loader'和'angular2-router-loader'。

+0

它也可以使用@ ngtools/webpack嗎?例如:['ngtools/webpack','angular2-template-loader','angular-router-loader'] –

0

目前不支持使用CLI捆綁器的延遲加載,請參閱here。它計劃在即將發佈的版本中進行,並且正在積極開發中,所以在此期間只需要緊張。