Formation Angular
Lab 3 Services
Lab 3.1: Create simple provider
1. Build the app using the CLI: Use the following command:
ng new
dependency-injection-ex100 --inline-template --inline-style
2. Start ng serve: Use the following code: cd dependency-injection-ex100
ng serve
3.Open app: Open a web browser and navigate to localhost:4200. You should
see “app works!”
4.Create service class: Create car.service.ts and change it to the following:
import { Injectable } from '@angular/core';
@Injectable()
export class CarService {
constructor(){
console.log('CarService: constructor');
}
// Some dummy method.
isSuperCharged(car: string){
return car === 'Ford GT' ? 'yes' : 'no';
}
}
5. Edit class: Edit app.component.ts and change it to the following:
import { Component, OnInit, Input } from '@angular/core';
import { CarService } from './car.service';
@Component({
selector: 'car',
template: `
<h3>
{{name}} Is Supercharged: {{supercharged}}
</h3>
`,
styles: [],
providers: [CarService]
})
export class CarComponent implements OnInit{
@Input() name;
supercharged: string = '';
constructor(private service: CarService){}
ngOnInit(){
this.supercharged = this.service.isSuperCharged(this.name);
}
}
@Component({
selector: 'app-root',
template: `
<car name="Ford GT"></car>
<car name="Corvette Z06"></car>
`,
styles: []
})
export class AppComponent {
title = 'app works!';
}
6. Edit module: Edit app.module.ts and change it to the following:
import { BrowserModule } from '@angular/platform-browser';
import { NgModule } from '@angular/core';
import { FormsModule } from '@angular/forms';
import { HttpModule } from '@angular/http';
import { AppComponent, CarComponent } from './app.component';
@NgModule({
declarations: [
AppComponent, CarComponent
],
imports: [
BrowserModule,
FormsModule,
HttpModule
],
providers: [],
bootstrap: [AppComponent]
})
export class AppModule { }
Your app should be working at localhost:4200.
Note the following:
• The car service outputs a log when in the constructor. This service
contains a method isSuperCharged that receives a car name as an
argument and returns a yes or no accordingly, as shown in Figure below.
• The app component has a car component that’s used twice. The
car
component specifies the car service as a provider. The car component
invokes the service method isSuperCharged in the method ngOnInit.
ngOnInit is fired when the component has been initialized.
Why do multiple instances of the same service get created? Open the
console and you’ll see something like this :
As you can see, the constructor is invoked twice, as the service is created
twice. That’s because the CarService is provided in the car component and
the car component is create twice.
7. Remove provider from components and add it in the module.
Notice that the provider is now instanciated only once
Lab 3.2: Class provider
Class providers allow us to tell the provider which class to use for a
dependency.
The figure below shows a component that relies on a Watch service.
Let’s do example dependency-injection-ex350:
1. Build the app using the CLI: Use the following command:
ng new
dependency-injection-ex350 --inline-template --inline-style
2. Start ng serve: Use the following code: cd dependency-injection-ex350
ng serve
5.Open app: Open a web browser and navigate to localhost:4200. You should
see “app works!”
6.Edit class: Edit app.component.ts and change it to the following:
import { Component } from '@angular/core';
class Watch {
getTime(): string {
return new Date() + "";
}
}
class Seiko extends Watch {
getTime(): string{
return "Seiko Time:" + super.getTime();
}
}
@Component({
selector: 'app-root',
template: `
<h1>
{{watch.getTime()}}
</h1>
`,
styles: [],
providers: [{
provide: Watch,
useClass: Seiko
}]
})
export class AppComponent {
constructor(private watch:Watch){}
}
Your app should be working at localhost:4200. Note that when we use the
Provider element of the @Component annotation to create the dependency,
we specify that subclass of the Watch (a Seiko).
Lab 3.3: Factory provider
Factory providers use a function to provide Angular with an instance of an
object. This is useful when you need to dynamically change the object that
you want created, based on some data.
This is a simple component that uses a logging service:
1. Build the app using the CLI: Use the following command:
ng new dependency-injection-ex400 --inline-template --inline-style
2. Start ng serve: Use the following code:
cd dependency-injection-ex400
ng serve
3. Open app: Open a web browser and navigate to localhost:4200. You
should see “app works!”
4.Create service class: This is the same as the previous example.
Create logging.service.ts and change it to the following:
import { Injectable } from '@angular/core';
@Injectable()
export class LoggingService {
constructor(private dateAndTime: boolean){
console.log('LoggingService: constructor');
}
log(message){
console.log((this.dateAndTime ? new Date() + ': ' : '') +
message);
}
}
5. Edit class: Edit app.component.ts and change it to the following:
import { Component } from '@angular/core';
import { LoggingService } from './logging.service';
@Component({
selector: 'app-root',
template: `
<h1>
{{title}}
</h1>
`,
styles: [],
providers: [provideLoggingService()]
})
export class AppComponent {
constructor(private logging: LoggingService){
logging.log('test log');
}
title = 'app works!';
}
export const LOGGING_USE_DATE = false;
export function provideLoggingService() {
return {
provide: LoggingService,
useFactory: () => new LoggingService(LOGGING_USE_DATE)
}}
Your app should be working at localhost:4200. Note that this logging
service has the option of including the logging date and time. You can set
this using the constructor
to the logging service. A factory provider is
used to provide an instance of the logging service.
export const LOGGING_USE_DATE = true;
export function provideLoggingService() {
return {
provide: LoggingService,
useFactory: () => new LoggingService(LOGGING_USE_DATE)
}}
Date included in logging
export const LOGGING_USE_DATE = false;
export function provideLoggingService() {
return {
provide: LoggingService,
useFactory: () => new LoggingService(LOGGING_USE_DATE)
}}
Date not included in logging
Lab 3.3: Value provider
Value providers simply provide a value of an object, as shown below
Let’s go through example dependency-injection-ex600:
1. Build the app using the CLI: Use the following command:
ng new
dependency-injection-ex600 --inline-template --inline-style
2. Start ng serve: Use the following code: cd dependency-injection-ex600
ng serve
7.Open app: Open a web browser and navigate to localhost:4200. You should
see “app works!”
8.Edit class: Edit app.component.ts and change it to the following:
import { Component, Injector } from '@angular/core';
@Component({
selector: 'app-root',
template: `
<h1>
{{title}}
</h1>
`,
styles: [],
providers: [{
provide: 'language',
useValue: 'en'
}]
})
export class AppComponent {
title: string = '';
constructor(private injector: Injector){
this.title = 'Language is: ' + injector.get('language');
}
}