Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

@ngx/store/update-reducers modifies state of my application undesirably

In my application developed in Angular, I use the services of Firebase Authentication to authenticate, at the moment of the login of my application the states are changed in the correct way, keeping all the state of the form as I need.

When I log in I noticed in Redux DevTools that the state of my application has the "auth" authentication status so I can access data from the authenticated user.

When I navigate to any other page on my system the "auth" auth status disappears after an event that occurs called "@ngrx/store/update-reducers" and there I can no longer have authentication status information on my system.

Why might this be happening? Why is "@ngrx/store/update-reducers" being invoked?

I have a file that is in a "store" folder inside the "src/app" tree. In this file I have all the reducers I create in the root module "app.module".

index.ts:

import { ActionReducerMap, createFeatureSelector } from '@ngrx/store';
import { ActivatedRouteSnapshot, RouterStateSnapshot, Params } from '@angular/router';

import * as fromRouter from '@ngrx/router-store';
import * as fromAuth from '../reducers/auth.reducer';
import * as fromMessenger from '../reducers/messenger.reducer';

export interface RouterStateUrl {
    url: string;
    queryParams: Params;
    params: Params;
}

export interface StateApp {
    auth: fromAuth.AuthState;
    router: fromRouter.RouterReducerState<RouterStateUrl>;
    messenger: fromMessenger.MessengerState;
}

export const reducers: ActionReducerMap<StateApp> = {
    auth: fromAuth.reducer,
    router: fromRouter.routerReducer,
    messenger: fromMessenger.reducer
};

export const getMessengerState = createFeatureSelector<fromMessenger.MessengerState>('messenger');
export const getAuthState = createFeatureSelector<fromAuth.AuthState>('auth');

export const getRouterState = createFeatureSelector
    <fromRouter.RouterReducerState<RouterStateUrl>>
    ('router');

export class CustomSerializer
    implements fromRouter.RouterStateSerializer<RouterStateUrl> {
    serialize(routerState: RouterStateSnapshot): RouterStateUrl {

        const { url } = routerState;
        const { queryParams } = routerState.root;

        let state: ActivatedRouteSnapshot = routerState.root;

        while (state.firstChild) {
            state = state.firstChild;
        }

        const { params } = state;

        return { url, queryParams, params };
    }
}

app.module.ts

import { reducers, CustomSerializer } from './store/reducers';
import { effects } from './store/effects';

 StoreModule.forRoot(reducers, { metaReducers }),
    EffectsModule.forRoot(effects),

The "messenger" state and the others are maintained, the only state that is not maintained when I navigate from one page to the other is the "auth" state.

like image 525
Luiz Avatar asked Aug 30 '18 20:08

Luiz


1 Answers

The @ngrx/store/update-reducers is dispatched where modules are registered. This is hard to "solve" without seeing the full code, be sure that you don't update your store state directly (the ngrx-store-freeze metareducer could help) and that every reducer is returning state (make sure to have a default case in your reducer's switch statement that simply returns state..

like image 189
timdeschryver Avatar answered Nov 30 '22 22:11

timdeschryver