Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Inital State is empty on AOT #258

Closed
Renader opened this issue Aug 10, 2017 · 17 comments
Closed

Inital State is empty on AOT #258

Renader opened this issue Aug 10, 2017 · 17 comments

Comments

@Renader
Copy link

Renader commented Aug 10, 2017

I'm submitting a...


**[x] Bug report  **

What is the current behavior?

If I'm building my application with --aot my store object is {} when the action @ngrx/store/init is fired. (bad)
When I build my application without --aot at the time of the init action the store object is already created in structure. (good)

I'm using a factory and scoped actions but I'm not sure if that is related. I'm already working with a reducer token in order to make it work with --aot.
The bug affects all reducers, those created with a factory and reducers that are just a switch#case statement.

It might be related to #247 but I'm not using any meta reducers.

Expected behavior:

Same behavior in JIT/AOT

Version of affected browser(s),operating system(s), npm, node and ngrx:

ngx 4.0.0 , Angular 4.3.1, Angular CLI 1.3.0.RC5

Other information:

app.module.ts

@NgModule({
  declarations: [
    AppComponent,
  ],
  imports: [
    EffectsModule.forRoot([]),
    StoreModule.forRoot(reducerToken),
    !environment.production ? StoreDevtoolsModule.instrument({maxAge: 50}) : []

  ],
  providers: [
    {
      provide: reducerToken,
      useValue: reducers
    }
  ],
  bootstrap: [AppComponent]
})
export class AppModule {
}

index.ts

export interface RootState {
  process: {
    formData: ProcessState,
    offerRequest: PaperWorkState<OfferRequest>,
  };
  address: AddressState;
}

export const reducerToken = new InjectionToken<ActionReducerMap<RootState>>('Registered Reducers');

export const reducers = {
  process: combineReducers(
      {
        formData: processReducer,
        offerRequest: PaperworkReducerFactory<OfferRequest>('offer-request'),
      }),
  address: addressReducer,
};

PaperworkReducerFactory

export function PaperworkReducerFactory<T extends RequiredBaseType>(scope: PaperworkStates): (state: PaperWorkState<T>, action: PaperWorkActionsType<T> | PaperWorkPositionActionsType<T>) => PaperWorkState<T> {
  return function (state: PaperWorkState<T> = paperworkInitState, action: PaperWorkActionsType<T> | PaperWorkPositionActionsType<T>): PaperWorkState<T> {
    if (action.scope !== scope) {
      return state;
    }
    switch (action.type) {

      case SELECT:
        return setSelectedId<T>(state, action);

      [....]

      default:
        return state;
    }
  };
}

@cormacrelf
Copy link

cormacrelf commented Aug 13, 2017

I've got the same with default factory (combineReducers) and a meta reducer inside the state tree.

I always thought state was meant to be undefined when the init action is fired, so that the reducer would set its own initial value with function reducer(state = initialState, action) {...}.

Edit: the reducer (caught in a breakpoint on reduceState) doesn't actually do anything useful. It may as well be combineReducers({}). I'm guessing I still have the problem down in #116.

My module is:

const REDUCER_INJECTION_TOKEN = new InjectionToken<ActionReducerMap<AppState>>('...');
Object.assign(REDUCER_INJECTION_TOKEN, reducerMap);
...
StoreModule.forRoot(REDUCER_INJECTION_TOKEN),
...
{ provide: REDUCER_INJECTION_TOKEN, useValue: reducerMap },

and reducerMap is, basically

export const reducerMap: ActionReducerMap<any> = {
    undo: undoable(combineReducers( { /* ... */ } ),
    other: reducers.here
}

I don't suppose it would have anything to do with that <any>.

@cormacrelf
Copy link

You know what, why not just scrap the whole injector deal. Can't we have a v2-style API as well? We shouldn't have to leap through hoops to do what a one-liner provideStore did before. A reducer completely defines a store's initialisation.

@Renader
Copy link
Author

Renader commented Aug 14, 2017

I just want to add:

Changing the versions from ngrx store from 4.0.0 to 4.x.x hasn't solved the issue to me. This bug is crucial to me, I can not ship my application anymore.

I'm happy to help with any information. Yet i don't know if I do something wrong or if there is a real bug in ngrx. It would be really great if someone would look into the issue.

@cormacrelf
Copy link

cormacrelf commented Aug 14, 2017 via email

@brandonroberts
Copy link
Member

@Renader a small reproduction of the issue in a github repo would help. One thing that the new API has uncovered is the amount of people using factories which were being hidden behind using a function to return the reducers in V2.

@Renader
Copy link
Author

Renader commented Aug 18, 2017

@brandonroberts I've attached a repro-repo. I'm currently traveling by plane so the code might be not the cleanest. The store contains of a "process" section which holds an invoice state. The invoice state is created by a factory.

The example will not throw any errors since it doesn't contain any select functions. But as you can see in the dev tools on aot the state stays empty forever. Neither the initial state is created nor the action is properly processed. The example action is dispatched in app.component.ts

Repro Steps Bug (aot):

ng serve -- aot

-> Store is empty, Action not processed

store at time of @ngrx/store/init:

{}

Same is working in JIT:

ng serve

-> Store is initialized, Action is processed.

store at time of @ngrx/store/init:

{
  process: {
    invoice: {
      entities: [],
      selectedId: null
    }
  }
}

Repository:
https://github.com/Renader/ngrx-aot-258

@Renader Renader closed this as completed Aug 18, 2017
@Renader Renader reopened this Aug 18, 2017
@Renader
Copy link
Author

Renader commented Aug 18, 2017

I think this is connected with #189

@brandonroberts
Copy link
Member

@Renader thanks for the repo. This works in both cases with the latest release. I submitted a PR against your repo with the working changes Renader/ngrx-aot-258#1

Closing as resolved.

@danielstern
Copy link

I am still getting this issue in 5.2.0

@Renader
Copy link
Author

Renader commented Apr 19, 2018

@danielstern for me this issue was resolved with the fix of brandon.

@vasyl-trs
Copy link

I'm still getting this issue (v 5.2) even if use simple example from documentation

@stormit-vn
Copy link

I also facing this issue. It is working properly in development mode, but when buidling release package with AOT mode, the intial state seems not get populated. I tried to set intial state when configure the store, but it leads the actions does not working (state cannot be changed).

@timdeschryver
Copy link
Member

@marchino21 @stormit-vn could you open a new issue please, and if possible a reproduction.

@Memeplexx
Copy link

Memeplexx commented Jun 15, 2018

@tdeschryver Perhaps I'm misunderstanding protocol here, feel free to correct me if I'm wrong :) but since this is apparently exactly the same problem I'm having with v 6.0.1, I'm going to post here so that the team doesn't get duplicate bugs.

I've reproduced a minimal example of the problem

https://angular-fbmtou.stackblitz.io/

I hope it is clear :)

@timdeschryver
Copy link
Member

@StephenPaul you can pass your initialState when you're calling combineReducers.

export const reducers = combineReducers({
  branch1: branch1Reducer,
  branch2: branch2Reducer,
}, intitialState);

Forked StackBlitz

@Memeplexx
Copy link

@tdeschryver, that fixes the problem. Much appreciated :)

@otissv
Copy link

otissv commented Jul 17, 2018

Spent the last two hour wondering what was wrong with my implementation. Turned out to be aot. @timdeschryver StackBlitz fixed it. How to use with aot should be add to the README.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Projects
None yet
Development

No branches or pull requests