Welcome to the Angular Effects Tutorial! In this comprehensive guide, we'll dive deep into Angular Effects - a powerful tool for managing asynchronous side effects in your applications. Let's get started! 🚀
Effects are a key feature of Angular's architecture, introduced with the RxJS library. They help manage side effects, such as data fetching, UI updates, or interaction with external services, in a clean and testable way.
Effects are used within the context of NgRx, a popular Angular library for managing state management in applications. While Angular itself doesn't require NgRx, it's a popular choice for managing complex applications with multiple components and services.
Before diving into Effects, make sure you're familiar with:
First, let's set up NgRx in our Angular project.
ng add @ngrx/storeimport { StoreModule } from '@ngrx/store';
@NgModule({
imports: [
StoreModule.forRoot({}) // Add your reducers here
]
})
export class AppModule { }import { createReducer, on } from '@ngrx/store';
import { exampleAction } from './example.actions';
export const exampleReducer = createReducer(
0,
on(exampleAction, state => state + 1)
);Now, let's create an Effect to handle an asynchronous action.
ng generate @ngrx/effects:effects exampleexample.effects.ts file:import { Injectable } from '@angular/core';
import { Actions, createEffect, ofType } from '@ngrx/effects';
import { exampleAction } from './example.actions';
import { of } from 'rxjs';
import { catchError, map, mergeMap } from 'rxjs/operators';
@Injectable()
export class ExampleEffects {
loadExample = createEffect(() =>
this.actions$.pipe(
ofType(exampleAction.loadExample),
mergeMap(() =>
this.exampleService.loadExample().pipe(
map(example => exampleAction.loadExampleSuccess({ example })),
catchError(error => of(exampleAction.loadExampleFailure({ error })))
)
)
)
);
constructor(private actions$: Actions, private exampleService: ExampleService) {}
}In this example, we've created an Effect called loadExample that listens for the exampleAction.loadExample action. When it's dispatched, the Effect triggers the loadExample method from ExampleService, and either dispatches the exampleAction.loadExampleSuccess action with the loaded example or the exampleAction.loadExampleFailure action with the error.
Now that we've created our Effect, let's test it out!
exampleAction.loadExample action in your component:import { exampleAction } from './example.actions';
loadExample() {
this.store.dispatch(exampleAction.loadExample());
}exampleReducer:import { Store } from '@ngrx/store';
import { exampleReducer } from './example.reducer';
constructor(private store: Store) {
this.store.select(exampleReducer).subscribe(console.log);
}Now, when you call the loadExample method in your component, you should see the Effect in action!
What is the primary purpose of Effects in Angular applications?
That's it for now! In the next sections, we'll dive deeper into Effects, explore advanced concepts, and build more complex examples. Keep learning, and happy coding! 🎉