中使用服务时出错

中使用服务时出错

本文介绍了尝试在动态创建的组件角度 5.1 中使用服务时出错的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

尝试在动态创建的组件中使用服务时,运行时出现此错误

When trying to use a service in dynamically created component We got this error at run time

错误错误:无法解析 class_1 的所有参数:(?).在 syntaxError (compiler.js:485)在 CompileMetadataResolver._getDependenciesMetadata (compiler.js:15664)在 CompileMetadataResolver._getTypeMetadata (compiler.js:15499)在 CompileMetadataResolver.getNonNormalizedDirectiveMetadata (compiler.js:15007)在 CompileMetadataResolver.loadDirectiveMetadata (compiler.js:14862)在 eval (compiler.js:34233)在 Array.forEach ()在 eval (compiler.js:34232)在 Array.forEach ()在 JitCompiler._loadModules (compiler.js:34229)

这是一个示例代码

  import { Compiler, Component, Injector, VERSION, ViewChild, NgModule, NgModuleRef, OnInit, ViewContainerRef } from '@angular/core';
    import { BrowserModule } from '@angular/platform-browser';
    import { RouterModule } from '@angular/router';
    import { CmsService } from "../../services/cms.service";

    @Component({
      selector: 'home-page',
      template: `
          <ng-container #vc></ng-container>
      `
    })

    export class HomePageComponent implements OnInit {
      constructor(private _compiler: Compiler, private _injector: Injector, private _m: NgModuleRef<any>) { }
      ngOnInit() {

      }
      @ViewChild('vc', { read: ViewContainerRef }) vc;
      ngAfterViewInit() {
        const tmpCmp = Component({ moduleId: module.id, templateUrl: '../../../assets/HomePage/home-page-rbu.component.html' })(
          class {
            constructor(public cms: CmsService) { }
            welcomeTXT: string;
            advertismentTXT: string;
            ngOnInit() {
              this.cms.getCMSItemValue('welcomeTXT').subscribe(res => {
                this.welcomeTXT = res;
              });
              this.cms.getCMSItemValue('advertismentTXT').subscribe(res => {
                this.advertismentTXT = res;
              });

            }
          });

        @NgModule({
          imports: [BrowserModule, RouterModule],
          declarations: [tmpCmp],
          providers: [CmsService]
        })
        class DynamicModule { }

        this._compiler.compileModuleAndAllComponentsAsync(DynamicModule)
          .then((factories) => {
            const f = factories.componentFactories[0];

            const cmpRef = f.create(this._injector, [], null, this._m);
            cmpRef.instance.name = 'dynamic';
            this.vc.insert(cmpRef.hostView);
          })
      }
    }

此示例代码在添加 CmsService 或任何角度服务之前运行良好我们正在使用 angular 5.1 和 angular-cli 1.5

this sample code was working fine before adding CmsService or any angular servicewe are using angular 5.1 and angular-cli 1.5

推荐答案

该问题的解决方法是使用 componentFactories 访问动态创建的组件的公共属性

Workaround for the issue is to access the public properties of the dynamic created componenet using the componentFactories

welcomeTXT: string;
advertismentTXT: string;

作为:

this._compiler.compileModuleAndAllComponentsAsync(DynamicModule)
  .then((factories) => {
    const f = factories.componentFactories[0];

    const cmpRef = f.create(this._injector, [], null, this._m);
    cmpRef.instance.welcomeTXT = _welcomeTXT;
    cmpRef.instance.advertismentTXT = _advertismentTXT;
    cmpRef.instance.visitorsCount = _visitorsCount;
    cmpRef.instance.name = 'dynamic';
    this.vc.insert(cmpRef.hostView);
  })

这是组件的完整代码:

import {  Compiler, Component, Injector, VERSION, ViewChild, NgModule, NgModuleRef, OnInit,  ViewContainerRef} from '@angular/core';
import { BrowserModule, DomSanitizer, SafeHtml } from '@angular/platform-browser';
import { RouterModule } from '@angular/router';
import { CmsService } from "../../services/cms.service";

@Component({
  selector: 'my-app',
  template: `
      <ng-container #vc></ng-container>
  `
})
export class HomePageComponent implements OnInit {
  @ViewChild('vc', { read: ViewContainerRef }) vc;

  constructor(private _compiler: Compiler, private _cms: CmsService, private _injector: Injector, private _m: NgModuleRef<any>, private sanitizer: DomSanitizer) { }
  ngOnInit() {

  }

  ngAfterViewInit() {
    let welcomeTXT: any = "";
    let advertismentTXT: any = "";
    let visitorsCount: number = 0;
    this._cms.getVisitorsCount().subscribe(res => {
      visitorsCount = res;
    });
    this._cms.getCMSItemValue('welcomeTXT').subscribe(res => {
      advertismentTXT = this.sanitizer.bypassSecurityTrustHtml(res);
      this._cms.getCMSItemValue('advertismentTEXT').subscribe(res => {
        welcomeTXT = this.sanitizer.bypassSecurityTrustHtml(res);
        this.CreateHomePageComponent(welcomeTXT, advertismentTXT, visitorsCount);
      });
    });
  }

  CreateHomePageComponent(_welcomeTXT: any, _advertismentTXT: any, _visitorsCount: number) {

    const tmpCmp = Component({ moduleId: module.id, templateUrl: '../../../assets/HomePage/home-page-rbu.component.html' })(
      class {
        welcomeTXT: string;
        advertismentTXT: string;
        visitorsCount: number = 0;
      });

    @NgModule({
      imports: [BrowserModule, RouterModule],
      declarations: [tmpCmp],
      providers: [CmsService]
    })
    class DynamicModule { }

    this._compiler.compileModuleAndAllComponentsAsync(DynamicModule)
      .then((factories) => {
        const f = factories.componentFactories[0];

        const cmpRef = f.create(this._injector, [], null, this._m);
        cmpRef.instance.welcomeTXT = _welcomeTXT;
        cmpRef.instance.advertismentTXT = _advertismentTXT;
        cmpRef.instance.visitorsCount = _visitorsCount;
        cmpRef.instance.name = 'dynamic';
        this.vc.insert(cmpRef.hostView);
      })
  }
}

我希望这对某人有所帮助

I wish this help someone

我们也可以将服务作为变量传递给visitorsCount

We can also pass the service as variable like visitorsCount

这篇关于尝试在动态创建的组件角度 5.1 中使用服务时出错的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持!

08-04 19:11