You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

Redux异步Action的Promise回调中执行setState报错如何解决

报错原因

  1. 未捕获Promise拒绝:你在Action返回的Promise中请求失败时会执行reject(false),但组件调用时只写了then回调,没有添加catch回调处理失败情况,一旦请求出错就会抛出未捕获的Promise异常。
  2. 已卸载组件更新状态:如果异步请求完成前,当前组件已经被卸载(比如用户提前退出页面、路由跳转),此时在then回调中调用setStep会触发已卸载组件的状态更新,React会抛出对应的更新错误。
  3. 你当前的thunk中finally逻辑为空,请求结束后没有关闭加载状态,可能触发SpinnerButton组件的状态异常,和组件状态更新同时触发时会导致渲染冲突。
  4. switch分支没有default兜底逻辑,如果type不匹配会导致url为空、data为null,直接触发请求失败。

解决方法

  1. 给Promise调用添加catch回调处理错误情况,同时添加组件挂载状态判断,避免卸载后更新状态:
// 组件内新增挂载标记
const isMounted = useRef(true);
useEffect(() => {
  return () => {
    isMounted.current = false;
  };
}, []);

const onPressBuyCharge = () => {
  dispatch(
    otherServices({
      type: SimCard_Charge,
      payload: {
        phoneNumber: phoneNumber,
        amount: amount,
        ewallets: selectedServicesWalletOptions,
      },
    })
  ).then(res => {
    if (isMounted.current) {
      setStep('input');
    }
  }).catch(err => {
    if (isMounted.current) {
      // 这里可以添加请求失败的提示逻辑,比如弹出toast
      console.log('请求失败', err);
    }
  });
};
  1. 补全thunk中的finally逻辑,关闭加载状态:
// 在otherServices的Promise中修改finally逻辑
.finally(() => {
  dispatch(toggleButtonSpinner(false));
});
  1. 给switch添加default分支,避免未知type导致请求参数异常:
switch (type) {
  // 原有case逻辑
  default: 
    return Promise.reject('未知的服务类型');
}

可选优化

你当前使用的InputNumber组件用的是defaultPhone属性,属于非受控组件,当切回input步骤时如果phoneNumber被清空,可能不会更新输入框显示,建议改成受控组件:

<InputNumber
  value={phoneNumber}
  onChangeText={e => onChangePhone(e)}
  onPressSimCard={onPressSimCard}
  onPressContacts={onPressSelectContacts}
/>

内容的提问来源于stack exchange,提问作者Mohamadamin

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.09.26 03:36:01