问题
I need to know how to create a listener e.g. I want to subscribe to the AppState changing.
Below is my current very basic service. I have a dispatch action on the view which increments the counter.
Once the counter changes value I'd like to detect this in other parts of my website e.g. the global header for example.
I'm using ng2-Redux with angular version 5.
Redux service:
export interface IAppState {
counter: number;
}
export const INITIAL_APP_STATE: IAppState = {
counter: 0
};
export function appReducer(state: IAppState, action: any): IAppState {
switch (action.type) {
case 'INCREMENT':
return {
counter: state.counter + action.payload
};
}
return state;
}
回答1:
angular-redux offers a very convenient way of selecting slices of your store with the @select()
decorator.
Let's say your IAppState
would be:
export interface IAppState {
counter: number;
auth: {token: string};
}
Then you can select the parts of your state like this:
// variable name is equal to state property + $
@select() counter$: Observable<number>;
@select() auth$: Observable<{token: string}>;
// path to store slice
@select(['auth', 'token']) token$: Observable<string>;
For further information, have a look at the select docs.
回答2:
I declare the actions in a file
// action.ts
export const FILTER_ROLES = "FILTER_ROLES"
// this action will be handled in the effect
export class FilterRoles implements Action {
readonly type = FILTER_ROLES
constructor(public query: any) { }
}
export const FILTERED_ROLES = "FILTERED_ROLES"
// this one will modify the reducer
export class FilteredRoles implements Action {
readonly type = FILTERED_ROLES
constructor(public values: Array<any>, public total: number) { }
}
the effects file will look like this, (effects will call the backend)
@Injectable()
export class RoleEffects {
@Effect() filter_roles = this.actions$
.ofType(FILTER_ROLES)
.flatMap((action: FilterRoles) => {
return
backendCall()
.mergeMap(({ values, total }) => {
return [
new FilteredRoles(values, total)
]
}).catch((err: Error) => { console.log("sss") })
}
the reducer will modify the current state of your store
export function RoleReducer(state: Roles = { values: [], total: 0 }, action: RoleActions) {
switch (action.type) {
case FILTERED_ROLES:
return Object.assign({}, state, { values: action.values, total: action.total })
default:
return state
}
}
In my module declaration you should declare both effects and reducer actions
const EffectModules = [
EffectsModule.run(RoleEffects)
....
....
]
in the imports of my module I will declare all the reducer and effects
@NgModule({
imports: [
StoreModule.provideStore({roles: RoleReducer,
... // all the other reducers
}),
...EffectModules,
]
})
I hope this code will help you
来源:https://stackoverflow.com/questions/48950721/in-angular-v5-how-do-i-listen-to-my-apps-redux-state-object-changing