Angular2 UpgradeComponent 缺少 $injector

Angular2 UpgradeComponent missing $injector

我正在尝试升级 Angular1 组件并在我的 Angular2 应用程序中使用它,方法是遵循 "Using Angular 1 Component Directives from Angular 2 Code" 下的 the official Angular2 documentation here,但出现以下错误:

error_handler.js:54 TypeError: Cannot read property 'get' of undefined
    at ChartDirective.UpgradeComponent (upgrade_component.js:97)

仔细检查第 97 行,发现 this.$inspector 未定义:

我的代码很简单:

import { Directive, ElementRef, Injector } from '@angular/core';
import { UpgradeComponent } from '@angular/upgrade/static';

export const coolComponent = {
  template: 'cool',
  controller: function() {
  }
};

@Directive({
    selector: 'app-chart'
})
export class ChartDirective extends UpgradeComponent {

    constructor(elementRef: ElementRef, injector: Injector) {
        super('coolComponent', elementRef, injector);
    }
}

我的 main.ts 引导程序是:

import { platformBrowserDynamic } from '@angular/platform-browser-dynamic';

import { AppModule } from './app.module';

platformBrowserDynamic().bootstrapModule(AppModule);

这是问题的简化版本,重现步骤最少: https://github.com/dolanmiu/angular2-upgrade-test

angular-cli

生成

我遇到了类似的问题。为了解决我的问题,我从 AppModule 定义中删除了以下行:

bootstrap: [AppComponent]

就我而言,我还必须将 AppComponent 添加到我的 entryComponents 部分:

entryComponents: [AppComponent]

您还需要实施 ngDoBootstrap 方法,如果您还没有:

export class AppModule {
  ngDoBootstrap() {}
}

这是我创建的一个工作示例的 plunker。我遇到了与您描述的相同的问题。对我来说关键是降级我的 AppComponent 并将降级的组件放入 Angular 1 app:

import { App1Component } from './app1.component';
import { App } from './app';
import { downgradeComponent } from '@angular/upgrade/static';

angular.module('ng1', [])
  .directive(
      'ng2AppComponent',
      downgradeComponent({component: App})
    )
  .component('app1Component', App1Component);

index.html:

...
<body>
   <ng2-app-component></ng2-app-component>
</body>
...

然后我需要按照上面的描述将 AppComponent 移动到我的 AppModule 中的 entryComponents。

@NgModule({
  imports: [ BrowserModule, UpgradeModule ],
  declarations: [ App, App1Directive ],
  entryComponents: [ App ]
})
export class AppModule {
  ngDoBootstrap() {}
}

在我的示例中,降级的 Angular 2 AppComponent 位于 index.html 中,但您可以将其放置在您想要的任何 Angular 1 模板中,如果这对您的应用程序更有意义的话。

https://plnkr.co/edit/YSw63x10WAEivMWdNffj?p=preview

当您将 ng2 用于 bootstrap 您的应用程序时,它不能使用由 UpgradeComponent 升级的 ng1 指令。

您需要将 ng1 用于 bootstrap 应用程序和 ng2 组件,然后在 ng2 组件中使用 ng1 指令。

其中需要删除@NgModulebootstrap中的所有内容,并将AppComponent移动到entryComponents,然后清空AppModule中的ngDoBootstrap()

@NgModule({
    bootstrap: [  ],
    //...
    entryComponents: [
        AppComponent,
        //...
    ]
})
export class AppModule {
    public ngDoBootstrap() {}
}

之后,降级AppComponent:

import { AppComponent } from '../app.component';
import { downgradeComponent } from '@angular/upgrade/static';
//...
angular.directive(
    'app', downgradeComponent({
        component: AppComponent
    }) as angular.IDirectiveFactory
);

现在,您可以在 ng2 组件中渲染升级后的 ng1 指令。

更多详情:Angular2 UpgradeComponent missing $injector