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

React Redux Toolkit中addProgress逻辑求助:待办任务无法移至进行中

Redux Toolkit Todo迁移至InProgress功能修复方案

我在实践Redux Toolkit时遇到问题:待办任务(Todo)迁移至进行中(InProgress)模块的功能失效,addTodo功能正常,但addProgress无法工作。核心错误是当前addProgress逻辑在progress的state中查找对应id的任务,正确逻辑应该是从todos的state中获取该任务,添加至progress并从todos中移除。

1. 为todosSlice添加移除任务的Reducer

在todosSlice.js中新增removeTodo reducer,用于移除被迁移的任务:

import { createSlice } from "@reduxjs/toolkit";

const todosSlice = createSlice({
  name: "todos",
  initialState: [],
  reducers: {
    addTodo: (state, action) => {
      // 替换固定id为动态生成的唯一值,避免重复
      state.push({
        id: Date.now(),
        text: action.payload,
      });
    },
    toggleTodo: (state, action) => {
      const todo = state.find((todo) => todo.id === action.payload);
      if (todo) {
        todo.completed = !todo.completed;
      }
    },
    // 新增移除任务的reducer
    removeTodo: (state, action) => {
      return state.filter(todo => todo.id !== action.payload);
    }
  },
});

export const { addTodo, toggleTodo, removeTodo } = todosSlice.actions;
export default todosSlice.reducer;

2. 修改progressSlice,使用createAsyncThunk处理跨slice操作

单个slice的reducer无法直接访问其他slice的state,因此用createAsyncThunk处理跨slice的任务迁移逻辑:

import { createSlice, createAsyncThunk } from "@reduxjs/toolkit";
import { removeTodo } from "../todo/todosSlice";

// 创建异步thunk,处理任务迁移
export const addProgress = createAsyncThunk(
  "progress/addProgress",
  async (todoId, { getState, dispatch }) => {
    // 从全局state中获取todos列表
    const { todos } = getState();
    const targetTodo = todos.find(todo => todo.id === todoId);
    if (targetTodo) {
      // 先移除todos中的目标任务
      dispatch(removeTodo(todoId));
      // 返回任务数据用于添加到progress
      return targetTodo;
    }
    return null;
  }
);

const progressSlice = createSlice({
  name: "progress",
  initialState: [],
  reducers: {},
  // 通过extraReducers处理thunk的执行结果
  extraReducers: (builder) => {
    builder
      .addCase(addProgress.fulfilled, (state, action) => {
        if (action.payload) {
          // 将任务添加到progress列表
          state.push(action.payload);
        }
      });
  }
});

export default progressSlice.reducer;

3. 组件调用保持不变

Todo组件中的按钮逻辑无需修改,确保正确引入新的addProgress即可:

import { addProgress } from '../features/inProgress/inProgressSlice';

// 按钮部分
<button
  onClick={() => {
    dispatch(addProgress(todo.id))
  }}
>
  移至进行中
</button>

4. 优化InProgress组件

保留核心渲染逻辑,移除不必要的加载判断:

import React from "react";
import { useSelector } from "react-redux";

const InProgress = () => {
  const progress = useSelector((state) => state.progress);

  return (
    <div>
      <div>
        <h2>In Progress</h2>
        <ul>
          {progress.map((item) => (
            <li key={item.id}>{item.text}</li>
          ))}
        </ul>
      </div>
    </div>
  );
};

export default InProgress;

额外注意事项

  • 原todosSlice中addTodo的固定id(111)会导致所有任务id重复,必须替换为动态生成的唯一值(如Date.now()或uuid库),否则会引发任务查找错误。
  • Redux Toolkit内置Immer库,支持在reducer中直接修改state或返回新state,两种写法均有效。

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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.07.30 04:10:26