In Angular 2 RC.5 I cannot find a fix for the mentioned error:
Unhandled Promise rejection: Template parse errors:
No provider for FormGroupDirective ("p>Custom begin </p>
<p>Host contains {{hostFormGroup.directives.length}} directives</p>
[ERROR ->]<nested></nested>
<p>Custom end </p>
</div>
"): CustomComponent@4:6 ; Zone: <root> ; Task: Promise.then ; Value:
happening when a custom component, nested within another custom component, has a dependency on containing @Host() hostFormGroup: FormGroupDirective
.
Here's a plunker showing the scenario. AppComponent shows a reactive/model-driven form (temporarily without controls, but that's not crucial at this point) containing CustomComponent, which in turn has a NestedComponent. See developer console for error details.
First-level custom component can have a dependency on hosting FormGroupDirective or not, it does not affect the issue. If it has the dependency, that is resolved correctly. The same does not happen for second-level custom component, no matter what in first-level component.
The problem goes away if the same NestedComponent is used directly in AppComponent.
What am I missing? TA
Here's main part of code, for reference:
import { Component, Host } from '@angular/core';
import {
REACTIVE_FORM_DIRECTIVES, FormBuilder,
FormGroup, FormGroupDirective
} from '@angular/forms';
///////////////////////
// Nested
@Component({
selector: 'nested',
template: `
Nested begin<br/>
Nested end <br/>
`,
})
class NestedComponent {
constructor(
@Host() private hostFormGroup: FormGroupDirective) {
}
}
///////////////////////
// Custom
@Component({
selector: 'custom',
template: `
Custom begin <br/>
<nested></nested> <br/>
Custom end <br/>
`,
directives: [NestedComponent],
})
class CustomComponent {
constructor(
@Host() private hostFormGroup: FormGroupDirective) {
}
}
///////////////////////
// App
@Component({
selector: 'my-app',
template: `
<h1>Angular 2 - @Host() issue</h1>
<form [formGroup]="mainForm" accept-charset="UTF-8" role="form">
<fieldset>
<custom></custom>
</fieldset>
</form>
`,
directives: [REACTIVE_FORM_DIRECTIVES, CustomComponent],
})
export class AppComponent {
constructor(formBuilder: FormBuilder) {
this.mainForm = formBuilder.group({});
}
}
Remove the @Host() decorators and the extra providers and it works.
@Component({
selector: 'nested',
template: `
<div>
<p>Nested begin </p>
<p>Host contains {{hostFormGroup.directives.length}} directives:</p>
<span *ngFor="let directive of hostFormGroup.directives">{{directive.name}}</span>
<p>Nested end </p>
</div>
`,
// tried this: no error, but injected one is not the actual container
// and it containes no directive
// without it: still same error 'No provider for FormGroupDirective'
//providers: [FormGroupDirective],
})
class NestedComponent {
constructor(
private hostFormGroup: FormGroupDirective) {
}
}
// Custom
@Component({
selector: 'custom',
template: `
<div>
<p>Custom begin </p>
<p>Host contains {{hostFormGroup.directives.length}} directives:</p>
<span *ngFor="let directive of hostFormGroup.directives">{{directive.name}}</span>
<nested></nested>
<p>Custom end </p>
</div>
`,
directives: [NestedComponent],
// tried this: still same error 'No provider for FormGroupDirective'
//providers: [FormGroupDirective],
})
class CustomComponent {
constructor(
private hostFormGroup: FormGroupDirective) {
}
}