Skip to content

Instantly share code, notes, and snippets.

@tomastrajan
Last active March 21, 2025 16:56
Show Gist options
  • Save tomastrajan/2fbd888c37e4672d2bfdeef0b075c883 to your computer and use it in GitHub Desktop.
Save tomastrajan/2fbd888c37e4672d2bfdeef0b075c883 to your computer and use it in GitHub Desktop.
NgRx effect helpers
import { inject } from '@angular/core';
import { HttpClient, HttpErrorResponse } from '@angular/common/http';
import { Actions, createEffect, ofType } from '@ngrx/effects';
import { Action, ActionCreator } from '@ngrx/store';
import { catchError, map, mergeMap, of } from 'rxjs';
type ActionCreatorWithData<T> = ActionCreator<
string,
(props: { data: T }) => { data: T } & Action
>;
type ActionCreatorWithError<T> = ActionCreator<
string,
(props: { error: T }) => { error: T } & Action
>;
export function postEffect<T, F>(
url: string,
events: ActionCreatorWithData<T>[],
success: ActionCreatorWithData<T>,
failure: ActionCreatorWithError<F>,
errorMapper?: (error: HttpErrorResponse) => F,
) {
const http = inject(HttpClient);
const events$ = inject(Actions);
return createEffect(
() => {
return events$.pipe(
ofType(...events),
mergeMap(({ data }) => {
return http.post<T>(url, data).pipe(
map((data) => success({ data })),
catchError((error) =>
of(failure({ error: errorMapper ? errorMapper(error) : error })),
),
);
}),
);
},
{ functional: true },
);
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment