DEV Community

Cover image for The ABCs of Angular : Dependency Injection Provider & Provide Part 2
Ismail Labbi
Ismail Labbi

Posted on

The ABCs of Angular : Dependency Injection Provider & Provide Part 2

In the previous article, we introduced the useClass property within the providers array to define how the Angular Dependency Injection system instantiates a class. In this article, we will delve deeper into this syntax and explore providers in Angular.

Before we proceed, let's refresh our memory 😁 .

In Angular, providers are an array of instructions, where each provider is an instruction or recipe that describes how an object for a particular class, string, token, etc., is created.

Now, let's focus on a specific object in the providers array:

{ provide: LoggerService, useClass: LoggerService }
Enter fullscreen mode Exit fullscreen mode

This Provider object contains two properties: provide and useClass.

The provide property represents the identifier of the provider, which can be either a string or an instance of InjectionToken. In our example

Contructor(public loggerService:LoggerService)
Enter fullscreen mode Exit fullscreen mode

we inject an instance of LoggerService into a component's constructor using LoggerService as the token 🥴🥴.

If this isn't clear, don't worry; examples will help you understand it better 😉.

Consider the following modified provider syntax:

providers: [
  { provide: LoggerService, useClass: BetterProductService }
]
Enter fullscreen mode Exit fullscreen mode

Now, when Angular encounters the need to inject LoggerService in a constructor, it will search the providers and find LoggerService. However, instead of injecting LoggerService, it will inject BetterProductService. In other words, the provide: LoggerService is merely a token used to identify what we want to inject.

For your Information :
Angular doesn't complain if the token is used multiple times. In the following example, the token LoggerService is used twice, but the last registration (BetterProductService) takes precedence.

providers: [
  { provide: LoggerService, useClass: LoggerService },
  { provide: LoggerService, useClass: BetterProductService }
]
Enter fullscreen mode Exit fullscreen mode

*You should also know that the token can also be a string ! *
For example:

providers: [{ provide: 'LoggerService', useClass: LoggerService }]
Enter fullscreen mode Exit fullscreen mode

In this case, 'LoggerService' serves as a string token. To inject LoggerService, we can use the @Inject decorator as shown below:

export class AppComponent {
  constructor(@Inject('LoggerService') private loggerService: LoggerService) {}
}
Enter fullscreen mode Exit fullscreen mode

However, using string tokens can introduce naming collisions if multiple parts of your application use the same string for different purposes. This can lead to conflicts and make your code harder to understand.

To address this, Angular provides the InjectionToken

What is an Injection Token?

An Injection Token is similar to a string token, but instead of using a hardcoded string, we create the Injection Token by instantiating the InjectionToken class. This ensures that the tokens are always unique.

To create an Injection Token, import InjectionToken from @angular/core:

import { InjectionToken } from '@angular/core';
Enter fullscreen mode Exit fullscreen mode

Next, create a new instance of InjectionToken with a unique name, such as LoggerServiceToken:

export const LoggerServiceToken = new InjectionToken<string>('LoggerService');

Enter fullscreen mode Exit fullscreen mode

Here, we specify the optional type parameter and the token description, which helps clarify the token's purpose.

Register the Injection Token in the providers array:

providers: [
  { provide: LoggerServiceToken, useClass: LoggerService },
  // Other providers...
]
Enter fullscreen mode Exit fullscreen mode

Now, you can inject the LoggerService using the Injection Token in your component:

export class AppComponent {
  constructor(@Inject(LoggerServiceToken) public loggerService: LoggerService) {}
Enter fullscreen mode Exit fullscreen mode

In the next article, we will explore additional properties of the provider object in Angular. Apart from provide, there are other properties that can be used to configure the dependency injection behavior.

Top comments (1)

Collapse
 
facupascual profile image
facupascual

Great article, Congratulations! Do you have a use case where you use InjectionToken?