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

点击Add Task按钮时Bootstrap模态框无法打开问题排查求助(附相关代码)

Fixing Bootstrap Modal Not Popping & Other Issues in Your React TodoList

Hey there! Let's work through the problems you're facing with your TodoList app—first the unresponsive Add Task modal, then the other subtle bugs that are causing it (and other issues) behind the scenes.

1. The Root Cause: Immediate Function Execution on Delete Button

Your hunch about the delete button was spot-on! Here's why it's breaking things:

<button className="btn" onClick={handleDelete(todo.todo_id)}>Delete</button>

When you write handleDelete(todo.todo_id) directly in the onClick prop, this function runs immediately when the component renders—not when you click the button. This triggers a delete request for every todo item as soon as the page loads, which messes up your app's state and can interfere with Bootstrap's modal initialization.

Fix: Use an Arrow Function for Click Callback

Change the delete button to wrap the function call in an arrow function so it only runs on click:

<button className="btn" onClick={() => handleDelete(todo.todo_id)}>Delete</button>

2. Fix the refreshList Filter Logic

Right now, your filter in refreshList doesn't actually do anything—you're filtering the response data but not saving the filtered result to state:

response.data.filter( (item) => item.completed === viewCompleted );
setTodoList(response.data);

This means your todo list is always showing all tasks, not just uncompleted ones. Update it to:

const filteredTasks = response.data.filter(item => item.completed === viewCompleted);
setTodoList(filteredTasks);

3. Bootstrap Modal Dependencies

Bootstrap 4+ modals require jQuery and Popper.js to function properly. If you haven't added these to your project, the modal won't pop up even if your React code is correct. Add these CDN links to your public/index.html file (before the Bootstrap CSS/JS):

<script src="https://code.jquery.com/jquery-3.6.0.min.js"></script>
<script src="https://cdn.jsdelivr.net/npm/popper.js@1.16.1/dist/umd/popper.min.js"></script>
<script src="https://cdn.jsdelivr.net/npm/bootstrap@4.6.0/dist/js/bootstrap.min.js"></script>

4. Small Typo in AddTask Component

Your Close button uses class instead of className (React's version of HTML class attribute)—this won't break the modal, but it's a good habit to fix:

<!-- Before -->
<button type="button" class="btn btn-danger" data-dismiss="modal">Close</button>

<!-- After -->
<button type="button" className="btn btn-danger" data-dismiss="modal">Close</button>

Updated Code Snippets

Fixed UncompletedTaskView.js

import React,{useState} from 'react';
import axios from 'axios';
import AddTask from './AddTask';
import EditButton from './EditButton';

const UncompletedTaskView = () => {
 const [todoList,setTodoList] = useState([]);
 const [viewCompleted,setViewCompleted] = useState(false);

 const refreshList = async () => {
 try {
 const response = await axios.get("http://localhost:8000/api/tasks/");
 // Apply filter and save to state
 const filteredTasks = response.data.filter(item => item.completed === viewCompleted);
 setTodoList(filteredTasks);
 } catch(err) {
 console.log(err.message);
 }
 };

 const handleDelete = async (id) => {
 await axios.delete(`http://localhost:8000/api/tasks/${id}/`);
 refreshList();
 };

 return (
 <div className="container">
 <h1 className='text-black text-uppercase text-center my-4'>Todo List</h1>
 <table className="table table-hover">
 <thead>
 <tr>
 <th>Title</th>
 <th>Description</th>
 <th>Mark Completed</th>
 <th>Edit</th>
 <th>Delete</th>
 </tr>
 </thead>
 <tbody>
 { todoList.map((todo) => {
 return <tr id={todo.todo_id}>
 <td>{todo.title}</td>
 <td>{todo.description}</td>
 <td className="radio">
 <label><input type="radio" name="optradio" onClick={() => setViewCompleted(true)}/>Completed</label>
 </td>
 <td><EditButton refreshList={refreshList}/></td>
 <td>
 <button className="btn" onClick={() => handleDelete(todo.todo_id)}>
 Delete
 </button>
 </td>
 </tr>
 }) }
 </tbody>
 </table>
 <AddTask refreshList={refreshList}/>
 </div>);
}

export default UncompletedTaskView;

Fixed AddTask.js

import React,{ useState} from 'react';
import axios from 'axios';

const AddTask = ({ refreshList }) => {
 const [title,setTitle] = useState("");
 const [description,setDescription] =useState("");
 const completed= false;

 const handleSubmit = async() => {
 const item = {
 "title" : title,
 "description": description,
 "completed": completed
 };
 try {
 await axios.post(`http://localhost:8000/api/tasks/`, item);
 refreshList();
 // Reset form fields after submission
 setTitle("");
 setDescription("");
 } catch (err) {
 console.log(err.message);
 }
 }

 return (<div>
 <button type="button" className="btn btn-success" data-toggle="modal" data-target="#myModal">
 Add Task
 </button>
 <div className="container">
 <div className="modal fade" id="myModal" role="dialog">
 <div className="modal-dialog">
 <div className="modal-content">
 <div className="modal-header">
 <button type="button" className="close" data-dismiss="modal">&times;</button>
 <h4 className="modal-title">Add Task</h4>
 </div>
 <div className="modal-body">
 <label htmlFor="title">Title</label>
 <input type="text" name="title" value={title} onChange={ (e) => setTitle(e.target.value)} placeholder="Task Title" />
 <label htmlFor="description">Description</label>
 <input type="text" name="description" value={description} onChange={ (e) => setDescription(e.target.value)} placeholder="Task Description" />
 </div>
 <div className="modal-footer">
 <button type="button" className="btn btn-success" onClick={handleSubmit}>Add</button>
 <button type="button" className="btn btn-danger" data-dismiss="modal">Close</button>
 </div>
 </div>
 </div>
 </div>
 </div>
 </div>)
}

export default AddTask;

I also added a small bonus: resetting the form fields after submitting a new task for better user experience.

Give these fixes a try—your modal should pop up as expected, and the delete button will work correctly too!

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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.04.29 19:27:37