Fake-Backend

Set defaultauth=fackbackend in the environment.ts file.
Also Remove the firebase setup code in the environment.tsfile.


How to Integrate custom FakeBackend?

Please follow the below steps:

-> First you needs to create json data files, which you can put in the folder src/app/data from where the data/json will be called.

const data = [ { id: "1", orderdate: "22 Feb, 2023", customer: "Deondre Fahey", name: "Ratke Group", paymethod: "COD", }, { id: "2", orderdate: "14 Feb, 2023", customer: "Warren Anderson", name: "Zibra Fashion", paymethod: "Mastercard", }, ] export { data }

-> In your Angular component, you dispatch an action to request data from the fake backend. This action triggers the store, For getting the data you should get data from the selector.ts file. And we can get data in selector as response from fakebackend.ts file.


-> Reducer is also worked as middleware for angular, which is placed at src/app/store/Note/notes-reducer.ts file.

import { Action, createReducer, on } from '@ngrx/store'; import { fetchNotesData, fetchNotesFailure, fetchNotesSuccess } from './notes-action'; export interface NotesState { notes: any[]; loading: boolean; error: any; } export const initialState: NotesState = { notes: [], loading: false, error: null, }; export const NotesReducer = createReducer( initialState, on(fetchNotesData, (state) => { return { ...state, loading: true, error: null }; }), on(fetchNotesSuccess, (state, { notes }) => { return { ...state, notes, loading: false }; }), on(fetchNotesFailure, (state, { error }) => { return { ...state, error, loading: false }; }), ); // Selector export function reducer(state: NotesState | undefined, action: Action) { return NotesReducer(state, action); }

-> A store effect works as a middleware, which is placed at src/app/store/Note/notes-effect.ts file.

import { Injectable } from "@angular/core"; import { of } from 'rxjs'; import { Actions, createEffect, ofType } from "@ngrx/effects"; import { CrudService } from "../../core/services/crud.service"; import { fetchNotesData, fetchNotesFailure, fetchNotesSuccess } from "./notes-action"; @Injectable() export class NotesEffects { fetchNotes$ = createEffect(() => this.actions$.pipe( ofType(fetchNotesData), mergeMap(() => this.CrudService.fetchData('/app/notes').pipe( map((notes) => fetchNotesSuccess({ notes })), catchError((error) => of(fetchNotesFailure({ error })) ) ) ), ), ) constructor( private actions$: Actions, private CrudService: CrudService ) { } }

-> After exporting data from reducer.ts file there was a main file for whole reducers files that combines all the reducers into one. src/app/store/index.ts here we combines the rootReducers for store. import { ActionReducerMap } from "@ngrx/store"; import { NotesReducer, NotesState } from "./Note/notes-reducer"; export interface RootReducerState { Notes: NotesState, } export const rootReducer: ActionReducerMap<RootReducerState> = { Notes: NotesReducer, }

-> After rootReducers for store, declare effect file in app.config.ts file. provideStore(rootReducer), provideEffects(NotesEffects),

-> we create a service to provide a convenient and reusable way to interact with a server's API. This service encapsulates the logic for making HTTP requests and can be injected into Angular components or other services that require data manipulation. To demonstrate its functionality, a fake URL can be used.

import { ActionReducerMap } from "@ngrx/store"; import { Injectable } from '@angular/core'; import { HttpClient } from '@angular/common/http'; import { Observable } from 'rxjs'; @Injectable({ providedIn: 'root' }) export class CrudService { constructor(private http: HttpClient) { } /*** * Get */ fetchData(url: any): Observable<any[]> { return this.http.get<any[]>(url); } addData(url: any, newData: any): Observable<any[]> { return this.http.post<any[]>(url, newData); } updateData(url: any, updatedData: any): Observable<any[]> { return this.http.put<any[]>(url, updatedData); } deleteData(url: any): Observable<void> { return this.http.delete<void>(url); } }

-> FakeBackend through we will getdata from app/data, we can pass the data, which is placed at src/app/helpers/fake-Backend.ts file.

import { Injectable } from '@angular/core'; import { HttpRequest, HttpResponse, HttpHandler, HttpEvent, HttpInterceptor, HTTP_INTERCEPTORS } from '@angular/common/http'; import { Observable, of, throwError } from 'rxjs'; import { delay, mergeMap, materialize, dematerialize } from 'rxjs/operators'; import { NotesData } from '../../data'; @Injectable() export class FakeBackendInterceptor implements HttpInterceptor { constructor() { } intercept(request: HttpRequest<any>, next: HttpHandler): Observable<HttpEvent<any>> { // wrap in delayed observable to simulate server api call return of(null).pipe(mergeMap(() => { // get Notes Data if (request.url.endsWith('/app/notes') && request.method === 'GET') { if (NotesData) { return of(new HttpResponse({ status: 200, body: NotesData })); } else { return throwError({ status: 401, error: { message: 'No Data Found' } }); } } // pass through any requests not handled above return next.handle(request); })) // tslint:disable-next-line: max-line-length .pipe(materialize()) .pipe(delay(500)) .pipe(dematerialize()); } }

-> After following the above steps you can call data and use it in your components or pages where is needed by the dispatch data method and managing the state.

private store = inject(Store) ngOnInit(): void { // Fetch Data setTimeout(() => { this.store.dispatch(fetchNotesData()); this.store.select(selectNoteLoading).subscribe(data => { if (data == false) { document.getElementById('elmLoader')?.classList.add('d-none') } }) this.store.select(selectNotes).subscribe(data => { this.noteList = data }); }, 500) }