【问题标题】:Redux: Dispatch actions in sequenceRedux:按顺序调度动作
【发布时间】:2022-01-12 17:27:37
【问题描述】:

我正在 Redux 上创建一个 Reddit 客户端,我在应用中触发了 2 个商店调度:

// App()
const dispatch = useDispatch();

useEffect(() => {
    const stateMatch = window.location.href.match(/state=([^&]*)/);
    const codeMatch = window.location.href.match(/code=([^&]*)/);

    if ((stateMatch && codeMatch) || localStorage.getItem("access_token")) {
        dispatch(fetchUser());
        dispatch(fetchSubs());
    }
});

...

但是,我希望 fetchUser()fetchSubs() 开始之前运行并完成,因为前者目前似乎在运行时破坏了后者的 API 调用。我该如何解决这个问题?

【问题讨论】:

标签: javascript reactjs redux


【解决方案1】:

由于您使用的是createAsyncThunk,因此您可以执行以下操作:

  dispatch(fetchUser())
  .unwrap()
  .then((user) => {
    // do anything you want with user, or don't, also dispatch actions
    dispatch(fetchSubs());
  })
  .catch((e) => {
    // error in case of rejection inside createAsyncThunk second argument
    console.log(e);
  });

说明

假设const thunk = fetchUser() 所以基本上dispatch(fetchUser())dispatch(thunk) 是一样的。

Redux 的 dispatch 函数返回其参数(操作)返回的任何内容。

所以在这种情况下,dispatch(thunk) 返回任何 thunk 返回。

thunk,基于createAsyncThunk 的工作方式,返回一个promise,它要么解析为已完成的操作,要么解析为被拒绝的操作。 (您在额外的 reducer 中收到的那些操作)。

您可以通过以下方式访问这些操作:

dispatch(thunk).then(fullfilledAction=>...).catch(rejectedAction=>...`

RTK 库还提供了一个名为unwrap 的方法。代替我上面解释的那些动作对象,它允许您使用来自createAsyncThunk 的第二个参数的返回值。

export const fetchUser = createAsyncThunk("user/fetchUser", async () => {
const user = await Reddit.getUser().then(val => {
    return val;
});

return user; // unwrap lets you use this instead of action objects.
})

【讨论】:

  • 这成功了!谢谢!如果您可以逐步向我解释这段代码中发生了什么,那也会有所帮助(特别是对unwrap() 感到好奇)。
  • @DavyKamanzi 编辑了我的答案。
【解决方案2】:

用纯 react 和 redux 钩子试试这个

...

const state = useStore(yourStore) //use your method to read state 
const dispatch = useDispatch();
const checkValue = () => {
   const stateMatch = window.location.href.match(/state=([^&]*)/);
    const codeMatch = window.location.href.match(/code=([^&]*)/);

    if ((stateMatch && codeMatch) || localStorage.getItem("access_token")) {
        return true;
    }
    return false;
}

useEffect(() => {
    if(checkValue())
        dispatch(fetchUser());
    }
}, []);

useEffect(() => {
    if(checkValue() && state.authState)
        dispatch(fetchSubs());
    }
}, [state.authState]);


...

【讨论】:

    猜你喜欢
    • 2020-09-10
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2021-10-14
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2021-05-13
    相关资源
    最近更新 更多