question-mark
Stuck on an issue?

Lightrun Answers was designed to reduce the constant googling that comes with debugging 3rd party libraries. It collects links to all the places you might be looking at while hunting down a tough bug.

And, if you’re still stuck at the end, we’re happy to hop on a call to see how we can help out.

Lazy-loading with new import syntax throws in AoT when routes are exported

See original GitHub issue

🐞 bug report

Affected Package

The issue is caused by package @angular/compiler

Is this a regression?

No

Description

When using the new lazy-loading import syntax with VE, if the lazy-loaded route is declared in a separate file, then the AoT compilation fails.

🔬 Minimal Reproduction

A repo is available to reproduce: https://github.com/cexbrayat/lazy-laoding-import

Running ng build --aot will trigger the error.

Basically, the problem happens when the routes are declared in a separate file: https://github.com/cexbrayat/lazy-laoding-import/blob/master/src/app/app.routes.ts#L3-L6

Note that if the routes are declared directly in app;module.ts the error does not occur.

🔥 Exception or Error


ERROR in src/app/app.module.ts(14,26): Error during template compile of 'AppModule'
  Function expressions are not supported in decorators in 'ROUTES'
    'ROUTES' contains the error at src/app/app.routes.ts(5,29)
      Consider changing the function expression into an exported function.

🌍 Your Environment

Angular Version:


Angular CLI: 8.0.0-beta.15
Node: 11.11.0
OS: darwin x64
Angular: 8.0.0-beta.13
... animations, common, compiler, compiler-cli, core, forms
... language-service, platform-browser, platform-browser-dynamic
... router

Package                           Version
-----------------------------------------------------------
@angular-devkit/architect         0.800.0-beta.15
@angular-devkit/build-angular     0.800.0-beta.15
@angular-devkit/build-optimizer   0.800.0-beta.15
@angular-devkit/build-webpack     0.800.0-beta.15
@angular-devkit/core              8.0.0-beta.15
@angular-devkit/schematics        8.0.0-beta.15
@angular/cli                      8.0.0-beta.15
@ngtools/webpack                  8.0.0-beta.15
@schematics/angular               8.0.0-beta.15
@schematics/update                0.800.0-beta.15
rxjs                              6.4.0
typescript                        3.4.3
webpack                           4.29.6

Anything else relevant?

This is about the VE support, the Ivy version works fine.

cc @filipesilva as we talked about on Slack.

Issue Analytics

  • State:closed
  • Created 4 years ago
  • Comments:12 (7 by maintainers)

github_iconTop GitHub Comments

2reactions
alexzuzacommented, Apr 17, 2019

Angular compiler supports lowering expessions like useValue, useFactory, data, id and loadChildren.

What happens here is that if you keep loadChildren expression in app.module.ts file or more precisely inside decorator (@NgModule) then compiler extracts your loadChildren expression in exported variable before processing AOT.


export const ɵ0 = () => import('./admin/admin.module').then(m => m.AdminModule);

@NgModule({
  ...
  imports: [
    ...
    RouterModule.forRoot([
      { path: '', loadChildren: ɵ0  }
    ])
  ],
})
export class AppModule { }

On the other hand, if you keep it as a part of exported variable in app.routes.ts file then compiler can’t lower it due to the this restriction:

https://github.com/angular/angular/blob/83291f01b084b834d8375ff5ac2366fb47ca15c0/packages/compiler-cli/src/transformers/lower_expressions.ts#L226-L228

How can we remedy this?

With a simple hack:

app.routes.ts

const ROUTES: Routes = [
  // { path: '', loadChildren: './admin/admin.module#AdminModule' }
  { path: '', loadChildren: () => import('./admin/admin.module').then(m => m.AdminModule) }
];

export { ROUTES };

This way compiler will lower loadChildren expression since it is not part of exported variable in AST structure.

1reaction
filipesilvacommented, Jul 23, 2019

I think the usecase is very legitimate, it’s just that we never managed to get it working well without Ivy, and then with Ivy there shouldn’t be a problem. The last comment (https://github.com/angular/angular-cli/issues/6373#issuecomment-453006158) also has a workaround for now that should work. Basically wrapping the lib module import in an app lazy module.

Read more comments on GitHub >

github_iconTop Results From Across the Web

Experimenting With Lazy Loaded Modules, Ahead Of Time ...
Ben Nadel shares the approach to lazy loading modules that he's finally got working with Angular 6.1.7, Webpack 4, and Ahead of Time...
Read more >
Pillar 3 — Lazy Loading, AOT, and Preloading - Angular inDepth
Lazy loading is a useful technique for faster initial page loads. With lazy loading, your application loads faster by shipping only the essential...
Read more >
angular6 feature module lazy loading throwing error TypeError
It is solved for me by removing import statement of lazy loaded module from app.module file. // remove this from app.module and app-routing....
Read more >
Angular Ahead of Time (AoT) Compilation, Lazy Loading and ...
In this blog post I want to show you how to get Ahead Of Time compilation enabled with lazy loading in combination with...
Read more >
AOT metadata errors - Angular
content_copy // CORRECTED import { Inject } from '@angular/core'; export const WINDOW = new InjectionToken('Window'); export function _window() { return window; } ...
Read more >

github_iconTop Related Medium Post

No results found

github_iconTop Related StackOverflow Question

No results found

github_iconTroubleshoot Live Code

Lightrun enables developers to add logs, metrics and snapshots to live code - no restarts or redeploys required.
Start Free

github_iconTop Related Reddit Thread

No results found

github_iconTop Related Hackernoon Post

No results found

github_iconTop Related Tweet

No results found

github_iconTop Related Dev.to Post

No results found

github_iconTop Related Hashnode Post

No results found