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

React中type为submit的删除按钮未触发onSubmit事件问题

问题分析

点击Update按钮时,updateItem执行后能正常触发handleSubmit,但点击Remove按钮时,只有removeItem执行,handleSubmit没触发。核心原因是:

  • Remove按钮的onClick会删除当前列表项,React会立即重新渲染,对应<li>元素被卸载,导致后续的表单提交事件因为触发元素已不存在而被中断。
  • Update按钮只是修改列表项的属性,组件不会被卸载,所以提交事件能完整执行。
解决方案

这里提供两种可行的解决思路:

思路一:延迟状态更新,让提交事件先执行

把删除操作放到setTimeout里,让表单提交事件先完成,再执行删除:

const removeItem = (id: number) => {
  // 用setTimeout把状态更新放到下一轮事件循环,确保submit先触发
  setTimeout(() => {
    setItems(items.filter((item) => item.id !== id));
  }, 0);
};

思路二:统一在submit事件中处理状态更新

把按钮的操作逻辑移到handleSubmit里,避免因组件卸载中断事件流:

  1. 修改按钮,添加标识属性区分操作类型
  2. 在handleSubmit中根据标识执行对应逻辑

修改后的完整代码:

import React, { useState } from "react";

function MyForm() {
  const [items, setItems] = useState([
    { id: 1, name: "item1" },
    { id: 2, name: "item2" },
    { id: 3, name: "item3" },
  ]);

  const removeItem = (id: number) => {
    setItems(items.filter((item) => item.id !== id));
  };

  const updateItem = (id: number) => {
    setItems(
      items.map((item) => {
        if (item.id === id) {
          return { ...item, name: "test" };
        } else {
          return item;
        }
      })
    );
  };

  const handleSubmit = (event: any) => {
    event.preventDefault();
    const target = event.submitter; // 获取触发提交的按钮
    const action = target.dataset.action;
    const id = Number(target.dataset.id);

    if (action === "update") {
      updateItem(id);
    } else if (action === "remove") {
      removeItem(id);
    }

    console.log("submit");
  };

  return (
    <form onSubmit={handleSubmit}>
      <ul>
        {items.map((item) => (
          <li key={item.id}>
            {item.name}
            <button type="submit" data-action="remove" data-id={item.id}>
              Remove
            </button>
            <button type="submit" data-action="update" data-id={item.id}>
              Update
            </button>
          </li>
        ))}
      </ul>
    </form>
  );
}

export default MyForm;

这种方式更符合表单的设计逻辑,所有操作都通过submit事件统一处理,避免了组件卸载导致的事件中断问题。

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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.06.13 05:06:12