54 votes

Comment charger manuellement un module paresseux?

J'ai essayé de charger les modules sans routeur à l'aide d' SystemJsNgModuleLoader, mais ne pouvais pas le faire fonctionner:

this.loader.load(url).then(console.info);

Je reçois Cannot find module xxx quelque soit la chaîne de caractères que j'utilise pour l'URL (aboslute/url relatives/les chemins... essayé plusieurs options). J'ai regardé à travers le Routeur code source et ne pouvait pas trouver autre chose alors c' SystemJsNgModuleLoader. Je ne suis même pas sûr que je devrais être à l'aide de ce...


Cette question a été posée hier à l' ng-europe 2016 conférence - Miško & Matias répondu:

Miško Hevery: Il suffit de se procurer du module, à partir de là, vous pouvez obtenir le maintien de la composante de l'usine et vous pouvez charger dynamiquement des composants de l'usine de n'importe où vous voulez dans l'application. C'est exactement ce que le routeur n'en interne. Il est donc tout à fait détroit vers l'avant pour vous de le faire.

Matias Niemelä La seule chose à noter est que le [Ng]Module il y a quelque chose qui s'appelle entryComponents et qui identifie les éléments qui pourraient être paresseux chargé - c'est l'entrée dans le jeu de composants. Ainsi, lorsque vous avez des modules qui sont paresseux chargé, s'il vous plaît mettre les choses en entryComponents.

...mais ce n'est pas que le détroit de l'avant, sans les exemples et les pauvres docs sur le sujet (;

Quelqu'un sait comment faire pour charger les modules manuellement, sans l'aide d' Route.loadChildren? Comment trouver le module et ce qui est exactement le truc qu'il faut aller en entryComponents (j'ai lu la FAQ, mais ne peut pas essayer sans module de chargement)?

60voto

yurzui Points 85802

Quelqu'un sait comment faire pour charger les modules manuellement, sans l'aide de L'itinéraire.loadChildren?

Vous pouvez utiliser SystemJsNgModuleLoader pour obtenir le module de l'usine:

this.loader.load('./src/lazy.module#TestModule').then((factory: NgModuleFactory<any>) => {
  console.log(factory);
});

Voici à quoi ça peut ressembler:

paresseux.le module.ts

@Component({
  selector: 'test',
  template: `I'm lazy module`,
})
export class Test {}

@NgModule({
  imports: [CommonModule],
  declarations: [Test],
  entryComponents: [Test]
})
export class LazyModule {
  static entry = Test;
}

app.ts

import {
  Component, NgModule, ViewContainerRef,
  SystemJsNgModuleLoader, NgModuleFactory,
  Injector} from '@angular/core'
import {BrowserModule} from '@angular/platform-browser'

@Component({
  selector: 'my-app',
  template: `<h2>Test lazy loading module</h2>`,
})
export class AppComponent {
  constructor(
    private loader: SystemJsNgModuleLoader, 
    private inj: Injector, 
    private vcRef: ViewContainerRef) {}

  ngOnInit() {
     this.loader.load('./src/lazy.module#LazyModule')
       .then((moduleFactory: NgModuleFactory<any>) => {
         const moduleRef = moduleFactory.create(this.inj);
         const entryComponent = (<any>moduleFactory.moduleType).entry;
         const compFactory = 
               moduleRef.componentFactoryResolver.resolveComponentFactory(entryComponent);
         this.vcRef.createComponent(compFactory);
      });
  }
} 

@NgModule({
  imports: [ BrowserModule ],
  declarations: [ AppComponent ],
  providers: [SystemJsNgModuleLoader],
  bootstrap: [ AppComponent ]
})
export class AppModule {} 
this.loader.load('./src/test.module#TestModule').then((factory: NgModuleFactory<any>) => {
  console.log(factory);
});

Plunker Exemple

Il y a deux options à précompiler module pour AOT:

1) Angulaire de la CLI lazyModules options (depuis Angulaire 6)

Utilisation angulaire/cli construire en fonction de:

{
  "projects": {
    "app": {
      "architect": {
        "build": {
          "options": {
            "lazyModules": [  <====== add here all your lazy modules
              "src/path-to.module"
            ]
          }
        }
      }
    }
  }
} 

Voir

2) à l'Aide de provideRoutes de RouterModule

app.le module.ts

providers: [
  SystemJsNgModuleLoader,
  provideRoutes([
     { loadChildren: 'app/lazy/lazy.module#LazyModule' }
  ])
],

app.composante.ts

export class AppComponent implements  OnInit {
    title = 'Angular cli Example SystemJsNgModuleLoader.load';

    @ViewChild('container', { read: ViewContainerRef }) container: ViewContainerRef;

    constructor(private loader: SystemJsNgModuleLoader, private inj: Injector) {}

    ngOnInit() {
        this.loader.load('app/lazy/lazy.module#LazyModule').then((moduleFactory: NgModuleFactory<any>) => {
            const entryComponent = (<any>moduleFactory.moduleType).entry;
            const moduleRef = moduleFactory.create(this.inj);

            const compFactory = moduleRef.componentFactoryResolver.resolveComponentFactory(entryComponent);
            this.container.createComponent(compFactory);
        });
    }
}

Dépôt Github angulaires-cli-paresseux


Chargement différé avec webpack et AOT

Compilation à l'aide de ngc

L'initialisation du Compilateur en utilisant la suite d'usine

export function createJitCompiler () {
    return new JitCompilerFactory([{useDebug: false, useJit: true}]).createCompiler();
}

Dépôt Github

10voto

RomainLT Points 91

[Angulaire 6]

Bonjour,

Je partage ma solution ici car je n'ai pas trouver comment le lazyload sans routeur sur stackoverflow .

Le Yurzui's way fonctionne mais il utilise le Routeur module pour compiler le paresseux module alors que je n'ai pas envie de l'utiliser.

Dans notre src/angular.json le fichier, nous pouvons demander à l' @angulaire/cli pour compiler un module à part.

Pour que l'on ajoute l' lazyModules clé "projet" > "votre-application-name" > "architecte" > "build" > "options".

Comme ceci :

  "$schema": "./node_modules/@angular/cli/lib/config/schema.json",
  "version": 1,
  "newProjectRoot": "projects", 
  "projects": {
    "lazy-load-app": {
      "root": "",
      "sourceRoot": "src",
      "projectType": "application",
      "prefix": "app",
      "schematics": {},
      "architect": {
        "build": {
          "builder": "@angular-devkit/build-angular:browser",
          "options": {
            "outputPath": "dist/lazy-custom-element-app",
            "index": "src/index.html",
            "main": "src/main.ts",
            "polyfills": "src/polyfills.ts",
            "tsConfig": "src/tsconfig.app.json",
            "assets": [
              "src/favicon.ico",
              "src/assets"
            ],
            "styles": [
              "src/styles.css"
            ],
            "scripts": [],
            "lazyModules": [
              "src/app/lazy-load/lazy-load.module",
              "src/app/another-lazy-load/another-lazy-load.module"
            ]

ensuite, nous pouvons l'appeler et de charger le module compilé.

Comme ceci :

export class LoaderComponent implements OnInit {

      // tag where we gonna inject the lazyload module and his default compononent "entry"
      @ViewChild('container', { read: ViewContainerRef }) viewRef: ViewContainerRef;

      constructor(
        private loader:     NgModuleFactoryLoader,
        private injector:   Injector,
        private moduleRef:  NgModuleRef<any>,) {
      }

      ngOnInit(): void {
       this.loader.load(this.pathModuleTemplate).then((moduleFactory: NgModuleFactory<any>) => {
          // our module had a static property 'entry' that references the component that  want to load by default with the module
          const entryComponent = (<any>moduleFactory.moduleType).entry;
          const moduleRef = moduleFactory.create(this.injector);
          const compFactory = moduleRef.componentFactoryResolver.resolveComponentFactory(entryComponent);
          this.viewRef.createComponent(compFactory);
        });
      }
}

source: https://github.com/angular/angular-cli/blob/9107f3cc4e66b25721311b5c9272ec00c2dea46f/packages/angular_devkit/build_angular/src/server/schema.json

En espérant que cela peut aider quelqu'un :)

Prograide.com

Prograide est une communauté de développeurs qui cherche à élargir la connaissance de la programmation au-delà de l'anglais.
Pour cela nous avons les plus grands doutes résolus en français et vous pouvez aussi poser vos propres questions ou résoudre celles des autres.

Powered by:

X