While bootstrapping a hybrid angular 1 + 2 application, how do you initialize the angular 1 injector?

843 views Asked by At

To recreate the issue, I forked the Angular Quickstart plunker.

I have this simple angular 1.x module:

'use strict';

angular.module('testModule', [])
  .factory('testService', function($q, $log, $interval, $rootScope){
    //Create a service object that we'll build up with methods and eventually
    //return.
    var service = {};
    service.test = 'test';
    return service;
  }); 

I have this angular 2 module which references the angular 1.x $injector to get the angular 1.x module as a provider:

import { NgModule } from '@angular/core';
import { BrowserModule } from '@angular/platform-browser';
import { UpgradeModule } from '@angular/upgrade/static';
import { AppComponent } from './app.component';

@NgModule({
  imports: [
    BrowserModule,
    UpgradeModule
  ],

  declarations: [
    AppComponent
  ],
  bootstrap: [ AppComponent ],
  providers: [{
    provide: 'testModule',
    useFactory: (i: any) => i.get('testModule'),
    deps: ['$injector']
  }]

})

export class AppModule {
  ngDoBootstrap() {}
}

And I have my angular 2 component which requests the angular 1.x module via dependency injection:

import { Component, Inject } from '@angular/core';

@Component({
  selector: 'my-app',
  template: `<h1>Hello {{name}}, my name is {{myName}}</h1>`
})
export class AppComponent { 
  name = 'Angular'; 
  constructor(@Inject('testModule') testModule: any) {
    this.myName = testModule.test;
  }
}

I then bootstrap the angular 2 module and the angular 1.x module

import { platformBrowserDynamic } from '@angular/platform-browser-dynamic';
import { AppModule } from './app.module';

platformBrowserDynamic().bootstrapModule(AppModule).then(platformRef => {
  const upgrade = platformRef.injector.get(UpgradeModule) as UpgradeModule;
  upgrade.bootstrap(document.body, ['testModule'], {strictDi: true});
});

I then get this error TypeError: Cannot read property 'get' of undefined at useFactory which is occurring from within the arrow function specified as the "useFactory" property of the provider definition I have in the angular 2 module

providers: [{
    provide: 'testModule',
    useFactory: (i: any) => i.get('testModule'),
    deps: ['$injector']
}]

I think there is something I'm not understanding about how to initialize the angular 1.x injector in a hybrid angular 1 + 2 application. You can see I am pulling angular 1.x in via script tag, otherwise my angular 1.x module will throw an error about "angular" not being defined, and I suspect the problem may be related to that. If anyone could provide guidance, I'd appreciate it.

Here is the plunker: https://plnkr.co/edit/wdR7K4rDKoF8L0pfQypM?p=info

Here is the error with call stack:

TypeError: Cannot read property 'get' of undefined at useFactory (https://run.plnkr.co/IgsjEBjD2d29O3YH/app/app.module.ts!transpiled:32:56) at AppModuleInjector.get (/AppModule/module.ngfactory.js:140:65) at AppModuleInjector.getInternal (/AppModule/module.ngfactory.js:192:46) at AppModuleInjector.NgModuleInjector.get (https://unpkg.com/@angular/core/bundles/core.umd.js:8918:48) at CompiledTemplate.proxyViewClass.AppView.injectorGet (https://unpkg.com/@angular/core/bundles/core.umd.js:12319:49) at CompiledTemplate.proxyViewClass.DebugAppView.injectorGet (https://unpkg.com/@angular/core/bundles/core.umd.js:12699:53) at CompiledTemplate.proxyViewClass.View_AppComponent_Host0.createInternal (/AppModule/AppComponent/host.ngfactory.js:15:63) at CompiledTemplate.proxyViewClass.AppView.createHostView (https://unpkg.com/@angular/core/bundles/core.umd.js:12275:25) at CompiledTemplate.proxyViewClass.DebugAppView.createHostView (https://unpkg.com/@angular/core/bundles/core.umd.js:12683:56) at ComponentFactory.create (https://unpkg.com/@angular/core/bundles/core.umd.js:7710:29) at ApplicationRef_.bootstrap (https://unpkg.com/@angular/core/bundles/core.umd.js:8677:61) at eval (https://unpkg.com/@angular/core/bundles/core.umd.js:8506:93) at Array.forEach (native) at PlatformRef_._moduleDoBootstrap (https://unpkg.com/@angular/core/bundles/core.umd.js:8506:46) at eval (https://unpkg.com/@angular/core/bundles/core.umd.js:8458:31)

1

There are 1 answers

0
Volodymyr Zherebnyi On

I had same issue and found solution for my case on github. Take a look at updated plunker. Note that there were also others not related issues in you code. Commented <script src="test-module.js"></script> and implicit injection parameters for testService. Hope it will help you.