createAsyncThunk创建的action无法使用dispatch
相关平台
微信小程序
小程序基础库: 3.4.1 使用框架: React
复现步骤
- 在slice中定义foo = createAsyncThunk(...),并在createSlice的extrareducers中使用build.addCase(foo.pending...)等
- 在页面中使用dispatch(foo)
期望结果
foo定义的async functionf
实际结果
执行时报错:AbortController is not defined
ReferenceError: AbortController is not defined
at vendors-node_modules_taro_weapp_prebundle_reduxjs_toolkit_js.js?t=wechat&s=1713083731279&v=c3009756f740784f3e1fbc8afa686d9b:2359
at vendors-node_modules_taro_weapp_prebundle_reduxjs_toolkit_js.js?t=wechat&s=1713083731279&v=c3009756f740784f3e1fbc8afa686d9b:1525
at vendors-node_modules_taro_weapp_prebundle_reduxjs_toolkit_js.js?t=wechat&s=1713083731279&v=c3009756f740784f3e1fbc8afa686d9b:1790
at vendors-node_modules_taro_weapp_prebundle_reduxjs_toolkit_js.js?t=wechat&s=1713083731279&v=c3009756f740784f3e1fbc8afa686d9b:1614
at Object.current (index.tsx?cf8d:13)
at Object.callback (vendors-node_modules_taro_weapp_prebundle_tarojs_plugin-framework-react_dist_runtime_js.js?t=wechat&s=1713083731279&v=dc9330fe3530ade2dc87a23f82bc3b47:96)
at vendors-node_modules_taro_weapp_prebundle_chunk-H5CKLZB7_js.js?t=wechat&s=1713083731279&v=1f79f6e1c526573bda1897e0aa961ea9:1131
at Array.map (<anonymous>)
at safeExecute (vendors-node_modules_taro_weapp_prebundle_chunk-H5CKLZB7_js.js?t=wechat&s=1713083731279&v=1f79f6e1c526573bda1897e0aa961ea9:1131)
at AppWrapper.<anonymous> (vendors-node_modules_taro_weapp_prebundle_chunk-H5CKLZB7_js.js?t=wechat&s=1713083731279&v=1f79f6e1c526573bda1897e0aa961ea9:1209)(env: macOS,mp,1.06.2402040; lib: 3.4.1)
环境信息
taro info
👽 Taro v3.6.26
(node:65681) [DEP0040] DeprecationWarning: The `punycode` module is deprecated. Please use a userland alternative instead.
(Use `node --trace-deprecation ...` to show where the warning was created)
Taro CLI 3.6.26 environment info:
System:
OS: macOS 14.4.1
Shell: 5.9 - /bin/zsh
Binaries:
Node: 21.7.2 - /opt/homebrew/bin/node
npm: 10.5.0 - /opt/homebrew/bin/npm
npmPackages:
@tarojs/cli: 3.6.26 => 3.6.26
@tarojs/components: 3.6.26 => 3.6.26
@tarojs/helper: 3.6.26 => 3.6.26
@tarojs/plugin-framework-react: 3.6.26 => 3.6.26
@tarojs/plugin-platform-alipay: 3.6.26 => 3.6.26
@tarojs/plugin-platform-h5: 3.6.26 => 3.6.26
@tarojs/plugin-platform-jd: 3.6.26 => 3.6.26
@tarojs/plugin-platform-qq: 3.6.26 => 3.6.26
@tarojs/plugin-platform-swan: 3.6.26 => 3.6.26
@tarojs/plugin-platform-tt: 3.6.26 => 3.6.26
@tarojs/plugin-platform-weapp: 3.6.26 => 3.6.26
@tarojs/react: 3.6.26 => 3.6.26
@tarojs/runtime: 3.6.26 => 3.6.26
@tarojs/shared: 3.6.26 => 3.6.26
@tarojs/taro: 3.6.26 => 3.6.26
@tarojs/taro-loader: 3.6.26 => 3.6.26
@tarojs/webpack5-runner: 3.6.26 => 3.6.26
babel-preset-taro: 3.6.26 => 3.6.26
eslint-config-taro: 3.6.26 => 3.6.26
react: ^18.0.0 => 18.2.0
补充信息
实际taro版本是3.6.26(无可选项)
解决方法: 1,安装这俩包:yet-another-abortcontroller-polyfill,event-target-polyfill 2,app.js import: import 'event-target-polyfill'; import 'yet-another-abortcontroller-polyfill';
感谢!按你的解决方法成功运行了。
不过是否应该从Taro框架本身引入才更好呢。
我按照seekerliu https://github.com/seekerliu 提供的解决方案已经可以正常使用了。
On May 8, 2024, at 15:40, 悟 @.***> wrote:
兄弟,我的不是报错,而是无法捕捉结果。不知道是啥原因,你们之前使用成功了吗?
Taro v3.6.28
extraReducers: (builder) => { builder.addCase(fetchUser.pending, (state, action) => { console.log(action) }); builder.addCase(fetchUser.rejected, (state, action) => { console.log(action) }); // Add reducers for additional action types here, and handle loading state as needed builder.addCase(fetchUser.fulfilled, (state, action) => { console.log('success', action) }) } — Reply to this email directly, view it on GitHub https://github.com/NervJS/taro/issues/15517#issuecomment-2099947523, or unsubscribe https://github.com/notifications/unsubscribe-auth/AFA7VLX6G2AEYL7MJBD25DLZBHJH5AVCNFSM6AAAAABGIQ5H7KVHI2DSMVQWIX3LMV43OSLTON2WKQ3PNVWWK3TUHMZDAOJZHE2DONJSGM. You are receiving this because you authored the thread.
@hikzhang 我遇到的问题是,模拟器正常,真机调试dispatch之后action没有执行。我的是抖音小程序。
装了以后直接白屏了
解决方法: 1,安装这俩包:yet-another-abortcontroller-polyfill,event-target-polyfill 2,app.js import: import 'event-target-polyfill'; import 'yet-another-abortcontroller-polyfill';
重新启动看看呢?似乎有些编译缓存不会被更新到。
On May 17, 2024, at 09:57, 悟 @.***> wrote:
装了以后直接白屏了
解决方法: 1,安装这俩包:yet-another-abortcontroller-polyfill,event-target-polyfill 2,app.js import: import 'event-target-polyfill'; import 'yet-another-abortcontroller-polyfill';
— Reply to this email directly, view it on GitHub https://github.com/NervJS/taro/issues/15517#issuecomment-2116489957, or unsubscribe https://github.com/notifications/unsubscribe-auth/AFA7VLTSE5UEZNZGBY2JCJTZCVPY3AVCNFSM6AAAAABGIQ5H7KVHI2DSMVQWIX3LMV43OSLTON2WKQ3PNVWWK3TUHMZDCMJWGQ4DSOJVG4. You are receiving this because you were mentioned.
遇到了同样的问题,感谢 @seekerliu
装了以后直接白屏了
解决方法: 1,安装这俩包:yet-another-abortcontroller-polyfill,event-target-polyfill 2,app.js import: import 'event-target-polyfill'; import 'yet-another-abortcontroller-polyfill';
解决了吗,我也是装完白屏
装了以后直接白屏了
解决方法: 1,安装这俩包:yet-another-abortcontroller-polyfill,event-target-polyfill 2,app.js import: import 'event-target-polyfill'; import 'yet-another-abortcontroller-polyfill';
解决了吗,我也是装完白屏
我放弃了,移除了redux
装了以后直接白屏了
解决方法: 1,安装这俩包:yet-another-abortcontroller-polyfill,event-target-polyfill 2,app.js import: import 'event-target-polyfill'; import 'yet-another-abortcontroller-polyfill';
解决了吗,我也是装完白屏
我放弃了,移除了redux
我这边解决了,后面遇到的同学可以参考,微信小程序应该是可以通过上述的polyfill方案解决 抖音小程序因为限制了globalThis和window的访问,pollyfill不行,引入那两个包以后会白屏,通过分析可以知道这个报错的主要原因是createAsyncThunk里面维护的promise abort状态导致的,可以通过绕过createAsyncThunk来解决,比如:
- 手动维护请求的状态
- 或者用redux-thunk之类的库去维护异步请求状态就可以避免了 参考:
import { createSlice } from '@reduxjs/toolkit';
import axios from 'axios';
const initialState = {
data: null,
loading: false,
error: null,
// 添加一个额外的字段
userId: null, // 假设我们需要使用这个字段来决定是否请求数据
};
const mySlice = createSlice({
name: 'mySlice',
initialState,
reducers: {
fetchStart: (state) => {
state.loading = true;
state.error = null;
},
fetchSuccess: (state, action) => {
state.loading = false;
state.data = action.payload;
},
fetchError: (state, action) => {
state.loading = false;
state.error = action.payload;
},
setUserId: (state, action) => {
state.userId = action.payload;
},
},
});
export const { fetchStart, fetchSuccess, fetchError, setUserId } = mySlice.actions;
// 修改后的 fetchData,读取 state
export const fetchData = () => async (dispatch, getState) => {
const state = getState(); // 读取当前 state
const { userId } = state.mySlice; // 从 state 中获取 userId
// 如果 userId 不存在或无效,则不进行请求
if (!userId) {
console.warn('User ID is required for this request');
return;
}
dispatch(fetchStart()); // 请求开始,设置 loading 为 true
try {
const response = await axios.get(`https://api.example.com/data/${userId}`); // 使用 state 中的 userId
dispatch(fetchSuccess(response.data)); // 请求成功,设置 data 和 loading 状态
} catch (error) {
dispatch(fetchError(error.toString())); // 请求失败,设置 error 和 loading 状态
}
};
export default mySlice.reducer;
现在好多库都有依赖AbortController 上面的方法尝试过无效,官方有什么更好的方案吗?