parent
3cf2005a93
commit
1c6516199e
|
@ -0,0 +1,24 @@
|
|||
import { browser, element, by } from 'protractor';
|
||||
import { logging } from 'selenium-webdriver';
|
||||
|
||||
describe('Providers and ViewProviders', function () {
|
||||
|
||||
|
||||
beforeEach(() => {
|
||||
browser.get('');
|
||||
});
|
||||
|
||||
it('shows basic flower emoji', function() {
|
||||
expect(element.all(by.css('p')).get(0).getText()).toContain('🌺');
|
||||
});
|
||||
|
||||
it('shows whale emoji', function() {
|
||||
expect(element.all(by.css('p')).get(1).getText()).toContain('🐳');
|
||||
});
|
||||
|
||||
it('shows sunflower from FlowerService', function() {
|
||||
expect(element.all(by.css('p')).get(8).getText()).toContain('🌻');
|
||||
});
|
||||
|
||||
});
|
||||
|
|
@ -0,0 +1,10 @@
|
|||
// #docregion animal-service
|
||||
import { Injectable } from '@angular/core';
|
||||
|
||||
@Injectable({
|
||||
providedIn: 'root'
|
||||
})
|
||||
export class AnimalService {
|
||||
emoji = '🐳';
|
||||
}
|
||||
// #enddocregion animal-service
|
|
@ -0,0 +1,15 @@
|
|||
import { Component } from '@angular/core';
|
||||
import { FlowerService } from './flower.service';
|
||||
import { AnimalService } from './animal.service';
|
||||
|
||||
|
||||
@Component({
|
||||
selector: 'app-root',
|
||||
templateUrl: './app.component.html',
|
||||
styleUrls: [ './app.component.css' ]
|
||||
})
|
||||
// #docregion injection
|
||||
export class AppComponent {
|
||||
constructor(public flower: FlowerService) {}
|
||||
}
|
||||
// #enddocregion injection
|
|
@ -0,0 +1,15 @@
|
|||
|
||||
<h2>From AppComponent:</h2>
|
||||
<!-- #docregion binding-flower -->
|
||||
<p>Emoji from FlowerService: {{flower.emoji}}</p>
|
||||
<!-- #enddocregion binding-flower -->
|
||||
<!-- #docregion binding-animal -->
|
||||
<p>Emoji from AnimalService: {{animal.emoji}}</p>
|
||||
<!-- #enddocregion binding-animal -->
|
||||
|
||||
<hr />
|
||||
|
||||
<h2>From ChildComponent:</h2>
|
||||
<!-- #docregion content-projection -->
|
||||
<app-child><app-inspector></app-inspector></app-child>
|
||||
<!-- #enddocregion content-projection -->
|
|
@ -0,0 +1,15 @@
|
|||
import { Component } from '@angular/core';
|
||||
import { FlowerService } from './flower.service';
|
||||
import { AnimalService } from './animal.service';
|
||||
|
||||
|
||||
@Component({
|
||||
selector: 'app-root',
|
||||
templateUrl: './app.component.html',
|
||||
styleUrls: [ './app.component.css' ]
|
||||
})
|
||||
// #docregion inject-animal-service
|
||||
export class AppComponent {
|
||||
constructor(public flower: FlowerService, public animal: AnimalService) {}
|
||||
}
|
||||
// #enddocregion inject-animal-service
|
|
@ -0,0 +1,17 @@
|
|||
import { NgModule } from '@angular/core';
|
||||
import { BrowserModule } from '@angular/platform-browser';
|
||||
import { FormsModule } from '@angular/forms';
|
||||
|
||||
import { AppComponent } from './app.component';
|
||||
import { ChildComponent } from './child/child.component';
|
||||
import { InspectorComponent } from './inspector/inspector.component';
|
||||
|
||||
// #docregion appmodule
|
||||
@NgModule({
|
||||
imports: [ BrowserModule, FormsModule ],
|
||||
declarations: [ AppComponent, ChildComponent, InspectorComponent ],
|
||||
bootstrap: [ AppComponent ],
|
||||
providers: []
|
||||
})
|
||||
export class AppModule { }
|
||||
// #enddocregion appmodule
|
|
@ -0,0 +1,19 @@
|
|||
import { Component, OnInit, Host, SkipSelf, Optional } from '@angular/core';
|
||||
import { FlowerService } from '../flower.service';
|
||||
|
||||
// #docregion flowerservice
|
||||
@Component({
|
||||
selector: 'app-child',
|
||||
templateUrl: './child.component.html',
|
||||
styleUrls: ['./child.component.css'],
|
||||
// use the providers array to provide a service
|
||||
providers: [{ provide: FlowerService, useValue: { emoji: '🌻' } }]
|
||||
})
|
||||
|
||||
export class ChildComponent {
|
||||
// inject the service
|
||||
constructor( public flower: FlowerService) { }
|
||||
}
|
||||
|
||||
// #enddocregion flowerservice
|
||||
|
|
@ -0,0 +1,4 @@
|
|||
.container {
|
||||
border: 1px solid darkblue;
|
||||
padding: 1rem;
|
||||
}
|
|
@ -0,0 +1,24 @@
|
|||
<!-- #docplaster -->
|
||||
<!-- #docregion child-component -->
|
||||
<!-- #docregion flower-binding -->
|
||||
<p>Emoji from FlowerService: {{flower.emoji}}</p>
|
||||
<!-- #enddocregion flower-binding -->
|
||||
<!-- #docregion animal-binding -->
|
||||
<p>Emoji from AnimalService: {{animal.emoji}}</p>
|
||||
<!-- #enddocregion animal-binding -->
|
||||
|
||||
<div class="container">
|
||||
<h3>Content projection</h3>
|
||||
<!-- #enddocregion child-component -->
|
||||
<p>The following is coming from content. It doesn't get to see the puppy because the puppy is declared inside the view only.</p>
|
||||
<!-- #docregion child-component -->
|
||||
<ng-content></ng-content>
|
||||
</div>
|
||||
|
||||
<h3>Inside the view</h3>
|
||||
<!-- #enddocregion child-component -->
|
||||
<p>The following is inside the view so it does see the puppy.</p>
|
||||
<!-- #docregion child-component -->
|
||||
<app-inspector></app-inspector>
|
||||
<!-- #enddocregion child-component -->
|
||||
|
|
@ -0,0 +1,44 @@
|
|||
// #docplaster
|
||||
import { Component, OnInit, Host, SkipSelf, Optional } from '@angular/core';
|
||||
import { FlowerService } from '../flower.service';
|
||||
import { AnimalService } from '../animal.service';
|
||||
|
||||
// #docregion provide-animal-service
|
||||
@Component({
|
||||
selector: 'app-child',
|
||||
templateUrl: './child.component.html',
|
||||
styleUrls: ['./child.component.css'],
|
||||
// provide services
|
||||
providers: [{ provide: FlowerService, useValue: { emoji: '🌻' } }],
|
||||
viewProviders: [{ provide: AnimalService, useValue: { emoji: '🐶' } }]
|
||||
})
|
||||
|
||||
export class ChildComponent {
|
||||
// inject service
|
||||
constructor( public flower: FlowerService, public animal: AnimalService) { }
|
||||
// #enddocregion provide-animal-service
|
||||
|
||||
// viewProviders ensures that only the view gets to see this.
|
||||
// With the AnimalService in the viewProviders, the
|
||||
// InspectorComponent doesn't get to see it because the
|
||||
// inspector is in the content.
|
||||
|
||||
|
||||
// constructor( public flower: FlowerService, @Optional() @Host() public animal: AnimalService) { }
|
||||
|
||||
// Comment out the above constructor and alternately
|
||||
// uncomment the two following constructors to see the
|
||||
// effects of @Host() and @Host() + @SkipSelf().
|
||||
|
||||
// constructor(
|
||||
// @Host() public animal : AnimalService,
|
||||
// @Host() @Optional() public flower : FlowerService) { }
|
||||
|
||||
// constructor(
|
||||
// @SkipSelf() @Host() public animal : AnimalService,
|
||||
// @SkipSelf() @Host() @Optional() public flower : FlowerService) { }
|
||||
|
||||
// #docregion provide-animal-service
|
||||
}
|
||||
// #enddocregion provide-animal-service
|
||||
|
|
@ -0,0 +1,11 @@
|
|||
import { Injectable } from '@angular/core';
|
||||
|
||||
// #docregion flowerservice
|
||||
@Injectable({
|
||||
providedIn: 'root'
|
||||
})
|
||||
export class FlowerService {
|
||||
emoji = '🌺';
|
||||
}
|
||||
// #enddocregion flowerservice
|
||||
|
|
@ -0,0 +1,4 @@
|
|||
<!-- #docregion binding -->
|
||||
<p>Emoji from FlowerService: {{flower.emoji}}</p>
|
||||
<p>Emoji from AnimalService: {{animal.emoji}}</p>
|
||||
<!-- #enddocregion binding -->
|
|
@ -0,0 +1,14 @@
|
|||
import { Component } from '@angular/core';
|
||||
import { FlowerService } from '../flower.service';
|
||||
import { AnimalService } from '../animal.service';
|
||||
|
||||
@Component({
|
||||
selector: 'app-inspector',
|
||||
templateUrl: './inspector.component.html',
|
||||
styleUrls: ['./inspector.component.css']
|
||||
})
|
||||
// #docregion injection
|
||||
export class InspectorComponent {
|
||||
constructor(public flower: FlowerService, public animal: AnimalService) { }
|
||||
}
|
||||
// #enddocregion injection
|
|
@ -0,0 +1,14 @@
|
|||
<!doctype html>
|
||||
<html lang="en">
|
||||
<head>
|
||||
<meta charset="utf-8">
|
||||
<title>providers vs. viewProviders</title>
|
||||
<base href="/">
|
||||
|
||||
<meta name="viewport" content="width=device-width, initial-scale=1">
|
||||
<link rel="icon" type="image/x-icon" href="favicon.ico">
|
||||
</head>
|
||||
<body>
|
||||
<app-root></app-root>
|
||||
</body>
|
||||
</html>
|
|
@ -0,0 +1,12 @@
|
|||
import { enableProdMode } from '@angular/core';
|
||||
import { platformBrowserDynamic } from '@angular/platform-browser-dynamic';
|
||||
|
||||
import { AppModule } from './app/app.module';
|
||||
import { environment } from './environments/environment';
|
||||
|
||||
if (environment.production) {
|
||||
enableProdMode();
|
||||
}
|
||||
|
||||
platformBrowserDynamic().bootstrapModule(AppModule)
|
||||
.catch(err => console.log(err));
|
|
@ -0,0 +1,10 @@
|
|||
{
|
||||
"description": "Inputs and Outputs",
|
||||
"files": [
|
||||
"!**/*.d.ts",
|
||||
"!**/*.js",
|
||||
"!**/*.[1,2].*"
|
||||
],
|
||||
"file": "src/app/app.component.ts",
|
||||
"tags": ["Inputs and Outputs"]
|
||||
}
|
|
@ -0,0 +1,21 @@
|
|||
import { browser, element, by } from 'protractor';
|
||||
|
||||
describe('Resolution-modifiers-example', function () {
|
||||
|
||||
beforeAll(function () {
|
||||
browser.get('');
|
||||
});
|
||||
|
||||
it('shows basic flower emoji', function() {
|
||||
expect(element.all(by.css('p')).get(0).getText()).toContain('🌸');
|
||||
});
|
||||
|
||||
it('shows basic leaf emoji', function() {
|
||||
expect(element.all(by.css('p')).get(1).getText()).toContain('🌿');
|
||||
});
|
||||
|
||||
it('shows yellow flower in host child', function() {
|
||||
expect(element.all(by.css('p')).get(9).getText()).toContain('🌼');
|
||||
});
|
||||
|
||||
});
|
|
@ -0,0 +1,14 @@
|
|||
<h1>DI resolution modifiers</h1>
|
||||
|
||||
<p>Basic flower service: {{flower.emoji}}</p>
|
||||
<p>Basic leaf service: {{leaf.emoji}}</p>
|
||||
|
||||
<app-optional></app-optional>
|
||||
|
||||
<app-self></app-self>
|
||||
|
||||
<app-self-no-data></app-self-no-data>
|
||||
|
||||
<app-skipself></app-skipself>
|
||||
|
||||
<app-host-parent></app-host-parent>
|
|
@ -0,0 +1,13 @@
|
|||
import { Component } from '@angular/core';
|
||||
import { LeafService } from './leaf.service';
|
||||
import { FlowerService } from './flower.service';
|
||||
|
||||
@Component({
|
||||
selector: 'app-root',
|
||||
templateUrl: './app.component.html',
|
||||
styleUrls: [ './app.component.css' ]
|
||||
})
|
||||
export class AppComponent {
|
||||
name = 'Angular';
|
||||
constructor(public flower: FlowerService, public leaf: LeafService) {}
|
||||
}
|
|
@ -0,0 +1,33 @@
|
|||
;
|
||||
import { OptionalComponent } from './optional/optional.component';
|
||||
import { NgModule } from '@angular/core';
|
||||
import { BrowserModule } from '@angular/platform-browser';
|
||||
import { FormsModule } from '@angular/forms';
|
||||
|
||||
import { AppComponent } from './app.component';
|
||||
import { SelfNoDataComponent } from './self-no-data/self-no-data.component';
|
||||
import { HostComponent } from './host/host.component';
|
||||
import { SelfComponent } from './self/self.component';
|
||||
import { SkipselfComponent } from './skipself/skipself.component';
|
||||
import { HostParentComponent } from './host-parent/host-parent.component';
|
||||
import { HostChildComponent } from './host-child/host-child.component';
|
||||
|
||||
@NgModule({
|
||||
imports: [
|
||||
BrowserModule,
|
||||
FormsModule
|
||||
],
|
||||
declarations: [
|
||||
AppComponent,
|
||||
OptionalComponent,
|
||||
SelfComponent,
|
||||
SelfNoDataComponent,
|
||||
HostComponent,
|
||||
SkipselfComponent,
|
||||
HostParentComponent,
|
||||
HostChildComponent
|
||||
],
|
||||
bootstrap: [AppComponent],
|
||||
providers: []
|
||||
})
|
||||
export class AppModule { }
|
|
@ -0,0 +1,9 @@
|
|||
import { Injectable } from '@angular/core';
|
||||
|
||||
@Injectable({
|
||||
providedIn: 'root' // provide this service in the root ModuleInjector
|
||||
|
||||
})
|
||||
export class FlowerService {
|
||||
emoji = '🌸';
|
||||
}
|
|
@ -0,0 +1,5 @@
|
|||
.section {
|
||||
border: 2px solid #369;
|
||||
padding: 1rem;
|
||||
margin: 1rem 0;
|
||||
}
|
|
@ -0,0 +1,4 @@
|
|||
<div class="section">
|
||||
<h2>Child of @Host() Component</h2>
|
||||
<p>Flower emoji: {{flower.emoji}}</p>
|
||||
</div>
|
|
@ -0,0 +1,11 @@
|
|||
import { Component } from '@angular/core';
|
||||
import { FlowerService } from '../flower.service';
|
||||
|
||||
@Component({
|
||||
selector: 'app-host-child',
|
||||
templateUrl: './host-child.component.html',
|
||||
styleUrls: ['./host-child.component.css']
|
||||
})
|
||||
export class HostChildComponent {
|
||||
constructor(public flower: FlowerService) { }
|
||||
}
|
|
@ -0,0 +1,5 @@
|
|||
.section {
|
||||
border: 2px solid #369;
|
||||
padding: 1rem;
|
||||
margin: 1rem 0;
|
||||
}
|
|
@ -0,0 +1,5 @@
|
|||
<div class="section">
|
||||
<h2>Parent of @Host() Component</h2>
|
||||
<p>Flower emoji: {{flower.emoji}}</p>
|
||||
<app-host></app-host>
|
||||
</div>
|
|
@ -0,0 +1,16 @@
|
|||
import { Component } from '@angular/core';
|
||||
import { FlowerService } from '../flower.service';
|
||||
|
||||
|
||||
@Component({
|
||||
selector: 'app-host-parent',
|
||||
templateUrl: './host-parent.component.html',
|
||||
styleUrls: ['./host-parent.component.css'],
|
||||
providers: [{ provide: FlowerService, useValue: { emoji: '🌺' } }]
|
||||
|
||||
})
|
||||
export class HostParentComponent {
|
||||
|
||||
constructor(public flower: FlowerService) { }
|
||||
|
||||
}
|
|
@ -0,0 +1,5 @@
|
|||
.section {
|
||||
border: 2px solid #369;
|
||||
padding: 1rem;
|
||||
margin: 1rem 0;
|
||||
}
|
|
@ -0,0 +1,6 @@
|
|||
<div class="section">
|
||||
<h2>@Host() Component</h2>
|
||||
<p>Flower emoji: {{flower.emoji}}</p>
|
||||
<p><i>(@Host() stops it here)</i></p>
|
||||
<app-host-child></app-host-child>
|
||||
</div>
|
|
@ -0,0 +1,21 @@
|
|||
import { Component, Host, Optional } from '@angular/core';
|
||||
import { FlowerService } from '../flower.service';
|
||||
|
||||
// #docregion host-component
|
||||
@Component({
|
||||
selector: 'app-host',
|
||||
templateUrl: './host.component.html',
|
||||
styleUrls: ['./host.component.css'],
|
||||
// provide the service
|
||||
providers: [{ provide: FlowerService, useValue: { emoji: '🌼' } }]
|
||||
})
|
||||
export class HostComponent {
|
||||
// use @Host() in the constructor when injecting the service
|
||||
constructor(@Host() @Optional() public flower: FlowerService) { }
|
||||
|
||||
}
|
||||
// #enddocregion host-component
|
||||
|
||||
// if you take out @Host() and the providers array, flower will be red hibiscus
|
||||
|
||||
|
|
@ -0,0 +1,11 @@
|
|||
import { Injectable } from '@angular/core';
|
||||
|
||||
@Injectable({
|
||||
providedIn: 'root'
|
||||
})
|
||||
// #docregion leafservice
|
||||
export class LeafService {
|
||||
emoji = '🌿';
|
||||
}
|
||||
// #enddocregion leafservice
|
||||
|
|
@ -0,0 +1,7 @@
|
|||
import { Injectable } from '@angular/core';
|
||||
|
||||
@Injectable()
|
||||
export class OptionalService {
|
||||
}
|
||||
|
||||
// This service isn't provided anywhere.
|
|
@ -0,0 +1,5 @@
|
|||
.section {
|
||||
border: 2px solid #369;
|
||||
padding: 1rem;
|
||||
margin: 1rem 0;
|
||||
}
|
|
@ -0,0 +1,4 @@
|
|||
<div class="section">
|
||||
<h2>@Optional() Component</h2>
|
||||
<p>This component still works even though the OptionalService (notice @Optional() in the consturctor isn't provided or configured anywhere. Angular goes through tree and visibilty rules, and if it doesn't find the requested service, returns null.</p>
|
||||
</div>
|
|
@ -0,0 +1,21 @@
|
|||
import { Component, Optional } from '@angular/core';
|
||||
import { OptionalService } from '../optional.service';
|
||||
|
||||
@Component({
|
||||
selector: 'app-optional',
|
||||
templateUrl: './optional.component.html',
|
||||
styleUrls: ['./optional.component.css']
|
||||
})
|
||||
|
||||
// #docregion optional-component
|
||||
export class OptionalComponent {
|
||||
constructor(@Optional() public optional: OptionalService) {}
|
||||
}
|
||||
// #enddocregion optional-component
|
||||
|
||||
// The OptionalService isn't provided here, in the @Injectable()
|
||||
// providers array, or in the NgModule. If you remove @Optional()
|
||||
// from the constructor, you'll get an error.
|
||||
|
||||
|
||||
|
|
@ -0,0 +1,5 @@
|
|||
.section {
|
||||
border: 2px solid #369;
|
||||
padding: 1rem;
|
||||
margin: 1rem 0;
|
||||
}
|
|
@ -0,0 +1,4 @@
|
|||
<div class="section">
|
||||
<h2>@Self() Component (without a provider)</h2>
|
||||
<p>Leaf emoji: {{leaf?.emoji}}</p>
|
||||
</div>
|
|
@ -0,0 +1,18 @@
|
|||
import { Component, Self, Optional } from '@angular/core';
|
||||
import { LeafService } from '../leaf.service';
|
||||
|
||||
// #docregion self-no-data-component
|
||||
@Component({
|
||||
selector: 'app-self-no-data',
|
||||
templateUrl: './self-no-data.component.html',
|
||||
styleUrls: ['./self-no-data.component.css']
|
||||
})
|
||||
export class SelfNoDataComponent {
|
||||
constructor(@Self() @Optional() public leaf: LeafService) { }
|
||||
}
|
||||
|
||||
// #enddocregion self-no-data-component
|
||||
|
||||
// The app doesn't break because the value being available at self is optional.
|
||||
// If you remove @Optional(), the app breaks.
|
||||
|
|
@ -0,0 +1,5 @@
|
|||
.section {
|
||||
border: 2px solid #369;
|
||||
padding: 1rem;
|
||||
margin: 1rem 0;
|
||||
}
|
|
@ -0,0 +1,4 @@
|
|||
<div class="section">
|
||||
<h2>@Self() Component</h2>
|
||||
<p>Flower emoji: {{flower?.emoji}}</p>
|
||||
</div>
|
|
@ -0,0 +1,19 @@
|
|||
import { Component, Self } from '@angular/core';
|
||||
import { FlowerService } from '../flower.service';
|
||||
|
||||
// #docregion self-component
|
||||
@Component({
|
||||
selector: 'app-self',
|
||||
templateUrl: './self.component.html',
|
||||
styleUrls: ['./self.component.css'],
|
||||
providers: [{ provide: FlowerService, useValue: { emoji: '🌼' } }]
|
||||
|
||||
})
|
||||
export class SelfComponent {
|
||||
constructor(@Self() public flower: FlowerService) {}
|
||||
}
|
||||
// #enddocregion self-component
|
||||
|
||||
// This component provides the FlowerService so the injector
|
||||
// doesn't have to look further up the injector tree
|
||||
|
|
@ -0,0 +1,5 @@
|
|||
.section {
|
||||
border: 2px solid #369;
|
||||
padding: 1rem;
|
||||
margin: 1rem 0;
|
||||
}
|
|
@ -0,0 +1,4 @@
|
|||
<div class="section">
|
||||
<h2>@SkipSelf() Component</h2>
|
||||
<p>Leaf emoji: {{leaf.emoji}}</p>
|
||||
</div>
|
|
@ -0,0 +1,18 @@
|
|||
import { Component, SkipSelf } from '@angular/core';
|
||||
import { LeafService } from '../leaf.service';
|
||||
|
||||
// #docregion skipself-component
|
||||
@Component({
|
||||
selector: 'app-skipself',
|
||||
templateUrl: './skipself.component.html',
|
||||
styleUrls: ['./skipself.component.css'],
|
||||
// Angular would ignore this LeafService instance
|
||||
providers: [{ provide: LeafService, useValue: { emoji: '🍁' } }]
|
||||
})
|
||||
export class SkipselfComponent {
|
||||
// Use @SkipSelf() in the constructor
|
||||
constructor(@SkipSelf() public leaf: LeafService) { }
|
||||
}
|
||||
// #enddocregion skipself-component
|
||||
|
||||
// @SkipSelf(): Specifies that the dependency resolution should start from the parent injector, not here.
|
|
@ -0,0 +1,14 @@
|
|||
<!doctype html>
|
||||
<html>
|
||||
<head>
|
||||
<meta charset="utf-8">
|
||||
<title>DI Resolution Modifiers Example</title>
|
||||
<base href="/">
|
||||
|
||||
<meta name="viewport" content="width=device-width, initial-scale=1">
|
||||
<link rel="icon" type="image/x-icon" href="favicon.ico">
|
||||
</head>
|
||||
<body>
|
||||
<app-root>Loading...</app-root>
|
||||
</body>
|
||||
</html>
|
|
@ -0,0 +1,11 @@
|
|||
import { enableProdMode } from '@angular/core';
|
||||
import { platformBrowserDynamic } from '@angular/platform-browser-dynamic';
|
||||
|
||||
import { AppModule } from './app/app.module';
|
||||
import { environment } from './environments/environment';
|
||||
|
||||
if (environment.production) {
|
||||
enableProdMode();
|
||||
}
|
||||
|
||||
platformBrowserDynamic().bootstrapModule(AppModule);
|
|
@ -0,0 +1,10 @@
|
|||
{
|
||||
"description": "NgModules",
|
||||
"files": [
|
||||
"!**/*.d.ts",
|
||||
"!**/*.js",
|
||||
"!**/*.[1,2].*"
|
||||
],
|
||||
"file": "src/app/app.component.ts",
|
||||
"tags": ["NgModules"]
|
||||
}
|
|
@ -134,7 +134,7 @@ The `@NgModule()` and `@Component()` decorators have the `providers` metadata op
|
|||
|
||||
Components are directives, and the `providers` option is inherited from `@Directive()`. You can also configure providers for directives and pipes at the same level as the component.
|
||||
|
||||
Learn more about [where to configure providers](guide/hierarchical-dependency-injection#where-to-register).
|
||||
Learn more about [where to configure providers](guide/hierarchical-dependency-injection).
|
||||
|
||||
</div>
|
||||
|
||||
|
|
File diff suppressed because it is too large
Load Diff
|
@ -0,0 +1 @@
|
|||
<?xml version="1.0" encoding="UTF-8" standalone="no"?><!DOCTYPE svg PUBLIC "-//W3C//DTD SVG 1.1//EN" "http://www.w3.org/Graphics/SVG/1.1/DTD/svg11.dtd"><svg width="100%" height="100%" viewBox="0 0 600 445" version="1.1" xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink" xml:space="preserve" xmlns:serif="http://www.serif.com/" style="fill-rule:evenodd;clip-rule:evenodd;stroke-linecap:round;stroke-linejoin:round;stroke-miterlimit:1.5;"><g id="NullInjector"><rect x="11.864" y="16.952" width="575.424" height="114.429" style="fill:#fff;stroke:#0159d3;stroke-width:3.81px;"/><text x="208.488px" y="67.96px" style="font-family:'ArialMT', 'Arial', sans-serif;font-size:30.514px;">NullInjector()</text><g transform="matrix(0.847458,0,0,0.847619,-81.3559,-80.5238)"><text x="286.27px" y="212px" style="font-family:'ArialMT', 'Arial', sans-serif;font-size:24px;">always throws an error unless</text><text x="334.768px" y="236.785px" style="font-family:'ArialMT', 'Arial', sans-serif;font-size:24px;">you use @Optional()</text></g></g><path d="M286.822,144.941l-7.161,0l11.017,-11.017l11.017,11.017l-7.161,0l0,38.992l-7.712,0l0,-38.992Z" style="fill:#0159d3;stroke:#0159d3;stroke-width:3.81px;"/><path d="M286.822,297.512l-7.161,0l11.017,-11.017l11.017,11.017l-7.161,0l0,38.993l-7.712,0l0,-38.993Z" style="fill:#0159d3;stroke:#0159d3;stroke-width:3.81px;"/><g id="Moduleinjector"><rect x="11.864" y="168.913" width="575.424" height="114.429" style="fill:#fff;stroke:#0159d3;stroke-width:3.81px;"/><text x="215.313px" y="211.956px" style="font-family:'ArialMT', 'Arial', sans-serif;font-size:25.429px;">ModuleInjector</text><g transform="matrix(0.847458,0,0,0.847619,-24.5763,-79.6762)"><text x="215.592px" y="385px" style="font-family:'ArialMT', 'Arial', sans-serif;font-size:24px;">(configured by PlatformModule)</text><text x="74.879px" y="409.785px" style="font-family:'ArialMT', 'Arial', sans-serif;font-size:24px;">has special things like DomSanitizer => platformBrowser()</text></g></g><g id="root"><rect x="10.599" y="320.428" width="577.966" height="113.581" style="fill:#fff;stroke:#0159d3;stroke-width:3.81px;"/><g transform="matrix(0.847458,0,0,0.847619,-59.3163,262.743)"><text x="280.144px" y="115px" style="font-family:'Courier';font-size:30px;">root</text><text x="370.158px" y="115px" style="font-family:'ArialMT', 'Arial', sans-serif;font-size:30px;">ModuleInjector</text></g><g transform="matrix(0.847458,0,0,0.847619,15.5593,-82.219)"><text x="165.889px" y="559px" style="font-family:'ArialMT', 'Arial', sans-serif;font-size:24px;">(configured by <tspan x="324.209px 338.014px 351.361px " y="559px 559px 559px ">You</tspan>rAppModule)</text><text x="5.57px" y="583.785px" style="font-family:'ArialMT', 'Arial', sans-serif;font-size:24px;">has things for your app => bootstrapModule(Y<tspan x="498.332px 511.68px " y="583.785px 583.785px ">ou</tspan>rAppModule)</text></g></g></svg>
|
After Width: | Height: | Size: 2.9 KiB |
Loading…
Reference in New Issue