Skip to content

Commit

Permalink
fix(ngrx): add store typing
Browse files Browse the repository at this point in the history
This adds the `<%= className%>PartialState` used to type the store from the
`DataPersistence` methods.
This adds the `XXX_FEATURE_KEY` to the `xxx.reducer.ts` file too.

close #748
  • Loading branch information
bcabanes authored and vsavkin committed Sep 28, 2018
1 parent e63e787 commit efe38c4
Show file tree
Hide file tree
Showing 5 changed files with 17 additions and 11 deletions.
Original file line number Diff line number Diff line change
Expand Up @@ -2,13 +2,13 @@ import { Injectable } from '@angular/core';
import { Effect, Actions } from '@ngrx/effects';
import { DataPersistence } from '@nrwl/nx';

import { <%= className %>State } from './<%= fileName %>.reducer';
import { <%= className %>PartialState } from './<%= fileName %>.reducer';
import { Load<%= className %>, <%= className %>Loaded, <%= className %>LoadError, <%= className %>ActionTypes } from './<%= fileName %>.actions';

@Injectable()
export class <%= className %>Effects {
@Effect() load<%= className %>$ = this.dataPersistence.fetch(<%= className %>ActionTypes.Load<%= className %>, {
run: (action: Load<%= className %>, state: <%= className %>State) => {
run: (action: Load<%= className %>, state: <%= className %>PartialState) => {
// Your custom REST 'load' logic goes here. For now just return an empty list...
return new <%= className %>Loaded([]);
},
Expand All @@ -21,5 +21,5 @@ export class <%= className %>Effects {

constructor(
private actions$: Actions,
private dataPersistence: DataPersistence<<%= className %>State>) { }
private dataPersistence: DataPersistence<<%= className %>PartialState>) { }
}
Original file line number Diff line number Diff line change
Expand Up @@ -2,7 +2,7 @@ import { Injectable } from '@angular/core';

import { select, Store } from '@ngrx/store';

import { <%= className %>State } from './<%= fileName %>.reducer';
import { <%= className %>PartialState } from './<%= fileName %>.reducer';
import { <%= propertyName %>Query } from './<%= fileName %>.selectors';
import { Load<%= className %> } from './<%= fileName %>.actions';

Expand All @@ -13,7 +13,7 @@ export class <%= className %>Facade {
all<%= className %>$ = this.store.pipe(select(<%= propertyName %>Query.getAll<%= className %>));
selected<%= className %>$ = this.store.pipe(select(<%= propertyName %>Query.getSelected<%= className %>));

constructor( private store: Store<{<%= propertyName %>: <%= className %>State}> ) { }
constructor(private store: Store<<%= className %>PartialState>) { }

loadAll() {
this.store.dispatch(new Load<%= className %>());
Expand Down
Original file line number Diff line number Diff line change
@@ -1,5 +1,7 @@
import { <%= className %>Action, <%= className %>ActionTypes } from './<%= fileName %>.actions';

export const <%= className.toUpperCase() %>_FEATURE_KEY = '<%= propertyName %>';

/**
* Interface for the '<%= className %>' data used in
* - <%= className %>State, and
Expand All @@ -19,6 +21,10 @@ export interface <%= className %>State {
error ?: any; // last none error (if any)
};

export interface <%= className %>PartialState {
readonly [<%= className.toUpperCase() %>_FEATURE_KEY]: <%= className %>State;
}

export const initialState: <%= className %>State = {
list : [ ],
loaded : false
Expand Down
8 changes: 4 additions & 4 deletions packages/schematics/src/collection/ngrx/ngrx.spec.ts
Original file line number Diff line number Diff line change
Expand Up @@ -166,7 +166,7 @@ describe('ngrx', () => {
const appModule = getFileContent(tree, '/apps/myapp/src/app/app.module.ts');
expect(appModule).toContain('StoreModule.forFeature');
expect(appModule).toContain('EffectsModule.forFeature');
expect(appModule).toContain("'state', stateReducer");
expect(appModule).toContain('STATE_FEATURE_KEY, stateReducer');
expect(appModule).toContain('{ initialState: stateInitialState }');
expect(appModule).not.toContain(
'!environment.production ? [storeFreeze] : []'
Expand Down Expand Up @@ -357,7 +357,7 @@ describe('ngrx', () => {
const content = getFileContent(tree, `${statePath}/users.facade.ts`);

[
`import { UsersState } from './users.reducer'`,
`import { UsersPartialState } from './users.reducer'`,
`import { usersQuery } from './users.selectors'`,
`export class UsersFacade`
].forEach(text => {
Expand Down Expand Up @@ -397,11 +397,11 @@ describe('ngrx', () => {
`import { DataPersistence } from \'@nrwl/nx\'`,
`import { LoadUsers, UsersLoaded, UsersLoadError, UsersActionTypes } from \'./users.actions\'`,
`loadUsers$`,
`run: (action: LoadUsers, state: UsersState)`,
`run: (action: LoadUsers, state: UsersPartialState)`,
`return new UsersLoaded([])`,
`return new UsersLoadError(error)`,
'private actions$: Actions',
'private dataPersistence: DataPersistence<UsersState>)'
'private dataPersistence: DataPersistence<UsersPartialState>)'
].forEach(text => {
expect(content).toContain(text);
});
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -38,7 +38,7 @@ export function addImportsToModule(context: RequestContext): Rule {
const reducerName = `${toPropertyName(context.featureName)}Reducer`;
const effectsName = `${toClassName(context.featureName)}Effects`;
const facadeName = `${toClassName(context.featureName)}Facade`;
const reducerImports = `initialState as ${featureName}InitialState, ${reducerName}`;
const reducerImports = `${featureName.toUpperCase()}_FEATURE_KEY, initialState as ${featureName}InitialState, ${reducerName}`;

const storeReducers = `{ ${featureName}: ${reducerName} }`;
const storeInitState = `initialState : { ${featureName} : ${featureName}InitialState }`;
Expand All @@ -55,7 +55,7 @@ export function addImportsToModule(context: RequestContext): Rule {
const storeForEmptyRoot = `StoreModule.forRoot({},{ ${storeMetaReducers} })`;
const effectsForRoot = `EffectsModule.forRoot([${effectsName}])`;
const effectsForEmptyRoot = `EffectsModule.forRoot([])`;
const storeForFeature = `StoreModule.forFeature('${featureName}', ${reducerName}, { initialState: ${featureName}InitialState })`;
const storeForFeature = `StoreModule.forFeature(${featureName.toUpperCase()}_FEATURE_KEY, ${reducerName}, { initialState: ${featureName}InitialState })`;
const effectsForFeature = `EffectsModule.forFeature([${effectsName}])`;
const devTools = `!environment.production ? StoreDevtoolsModule.instrument() : []`;
const storeRouterModule = 'StoreRouterConnectingModule';
Expand Down

0 comments on commit efe38c4

Please sign in to comment.