Ngx-bootstrap: Modal component causes 'Error: Token must be defined!' for AoT runtime

Created on 5 Jan 2017  路  41Comments  路  Source: valor-software/ngx-bootstrap

I use shared module to define Modals and share it with different parts of the app

import { NgModule, ModuleWithProviders } from '@angular/core';
import { CommonModule } from '@angular/common';
import { FormsModule } from '@angular/forms';

import { ModalModule } from 'ng2-bootstrap';


@NgModule({
  imports: [
      CommonModule,
      ModalModule.forRoot()
  ],
  exports: [
      CommonModule,
      FormsModule,
      ModalModule
  ]
})
export class SharedModule {
  static forRoot(): ModuleWithProviders {
    return {
      ngModule: SharedModule
    };
  }
}

JIT compilation and runtime work fine.
AoT compilation works fine but during runtime I got this error:

EXCEPTION: Uncaught (in promise): Error: Token must be defined!
Error: Token must be defined!

The issue disappears when I remove modal component div (bsModal) from template.

I use Angular 2.4.1, ng2-bootstrap 1.1.16-11

Here is a repo with steps to reproduce:
https://github.com/irsick/ng2-bootstrap-bsModals-issue

Probably it's related to #986

comp(modal) issue

Most helpful comment

your PR published as v1.2.6

All 41 comments

interesting, huge thanks for repo!

I will take a look asap

I'm getting the same issue with the typeahead directive. Angular 2.4.2, ng2-bootstrap 1.1.16-11, AOT build.

@valorkin Any update on this? It would appear that ng2-bootstrap is currently unusable with AOT builds for certain directives, including modal and typeahead.

I tried to reproduce, but works fine for me. Can you do a sample repo

@valorkin Did you try the sample repo from @irsick ?

Just checked repo. AoT build has throws runtime error as it supposed to do:

bsmodal_issue

I think it is missing the stuff from the utils folder in the AOT build.

found some sortable component issues, but @irsick repo found another issues
I will try to fix it completely, seems you are using angular-seed repo?

@valorkin Yes, I am using the seed.

updated ng2-bootstrap to v1.2.3, no AoT compilation issues now, but
seems to be seed issue, or what so ever

Error: Error encountered resolving symbol values statically. Could not resolve events relative to /Users/valorkin/work/open-source/temp/ng2-bootstrap-bsModals-issue/node_modules/protractor/built/runner.d.ts., resolving symbol Runner in /Users/valorkin/work/open-source/temp/ng2-bootstrap-bsModals-issue/node_modules/protractor/built/runner.d.ts
    at simplifyInContext (/Users/valorkin/work/open-source/temp/ng2-bootstrap-bsModals-issue/node_modules/@angular/compiler/bundles/compiler.umd.js:25709:25)
    at StaticReflector.simplify (/Users/valorkin/work/open-source/temp/ng2-bootstrap-bsModals-issue/node_modules/@angular/compiler/bundles/compiler.umd.js:25721:15)
    at StaticReflector.annotations (/Users/valorkin/work/open-source/temp/ng2-bootstrap-bsModals-issue/node_modules/@angular/compiler/bundles/compiler.umd.js:25214:82)
    at NgModuleResolver.resolve (/Users/valorkin/work/open-source/temp/ng2-bootstrap-bsModals-issue/node_modules/@angular/compiler/bundles/compiler.umd.js:17564:84)
    at CompileMetadataResolver.getNgModuleMetadata (/Users/valorkin/work/open-source/temp/ng2-bootstrap-bsModals-issue/node_modules/@angular/compiler/bundles/compiler.umd.js:18072:62)
    at addNgModule (/Users/valorkin/work/open-source/temp/ng2-bootstrap-bsModals-issue/node_modules/@angular/compiler/bundles/compiler.umd.js:24980:60)
    at /Users/valorkin/work/open-source/temp/ng2-bootstrap-bsModals-issue/node_modules/@angular/compiler/bundles/compiler.umd.js:24991:16
    at Array.forEach (native)
    at _createNgModules (/Users/valorkin/work/open-source/temp/ng2-bootstrap-bsModals-issue/node_modules/@angular/compiler/bundles/compiler.umd.js:24990:28)
    at analyzeNgModules (/Users/valorkin/work/open-source/temp/ng2-bootstrap-bsModals-issue/node_modules/@angular/compiler/bundles/compiler.umd.js:24865:16)
Compilation failed

if using https://github.com/irsick/ng2-bootstrap-bsModals-issue
@sublime392 please try latest too

and why not to use angular-cli?

I will try to create/modify what @irsick has later tonight in order to demonstrate what I am seeing. In the meantime:

If I only import the modules I need like import { ModalModule } from 'ng2-bootstrap/modal' I get the runtime message about Token needs to be defined, or whatever. I also do not see anything from the utils in the compiled code.

If I import like import { ModalModule } from 'ng2-bootstrap' I was getting compile an error about the private items in sortable. Now (1.2.3) I get ng2-bootstrap/sortable/sortable.component.ngfactory.ts(424,35): error TS2346: Supplied parameters do not match any signature of call target.

I believe I also saw that error on 1.2.2 but it was after the private items error so I ignored it.

Like I said though, I will try to get something demonstrable later on.

Why am I using the seed? It is what I started my current project with back when Angular2 first went to beta. It is all I know at this point.

@valorkin I see the sortable compile error I now get with 1.2.3 seems to related to mouse event comment in this issue: https://github.com/valor-software/ng2-bootstrap/issues/1514

@sublime392 fixed in v1.2.4, please try again ;D

I've tested my repo with ng2-bootstrap 1.2.5. The issue still persists.

I don't know if this is totally useless information, or not:
I turned off the minification on my build and found the source of the token error (not the reason)

For this line
this._ModalDirective_40_5 = new import18.Wrapper_ModalDirective(new import10.ElementRef(this._el_40), this._vc_40.vcRef, this.renderer, this.parentView.injectorGet(import19.ComponentLoaderFactory, this.parentIndex));
the import19 does not have a ComponentLoaderFactory (undefined).

import19 looks like:

AccordionComponent:e(e)
AccordionConfig:e()
AccordionModule:e()
AccordionPanelComponent:e(e)
AlertComponent:e(e)
AlertConfig:e()
AlertModule:e()
BarComponent:e(e)
BsRootModule:e()
ButtonCheckboxDirective:e()
ButtonRadioDirective:e(e)
ButtonsModule:e()
CarouselComponent:e(e)
CarouselConfig:e()
CarouselModule:e()
ClassName:Object
CollapseDirective:e(e, t)
CollapseModule:e()
DateFormatter:e()
DatePickerComponent:e(e)
DatepickerConfig:e()
DatepickerModule:e()
DayPickerComponent:e(e)
DraggableItemService:e()
DropdownConfig:e()
DropdownDirective:e(e, t, n)
DropdownMenuDirective:e(e, t)
DropdownModule:e()
DropdownService:e()
DropdownToggleDirective:e(e, t)
ModalBackdropComponent:e(e, t)
ModalBackdropOptions:e(e)
ModalDirective:e(e, t, n, i)
ModalModule:e()
MonthPickerComponent:e(e)
Ng2BootstrapModule:e()
NgTranscludeDirective:e(e)
OnChange:i(e)
PagerComponent:e(e, t, n)
PaginationComponent:e(e, t, n)
PaginationModule:e()
PopoverConfig:e()
PopoverContainerComponent:e(e)
PopoverDirective:e(e, t, n, i, a)
PopoverModule:e()
ProgressDirective:e()
ProgressbarComponent:e(e)
ProgressbarConfig:e()
ProgressbarModule:e()
RatingComponent:e()
RatingModule:e()
Selector:Object
SlideComponent:e(e)
SortableComponent:e(e)
SortableModule:e()
TabDirective:e(e)
TabHeadingDirective:e(e, t)
TabsModule:e()
TabsetComponent:e(e)
TabsetConfig:e()
TimepickerComponent:e(e)
TimepickerConfig:e()
TimepickerModule:e()
TooltipConfig:e()
TooltipContainerComponent:e(e)
TooltipDirective:e(e, t, n, i, a)
TooltipModule:e()
TypeaheadContainerComponent:e(e)
TypeaheadDirective:e(e, t, n, i, a)
TypeaheadMatch:e(e, t, n)
TypeaheadModule:e()
TypeaheadOptions:e(e)
TypeaheadUtils:e()
YearPickerComponent:e(e)
isBs3:i()
modalConfigDefaults:Object
__proto__:Object

@valorkin I tried loading a modal straight in the root app component instead of a feature module. The error changed to TypeError: import69.PositioningService is not a constructor
In the compiled code looks like import69.PositioningService points to this._PositioningService_98

 if (token === import69.PositioningService) {
           return this._PositioningService_98;
  }

but this._PositioningService_98 points to import69.PositioningService?

 Object.defineProperty(AppModuleInjector.prototype, "_PositioningService_98", {
            get: function () {
                if (this.__PositioningService_98 == null) {
                    this.__PositioningService_98 = new import69.PositioningService();
                }
                return this.__PositioningService_98;
            },
            enumerable: true,
            configurable: true
        });

And you are using forRoot? Can you fork and update sample repo?

@valorkin Here you go. I tried to keep it to the bare minimum for example. Instructions are in README. https://github.com/sublime392/ng2-bootstrap-bsModals-issue

Awesome, thank you! We are getting closer.
From first look code should work,
Seems too much gulp magic

@mgechev have you seen such things before?

@valorkin I figured it out! woot! I think I sent a pull request.

awesome, I just was installing dependencies :)

oh, now I feel so stupid >.<
another question... why angular-cli in aot mode doesn't complain about it

dist/tmp/node_modules/ng2-bootstrap/index.ngfactory.ts(137,127): error TS2345: Argument of type 'this' is not assignable to parameter of type 'ComponentFactoryResolver'.
  Type 'BsRootModuleInjector' is not assignable to type 'ComponentFactoryResolver'.
    Types of property 'resolveComponentFactory' are incompatible.
      Type '<T>(component: new (...args: any[]) => T) => ComponentFactory<T>' is not assignable to type '<T>(component: Type<T>) => ComponentFactory<T>'.
        Type 'ComponentFactory<any>' is not assignable to type 'ComponentFactory<any>'.
          Types have separate declarations of a private property '_viewClass'.

whyyyy?

your PR published as v1.2.6

I can not handle this gulp stuff

I am glad I was able to help a little. I am also pretty stoked about making my first PR to such an awesome project.

@sublime392 my congratulations with first PR :)
give me a note, did it helped?

@valorkin I apologize, but I don't understand this part:

give me a note, did it helped?

https://github.com/valorkin/ng2-bootstrap-bsModals-issue

can you try npm run build.prod here?
may be you will be able to fix it

I tweaked a couple of imports and it worked. Now I see the bs folder is gone though. When using barrel files with ( systemjs? gulp? something?) the index needs to be on end of import. (unlike webpack). I just don't use barrel files anymore so I dont have to worry about it.

Thanks I will check it asap

tried again with ng2-bootstrap v1.2.6
seems fixed

I still get Error: Token must be defined! similar issue with PaginationComponent

this._PaginationComponent_64_3 = new import61.Wrapper_PaginationComponent(this.renderer, new import31.ElementRef(this._el_64), this.parentView.injectorGet(import62.PaginationConfig, this.parentIndex));

I got same setup (I am importing PaginationModule.forRoot() and exporting in my SharedModule.

I tried local build of ng2-bootstrap and exporting PaginationConfig class fixed the issue

dist/tmp/node_modules/ng2-bootstrap/index.ngfactory.ts(137,127): error TS2345: Argument of type 'this' is not assignable to parameter of type 'ComponentFactoryResolver'. Type 'BsRootModuleInjector' is not assignable to type 'ComponentFactoryResolver'. Types of property 'resolveComponentFactory' are incompatible. Type '<T>(component: new (...args: any[]) => T) => ComponentFactory<T>' is not assignable to type '<T>(component: Type<T>) => ComponentFactory<T>'. Type 'ComponentFactory<any>' is not assignable to type 'ComponentFactory<any>'. Types have separate declarations of a private property '_viewClass'.

@valorkin -- did you ever resolve this error? I get the same error on a library I'm working on, and this github issue is literally the ONLY google result :)

@jlee1201 it seems pretty change:
replace all 'export *' with named exports

actually, I finally figured out that it was because I was using symlink for the library I was working on. Related to: https://github.com/Microsoft/TypeScript/issues/9552

Was this page helpful?
0 / 5 - 0 ratings