在 React + Firebase 中,如何删除在创建时已被赋予唯一 ID 的列表项?
How do I delete a list item that has been given a unique id when created, in React + Firebase?
我正在使用 React 和 Firebase 创建待办事项列表。到目前为止,我已经创建了 AddToDo 功能,但是,现在我在使用删除功能时遇到了问题。我相信这就是我的问题所在。例如,当我尝试单击我设置的删除图标时,出现错误:
Unhandled Runtime Error
TypeError: Cannot read properties of undefined (reading 'id')
这就是代码,如果有帮助的话。 AddLink.js
import { useState, useEffect } from "react";
import classes from "./addlink.module.css";
import firebase from "firebase/app";
import initFirebase from "../../config";
import "firebase/firestore";
import Todo from "../Todo/Todo";
import { v4 as uuidv4 } from "uuid";
initFirebase();
const db = firebase.firestore();
function AddLink(props) {
const [todos, setTodos] = useState([]);
const [input, setInput] = useState("");
useEffect(() => {
db.collection("links")
.orderBy("timestamp", "desc")
.onSnapshot((snapshot) => {
// this gives back an array
setTodos(
snapshot.docs.map((doc) => ({
id: doc.id,
todo: doc.data().todo,
}))
);
});
}, []);
const addTodo = (event) => {
event.preventDefault();
console.log("clicked");
db.collection("links").add({
id: uuidv4(),
todo: input,
timestamp: firebase.firestore.FieldValue.serverTimestamp(),
});
setInput("");
};
return (
<div className={classes.addlink}>
<form>
<div className={classes.adminlink}>
<input
type="text"
value={input}
onChange={(event) => setInput(event.target.value)}
/>
<button
className={classes.adminbutton}
type="submit"
onClick={addTodo}
>
Add new link
</button>
</div>
</form>
{todos.map((todo, id) => (
<Todo value={todo} key={id} />
))}
{/* {modalIsOpen && (
<Modal onCancel={closeModalHandler} onConfirm={closeModalHandler} />
)}
{modalIsOpen && <Backdrop onCancel={closeModalHandler} />} */}
</div>
);
}
export default AddLink;
和Todo.js
import React from "react";
import { AiOutlinePicture } from "react-icons/ai";
import { AiOutlineStar } from "react-icons/ai";
import { GoGraph } from "react-icons/go";
import DeleteForeverIcon from "@material-ui/icons/DeleteForever";
import classes from "./todo.module.css";
import firebase from "firebase/app";
import initFirebase from "../../config";
import "firebase/firestore";
initFirebase();
const db = firebase.firestore();
function Todo(props) {
const deleteHandler = () => {
db.collection("todos").doc(props.todo.id).delete();
};
return (
<li className={classes.adminsection}>
<div className={classes.linkCards}>
<h3>{props.text}</h3>
<p>This is a new link</p>
<div>
<AiOutlinePicture />
<AiOutlineStar />
<GoGraph />
<DeleteForeverIcon onClick={deleteHandler} />
</div>
</div>
</li>
);
}
export default Todo;
如有任何帮助,我们将不胜感激。
const deleteHandler = () => {
db.collection("todos").doc(props.todo.id).delete();
};
您应该将 props.todo.id
替换为 props.value.id
。
const deleteHandler = () => {
db.collection("todos").doc(props.value.id).delete();
};
或者您可以更改:
<Todo value={todo} key={id} />
到
<Todo todo={todo} key={id} />
您用来访问 props.value
的密钥应该与 jsx 模板中声明的密钥相同。使用 proptypes 可以帮助您避免这些错误。
从数据库中删除后,您应该更新状态,UI 为
Todos.filter(d=>d.id !== id of deleted list item)
我正在使用 React 和 Firebase 创建待办事项列表。到目前为止,我已经创建了 AddToDo 功能,但是,现在我在使用删除功能时遇到了问题。我相信这就是我的问题所在。例如,当我尝试单击我设置的删除图标时,出现错误:
Unhandled Runtime Error
TypeError: Cannot read properties of undefined (reading 'id')
这就是代码,如果有帮助的话。 AddLink.js
import { useState, useEffect } from "react";
import classes from "./addlink.module.css";
import firebase from "firebase/app";
import initFirebase from "../../config";
import "firebase/firestore";
import Todo from "../Todo/Todo";
import { v4 as uuidv4 } from "uuid";
initFirebase();
const db = firebase.firestore();
function AddLink(props) {
const [todos, setTodos] = useState([]);
const [input, setInput] = useState("");
useEffect(() => {
db.collection("links")
.orderBy("timestamp", "desc")
.onSnapshot((snapshot) => {
// this gives back an array
setTodos(
snapshot.docs.map((doc) => ({
id: doc.id,
todo: doc.data().todo,
}))
);
});
}, []);
const addTodo = (event) => {
event.preventDefault();
console.log("clicked");
db.collection("links").add({
id: uuidv4(),
todo: input,
timestamp: firebase.firestore.FieldValue.serverTimestamp(),
});
setInput("");
};
return (
<div className={classes.addlink}>
<form>
<div className={classes.adminlink}>
<input
type="text"
value={input}
onChange={(event) => setInput(event.target.value)}
/>
<button
className={classes.adminbutton}
type="submit"
onClick={addTodo}
>
Add new link
</button>
</div>
</form>
{todos.map((todo, id) => (
<Todo value={todo} key={id} />
))}
{/* {modalIsOpen && (
<Modal onCancel={closeModalHandler} onConfirm={closeModalHandler} />
)}
{modalIsOpen && <Backdrop onCancel={closeModalHandler} />} */}
</div>
);
}
export default AddLink;
和Todo.js
import React from "react";
import { AiOutlinePicture } from "react-icons/ai";
import { AiOutlineStar } from "react-icons/ai";
import { GoGraph } from "react-icons/go";
import DeleteForeverIcon from "@material-ui/icons/DeleteForever";
import classes from "./todo.module.css";
import firebase from "firebase/app";
import initFirebase from "../../config";
import "firebase/firestore";
initFirebase();
const db = firebase.firestore();
function Todo(props) {
const deleteHandler = () => {
db.collection("todos").doc(props.todo.id).delete();
};
return (
<li className={classes.adminsection}>
<div className={classes.linkCards}>
<h3>{props.text}</h3>
<p>This is a new link</p>
<div>
<AiOutlinePicture />
<AiOutlineStar />
<GoGraph />
<DeleteForeverIcon onClick={deleteHandler} />
</div>
</div>
</li>
);
}
export default Todo;
如有任何帮助,我们将不胜感激。
const deleteHandler = () => {
db.collection("todos").doc(props.todo.id).delete();
};
您应该将 props.todo.id
替换为 props.value.id
。
const deleteHandler = () => {
db.collection("todos").doc(props.value.id).delete();
};
或者您可以更改:
<Todo value={todo} key={id} />
到
<Todo todo={todo} key={id} />
您用来访问 props.value
的密钥应该与 jsx 模板中声明的密钥相同。使用 proptypes 可以帮助您避免这些错误。
从数据库中删除后,您应该更新状态,UI 为
Todos.filter(d=>d.id !== id of deleted list item)