I have provider which I would like to act as transient instead of a singleton. I know I can create object manually but I would like to still resolve dependencies through the dependency injector.
export class HubServiceBase {
private readonly hubAuthorizationQueryParameter = 'authToken';
onCreate = new EventEmitter<any>();
connectionEstablished = new EventEmitter<Boolean>();
connectionExists = false;
private _hubConnection: any;
constructor(public authManager: AuthenticationProvider) {
}
initialize(hubSubRoute: string): void{
const accessToken = this.authManager.getRawAccessToken();
let hubUrl = environment.baseUrl + hubSubRoute;
if (accessToken) {
hubUrl += '?' + this.hubAuthorizationQueryParameter +'=' + accessToken;
}
this._hubConnection = new HubConnectionBuilder()
.withUrl(hubUrl)
.build();
}
//...
}
the initialize function can be called from different services and it maintains a web socket with my server. There can be multiple sockets open running concurrently.
How can I get a new one from the Dependency injector each time a page requests it?
There are multiple ways to prevent this: Use the providedIn syntax instead of registering the service in the module. Separate your services into their own module. Define forRoot() and forChild() methods in the module.
The answer would be no. The main objective of angular services is to share data across Angular application. Practically an angular service can be shared between all the components or can be limited to some component. Hence Angular service can be a singleton as well as non-singleton in nature.
When you register a service into DI in Angular, the services are marked Singleton. Alternatively to create a transient service (a new instance of service is returned from DI whenever requested), we can use factory while declaring in the NgModule.
Providing a servicelink The service itself is a class that the CLI generated and that's decorated with @Injectable() . By default, this decorator has a providedIn property, which creates a provider for the service. In this case, providedIn: 'root' specifies that Angular should provide the service in the root injector.
Use the providers
property in the @Component
decorator.
@Component({
selector: 'selector-name',
templateUrl: './template.component.html',
providers: [ SomeService ]
})
Docs (not great): https://angular.io/api/core/Component
Example: https://stackblitz.com/edit/angular-playground-vewqis?file=app%2Fhello-framework%2Fcomponents%2Fcounter%2Fcounter.component.ts
you can configure injectors in Angular by:
providers on NgModule
.
providers on Components
If you want an instance of a dependency to be shared globally and share state across the application you configure it on the NgModule
.-Singleton
If you want a separate instance of a dependency to be shared across each instance of a component and it’s children you configure it on the components providers
property.Non-singleton
Providing services
Angular's Hierarchical Dependency Injection system
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With