Use of Angular service (Advanced)

Posted by tomo11 on Sun, 19 Dec 2021 07:08:38 +0100

DI, fully known as dependency injection, is translated as dependency injection
Token, DI token

providers: [AnimalService]

Equivalent to

providers: [{provide: AnimalService, useClass: AnimalService}]

When using provider providers to configure injector (injector is the class modified by @ injectable, which can be understood as a service), The provider is associated with a dependency injection Token (Token or DI Token). The injector allows Angular to create a mapping of any internal dependencies. The Token acts as the key name of the mapping. The dependency value is an instance, and the type of this class is used as the lookup key.
provide: XXXClass is the key of the provider. The provider can be found in the Angular DI registry according to this key
useClass: XXXValue, a strategy passed to the provider to tell the provider what value should be provided for the specified key

// Root module
providers: [
	{provide: AnimalService, useClass: AnimalService},
]
// Module A
providers: [
	{provide: AaService, useClass: AaService},
]
// X assembly under module A
providers: [
	{provide: XxService, useClass: XxService},
]
// BC module
providers: [
	{provide: BbService, useClass: BbService},
	{provide: CcService, useClass: CcService},
]

// The Angular ID will associate the provider with the dependency injection token and maintain a provider registry, which supports querying the provider according to the key
// provider registry, which can be simply understood as
const provider = {
	AnimalService: new AnimalService(),
	A: {
		AaService: new AaService(),
		X: {
			XxService: new XxService(),
		}
	}
	BC: {
		BbService: new BbService(),
		CcService: new CcService(),
	}
	...
}
// A component under module a
// When defining constructor parameters using the type of the AaService class, Angular injects the service associated with the AaService class token
// That is, Angular will find the dependency value associated with the key type in the provider registry. At this point, the constructor parameter aaService points to provider A.aaService
constructor(private aaService: AaService) {}

Example:

Define animal service class: AnimalService

// anmial.service.ts
import { Injectable } from '@angular/core';

@Injectable()
export class AnimalService {
  message = 'I am AnimalService';
  constructor() { }
}

Define fruit service class: FruitService

// fruit.service.ts
import { Injectable } from '@angular/core';

@Injectable()
export class FruitService {
  message = 'I am FruitService';
  constructor() { }
}

Root module provider configuration injector

// app.module.ts
providers: [
	AnimalService,
	{ provide: FruitService, useClass: AnimalService },
]

Use in root module components

// app.component.ts
export class AppComponent {
  message = 'I am AppComponent';
  constructor(private animalService: AnimalService, private fruitService: FruitService) {
    this.animalService.message = this.message;
    console.log(this.fruitService.message);    // I am AnimalService
  }
}

Used in the home component

// home.component.ts
export class HomeComponent {
  message = 'I am HomeComponent';
  constructor(private animal: AnimalService, private fruit: FruitService) {
    console.log(this.animal.message);		// I am AppComponent
    console.log(this.fruit.message);		// I am AnimalService
  }
}

Provider: providers of the root module
Injector: Animal Service AnimalService, fruit service FruitService
After configuring the providers of the root module, Angular associates the provider with the dependency injection DI token

  • AnimalService is a DI token that points to an instance of AnimalService
  • FruitService is a DI token that points to an instance of AnimalService

The type of the root component constructor parameter animalservice is animalservice, which points to an instance of animalservice according to the ID token
The type of the root component constructor parameter fruitservice is fruitservice, which points to an instance of AnimalService according to the ID token
The type of the home component constructor parameter animal is AnimalService, which points to an instance of AnimalService according to the ID token
The type of the home component constructor parameter fruit is FruitService, which points to an instance of AnimalService according to the ID token

be careful:

  • AnimalService and fruitService are two different instances of AnimalService
  • Animalservice and animalservice are the same animalservice instance
  • fruitService and fruit are the same AnimalService instance

Therefore, modifying the message attribute of the root component animalService will not affect the message attribute of the fruitService and home component fruit, but will affect the message attribute of the animal in the home component.

Topics: angular