NgRx - 如何从状态正确 select
NgRx - how to properly select from state
我正在研究 NgRx 并遵循他们网站上的入门教程。使用 Redux Dev Tools chrome 扩展进行调试,我可以看到我的操作被触发并且正在正确更新商店。尽管我在状态和组件方面遇到问题 select。
在app.module.ts
:
import { StoreModule } from '@ngrx/store';
import { reducers, metaReducers } from './store/reducers';
然后
imports: [
...
StoreModule.forRoot(reducers, { metaReducers }),
!environment.production ? StoreDevtoolsModule.instrument() : [],
...
]
在store/reducers/index.ts
import {
ActionReducer,
ActionReducerMap,
createFeatureSelector,
createSelector,
MetaReducer
} from '@ngrx/store';
import { environment } from '../../../environments/environment';
import * as fromLayout from './layout.reducer';
export interface State {
[fromLayout.layoutFeatureKey]: fromLayout.State;
}
export const reducers: ActionReducerMap<State> = {
[fromLayout.layoutFeatureKey]: fromLayout.reducer,
};
export const metaReducers: MetaReducer<State>[] = !environment.production ? [] : [];
在layout.reducer.ts
export const layoutFeatureKey = 'layout';
export interface State {
showSettingsPanel: boolean;
theme: string;
scheme: string;
layout: string;
}
export const initialState: State = {
showSettingsPanel: false,
theme: 'default',
scheme: 'light',
layout: 'classy',
};
export const reducer = createReducer(
initialState,
on(layoutActions.toggleSettingsPanel, state => ({ ...state, showSettingsPanel: !state.showSettingsPanel })),
on(layoutActions.changeTheme, (state, { theme }) => ({ ...state, theme })),
on(layoutActions.changeScheme, (state, { scheme }) => ({ ...state, scheme })),
on(layoutActions.changeLayout, (state, { layout }) => ({ ...state, layout })),
);
最后是我的组件:
@Component({
selector : 'example',
templateUrl : './example.component.html',
encapsulation: ViewEncapsulation.None
})
export class ExampleComponent
{
layout$: Observable<layoutReducer.State>;
theme$: Observable<string>;
constructor(
private store: Store<layoutReducer.State>
)
{
this.layout$ = store.select(state => state);
this.theme$ = store.select('theme');
}
}
组件HTML:
<h3>{{(theme$ | async)}}</h3>
<div *ngIf="( layout$ | async ) as layout">
<h3>{{ layout.theme }}</h3>
<h3>{{ layout.scheme }}</h3>
</div>
最后什么也没有打印出来。我在州 select 做错了什么?
尝试在组件内订阅以进行调试。
export class ExampleComponent implements OnInit {
layout$: Observable<laoutReducer.State>;
theme$: Observable<string>;
constructor(
private store: Store<layoutReducer.State>
)
{}
ngOnInit() {
// this should log the whole state for debugging, remove once debugged
this.store.select(state => state).subscribe(state => console.log({ state });
// I imagine layout$ and theme$ should be like this but the above should help you debug
this.layout$ = this.store.select(layoutFeatureKey);
this.theme$ = this.store.select(layoutFeatureKey).pipe(
map(layout => layout.theme),
);
}
}
我正在研究 NgRx 并遵循他们网站上的入门教程。使用 Redux Dev Tools chrome 扩展进行调试,我可以看到我的操作被触发并且正在正确更新商店。尽管我在状态和组件方面遇到问题 select。
在app.module.ts
:
import { StoreModule } from '@ngrx/store';
import { reducers, metaReducers } from './store/reducers';
然后
imports: [
...
StoreModule.forRoot(reducers, { metaReducers }),
!environment.production ? StoreDevtoolsModule.instrument() : [],
...
]
在store/reducers/index.ts
import {
ActionReducer,
ActionReducerMap,
createFeatureSelector,
createSelector,
MetaReducer
} from '@ngrx/store';
import { environment } from '../../../environments/environment';
import * as fromLayout from './layout.reducer';
export interface State {
[fromLayout.layoutFeatureKey]: fromLayout.State;
}
export const reducers: ActionReducerMap<State> = {
[fromLayout.layoutFeatureKey]: fromLayout.reducer,
};
export const metaReducers: MetaReducer<State>[] = !environment.production ? [] : [];
在layout.reducer.ts
export const layoutFeatureKey = 'layout';
export interface State {
showSettingsPanel: boolean;
theme: string;
scheme: string;
layout: string;
}
export const initialState: State = {
showSettingsPanel: false,
theme: 'default',
scheme: 'light',
layout: 'classy',
};
export const reducer = createReducer(
initialState,
on(layoutActions.toggleSettingsPanel, state => ({ ...state, showSettingsPanel: !state.showSettingsPanel })),
on(layoutActions.changeTheme, (state, { theme }) => ({ ...state, theme })),
on(layoutActions.changeScheme, (state, { scheme }) => ({ ...state, scheme })),
on(layoutActions.changeLayout, (state, { layout }) => ({ ...state, layout })),
);
最后是我的组件:
@Component({
selector : 'example',
templateUrl : './example.component.html',
encapsulation: ViewEncapsulation.None
})
export class ExampleComponent
{
layout$: Observable<layoutReducer.State>;
theme$: Observable<string>;
constructor(
private store: Store<layoutReducer.State>
)
{
this.layout$ = store.select(state => state);
this.theme$ = store.select('theme');
}
}
组件HTML:
<h3>{{(theme$ | async)}}</h3>
<div *ngIf="( layout$ | async ) as layout">
<h3>{{ layout.theme }}</h3>
<h3>{{ layout.scheme }}</h3>
</div>
最后什么也没有打印出来。我在州 select 做错了什么?
尝试在组件内订阅以进行调试。
export class ExampleComponent implements OnInit {
layout$: Observable<laoutReducer.State>;
theme$: Observable<string>;
constructor(
private store: Store<layoutReducer.State>
)
{}
ngOnInit() {
// this should log the whole state for debugging, remove once debugged
this.store.select(state => state).subscribe(state => console.log({ state });
// I imagine layout$ and theme$ should be like this but the above should help you debug
this.layout$ = this.store.select(layoutFeatureKey);
this.theme$ = this.store.select(layoutFeatureKey).pipe(
map(layout => layout.theme),
);
}
}