getState in redux-saga?

getState in redux-saga?

本文关键字:redux-saga in getState      更新时间:2023-09-26

我有一个商店,里面有项目列表。当我的应用首次加载时,我需要反序列化项目,就像基于项目创建一些内存中对象一样。这些项目存储在我的 redux 存储中,并由itemsReducer处理。

我正在尝试使用 redux-saga 来处理反序列化,作为副作用。在第一次页面加载时,我调度一个操作:

dispatch( deserializeItems() );

我的传奇设置很简单:

function* deserialize( action ) {
    // How to getState here??
    yield put({ type: 'DESERISLIZE_COMPLETE' });
}
function* mySaga() {
    yield* takeEvery( 'DESERIALIZE', deserialize );
}

在我的反序列化传奇中,我想处理创建项目的内存中版本的副作用,我需要从存储中读取现有数据。我不确定如何在这里做到这一点,或者这是否是我什至应该尝试使用 redux-saga 的模式。

您可以使用选择效果

import {select, ...} from 'redux-saga/effects'
function* deserialize( action ) {
    const state = yield select();
    ....
    yield put({ type: 'DESERIALIZE_COMPLETE' });
}

您也可以将其与选择器一起使用

const getItems = state => state.items;
function* deserialize( action ) {
    const items = yield select(getItems);
    ....
    yield put({ type: 'DESERIALIZE_COMPLETE' });
}

除了 @Kokovin Vladislav 的答案之外,如果我们喜欢使用 Typescript 的类型,我们可以在这个文档中使用 redux-toolkit 引入的"定义的类型化钩子"模式:https://redux-toolkit.js.org/tutorials/typescript#define-typed-hooks。

因此,在app/hooks.ts文件中,我们有:

import { useDispatch, useSelector } from 'react-redux'
import type { TypedUseSelectorHook } from 'react-redux'
import type { RootState, AppDispatch } from './store'
import { select } from 'redux-saga/effects'
// Use throughout your app instead of plain `useDispatch` and `useSelector` ( From redux-toolkit docs )
export const useAppDispatch: () => AppDispatch = useDispatch
export const useAppSelector: TypedUseSelectorHook<RootState> = useSelector
// THIS IS THE ADDITIONAL SELECTOR!!!!!!!
export function* appSelect<TSelected>( selector: (state: RootState) => TSelected, ): Generator<any, TSelected, TSelected> { return yield select(selector); }

然后在生成器函数中,您可以像这样做:

import { appSelect } from "app/hooks"
function* deserialize( action ) {
    const items = yield* appSelect(state => state.items);
    ....
    yield put({ type: 'DESERIALIZE_COMPLETE' });
}

这样,我们就在每次调用appSelect()时都有很强的打字和state智能。

信用:https://github.com/redux-saga/redux-saga/issues/970#issuecomment-880799390

如果我们在回调函数中,当 Saga 不处理代码流时,选择效果对我们没有帮助。在这种情况下,只需传递dispatchgetState根传奇:

store.runSaga(rootSaga, store.dispatch, store.getState)

并将参数传递给子传奇

export default function* root(dispatch, getState) { yield all([ fork(loginFlow, dispatch, getState), ]) }

然后在手表方法中

export default function* watchSomething(dispatch, getState) ...