我已经看到注销后清除/重置商店的解决方案,但不明白如何为以下设置 redux 商店的方式实现相同的功能。
商店.js:
import { configureStore, getDefaultMiddleware } from '@reduxjs/toolkit'
import authReducer from './ducks/authentication'
import snackbar from './ducks/snackbar'
import sidebar from './ducks/sidebar'
import global from './ducks/global'
import quickView from './ducks/quickView'
import profileView from './ducks/profileView'
const store = configureStore({
reducer: {
auth: authReducer,
snackbar,
sidebar,
global,
quickView,
profileView,
},
middleware: [...getDefaultMiddleware()],
})
export default store
Run Code Online (Sandbox Code Playgroud)
以下是使用@reduxjs/toolkit 中的 createAction 和 createReducer 实现所有 reducer 的方法。
小吃店.js:
import { createAction, createReducer } from '@reduxjs/toolkit'
export const handleSnackbar = createAction('snackbar/handleSnackbar')
export const openSnackBar = …Run Code Online (Sandbox Code Playgroud) 每当 URL 包含带有 ID 的查询参数时,我都会尝试使用数据库中的信息预填充表单。当从数据库中获取信息时,我无法使站点触发重新渲染。组件中的相关代码如下所示。
let { id } = useParams();
const { title, summary, severity, references, type, vulnerabilities } = useSelector(
(state: RootState) => state.articles.article
)
useEffect(() => {
if(id) dispatch(fetchArticle(id))
}, [])
const [form, setForm] = useState<FormState>({
title: title,
type: type,
summary: summary,
severity: severity,
references: references,
vulnerabilities: vulnerabilities,
autocompleteOptions: autocompleteSuggestions,
reference: "",
vulnerability: "",
})
useEffect(() => {
setForm({
...form,
title: title,
summary: summary,
severity: severity,
references: references,
type: type,
vulnerabilities: vulnerabilities
})
}, [title, summary, severity, …Run Code Online (Sandbox Code Playgroud) 我希望两个不同的切片能够交叉引用彼此的操作,如下所示:
const sliceA = createSlice({
name: "sliceA",
initialState: null,
reducers: {
someReducer: (state, action) => {
// do something
},
},
extraReducers: {
[sliceB.actions.anotherReducer]: (state, action) => {
// do something
},
},
});
const sliceB = createSlice({
name: "sliceB",
initialState: null,
reducers: {
anotherReducer: (state, action) => {
// do something else
},
},
extraReducers: {
[sliceA.actions.someReducer]: (state, action) => {
// do something else
},
},
});
Run Code Online (Sandbox Code Playgroud)
问题是我在尝试为 sliceA 设置 extraReducers 时收到 sliceB 未定义的错误。
为了清楚起见,我想将切片分开,但它们的某些操作会相互影响。
实现这一目标的好方法是什么?
我是 Redux 和 Redux 工具包的新手。我了解到createSelector可以接受多个输入选择器,它们可以作为单独的参数或数组提供。所有输入选择器的结果作为单独的参数提供给输出选择器。
const selectA = state => state.a;
const selectB = state => state.b;
const selectC = state => state.c;
const selectABC = createSelector(
[selectA, selectB, selectC],
(a, b, c) => {
// do something with a, b, and c, and return a result
return a + b + c;
}
);
Run Code Online (Sandbox Code Playgroud)
我的问题是,如果我只关心一个简单的状态,我可以这样使用useSelector吗
const selectA = state => state.a;
const a = useSelector(selectA)
Run Code Online (Sandbox Code Playgroud)
这两种用法有什么区别?
我有这个小模块管理片:
const WorkspaceSlice = createSlice({
name: "workspace",
initialState: {
activeModule: null,
modules:
{
["someModule"]: { ...moduleRenderingData },
},
},
reducers: {
setActiveModule(state, action)
{
state.activeModule = action.payload;
},
addModule(state, action)
{
const { moduleName, renderingData } = action.payload;
if (!state.modules[moduleName])
{
state.modules[moduleName] = renderingData;
}
// state.activeModule = moduleName; <- basically the same as 'setActiveModule'
this.setActiveModule(state, action.payload.module); // <- 'this' is undefined
},
},
});
export default WorkspaceSlice;
Run Code Online (Sandbox Code Playgroud)
我想要做的是setActiveModule从内部调用,addModule这样我就不会有重复的代码,但我收到一个错误,因为this未定义。
有没有办法从另一个内部调用一个减速器?那的语法是什么?
如果没有,是否有可能以另一种方式实现此功能,假设我想同时保留addModule和setActiveModule …
我最近开始使用redux-toolkit并开始使用createSlice以下他们的文档编写我的减速器。
一个减速器,我们称之为reducerA,导入customAsyncFunction来处理它的回调,这个函数是通过createAsyncThunk它创建的,通过它依次读取RootState调用时thunkApi.getState(),现在的问题RootReducer是导入时,reducerA将被导入生成循环引用。
基本上:RootReducer -> reducerA -> actions -> RootReducer -> ...
下面我尝试简化问题。
// actions.ts file
import { RootState } from "./RootReducer";
export const customAsyncAction = createAsyncAction("myaction", async (_, thunkApi) =>
const state = thinkApi.getState() as RootState;
...
);
// reducerA.ts file
import { customAsyncAction } from "./actions";
const slice = createSlice({
...
extraReducers: {
[customAsyncAction.fulfilled.toString()]: ... // handles fulfilled action
}
}); …Run Code Online (Sandbox Code Playgroud) 我试图通过名为 的 redux 操作重置状态resetState,其中我将状态分配给initialState变量,但这不起作用。
const initialState = {
someArray: [],
someEvents: {}
}
const stateSlice = createSlice({
name: "someState",
initialState,
reducers: {
...someActions,
resetState: (state, action) => {
// THIS DOES NOT WORK
state = initialState
},
resetState2: (state, action) => {
// THIS WORKS!!!!
return initialState
},
});
Run Code Online (Sandbox Code Playgroud)
当我返回初始状态时,状态会正确重置,但将其分配给initialState不会。
您好,我试图让 redux 继续使用 redux 工具包(也在打字稿中),但出现以下错误:
Exported variable 'store' has or is using name '$CombinedState' from external module "home/..../node_modules/redux/index" but cannot be named.
我看到这个问题之前在这里被问过,但也没有得到回答。
以下是我的代码,如果您有解决此问题的想法,请告诉我,谢谢
import { configureStore, getDefaultMiddleware } from "@reduxjs/toolkit";
import {combineReducers} from 'redux';
import { TypedUseSelectorHook, useDispatch, useSelector } from "react-redux";
import myModuleReducer from "../../modules/my-module/redux/my-module-slice";
import myModuleTwoReducer from "../../modules/my-module-two/redux/my-module-two-slice";
import {
persistStore,
persistReducer,
FLUSH,
REHYDRATE,
PAUSE,
PERSIST,
PURGE,
REGISTER,
} from 'redux-persist'
import storage from 'redux-persist/lib/storage' // defaults to localStorage for web
const persistConfig = { …Run Code Online (Sandbox Code Playgroud) 在我的 api 上,我有两个突变,奇怪的是,其中一个确实触发了重新获取,但另一个没有,我不知道为什么。这两种突变都会进行网络调用,并且更改会反映在服务器中。
这是我的 api 定义。
import { createApi, fetchBaseQuery } from "@reduxjs/toolkit/dist/query/react";
import Sample from "core/types/Sample";
import getApiURL from "core/utils/getApiURL";
export const lithologyApi = createApi({
baseQuery: fetchBaseQuery({ baseUrl: getApiURL() }),
tagTypes: ["Samples"],
endpoints: build => ({
addSample: build.mutation<Sample, Sample>({
query: sample => ({
url: `lithology/add-sample`,
method: "POST",
body: sample,
}),
invalidatesTags: ["Samples"],
}),
getSamples: build.query<Sample[], void>({
query: () => "lithology/get-samples",
providesTags: ["Samples"],
}),
deleteSample: build.mutation<void, number>({
query: id => ({ url: `lithology/delete-sample/${id}`, method: "DELETE" }),
invalidatesTags: ["Samples"],
}),
}), …Run Code Online (Sandbox Code Playgroud) 我怎样才能记住我的rawTranscript变量,这样它就不会触发useEffect下面的函数,从而触发昂贵的transcriptParser函数?我一直在尝试很多不同的方法,但事实上,我使用 redux-hook ( useAppSelector) 从存储中捕获数据意味着我无法使用空依赖项 useEffect 进行初始安装(钩子不能位于内部)使用效果)。出于同样的原因,我似乎也无法用useAppSelector任何一个来包装。useMemo
关于如何记住变量rawTranscript以便它不会重新触发的任何想法useEffect?
useMemo在, ,useEffect中使用 redux-hook 时出错useCallback:
React Hook“useAppSelector”无法在回调内调用。React Hooks 必须在 React 函数组件或自定义 React Hook 函数中调用。
成分
const TranscriptCardController = (): JSX.Element => {
const dispatch = useAppDispatch();
// how to memoize rawTranscript?
const rawTranscript = useAppSelector(selectRawTranscript);
const parsedTranscript = useAppSelector(selectParsedTranscript);
useEffect(() => {
const parsedResult = transcriptParser(rawTranscript, undefined, 0.9);
dispatch(updateParsedTranscript(parsedResult));
}, [dispatch, rawTranscript]);
// ... …Run Code Online (Sandbox Code Playgroud) redux-toolkit ×10
reactjs ×8
redux ×7
react-redux ×4
javascript ×2
typescript ×2
reselect ×1
rtk-query ×1