23. Providers and Scoping
Providers tell Angular how to create an instance of a dependency. Scoping dictates where that instance is available and how long it lives.
Provider Configuration Locations
-
Root (Singleton): Using
providedIn: 'root'in the service decorator. The service is available everywhere and is a true singleton. -
Module Scope: Listing the service in the
providersarray of a specific NgModule (e.g.,AppModule). The service is scoped to all components declared within that module or modules that import it. -
Component Scope: Listing the service in the
providersarray of a specific Component's metadata (@Component).
Component Scope Behavior
When a service is provided at the component level, Angular creates a new instance for that specific component and all its children. If the component is destroyed, the service instance is also destroyed. This creates multiple, independent instances of the service.
Example of Component-Scoped Service:
typescript import { CounterService } from './counter.service';
@Component({ selector: 'app-component-scoped', templateUrl: './component-scoped.component.html', providers: [CounterService] // New instance for this component and children }) export class ComponentScopedComponent { // ... constructor injection }
When to use which scope?
- Root: For global state, logging, configuration, and data fetching services (most common).
- Module: For feature-specific dependencies (e.g., providing specialized form validators only for the 'Settings' module).
- Component: For temporary or isolated services (e.g., a service to manage the state of a single, complex modal window).
Understanding scope is critical for managing state and avoiding unintended data sharing.