我正在学习react-redux,我正在使用JSON占位符创建一个简单的CRUD应用,现在我可以使用post和delete方法显示数据并删除数据,但是我不知道如何使用put方法更新数据在redux中,我需要帮助。
**
以下是沙盒中的实时演示:redux live demo
**
这是我到目前为止所拥有的用户组件(只是代码的一部分)
return(
<div>
<table id="users">
<thead>
<tr>
<th>Id</th>
<th>Name</th>
<th>Action</th>
</tr>
</thead>
{userData &&
userData.users &&
userData.users.map(user =>
<tbody>
{user.editing ? <UserForm user={user} key={user.id} />:
<tr key={user.id}>
<td>{user.id}</td>
<td>{user.name}</td>
<td>
<button key={user.id} type="button" className="btn btn-danger btn-link" onClick={() => deleteUser(user.id)}>
<i className="material-icons">delete</i>
</button>
<button key={user.id} type="button" className="btn btn-success btn-link" onClick={() =>editUser(user.id)}>
<i className="material-icons">edit</i>
</button>
</td>
</tr>
}
</tbody>
)}
</table>
</div>
)
这是userfom组件
import React from 'react'
import { useForm } from "react-hook-form";
function UserForm() {
const { edit, handleSubmit} = useForm();
return (
<div>
<form onSubmit={handleSubmit}>
<input name="name" defaultValue="test" ref={edit} />
<input type="submit" />
</form>
</div>
)
}
export default UserForm
这是reducer中的Edit用户
case ActionTypes.EDIT_USER:
return{
...state,
users:state.users.map((user)=>user.id === action.payload ? {
...user,editing:!user.editing
}:user)
}
现在,当我单击“编辑并提交数据”时,它将刷新页面,并且用户信息中没有任何更新(check it here live
我的代码有什么问题?
答案 0 :(得分:1)
好吧,我对react-hook-form的知识不多,但是我会尽力帮助您,首先您需要将一个函数传递给您的“ handleSubmit”,因为否则我认为您不会阻止提交的默认行为,我的意思是handleSubmit函数不执行'event.preventDefault()',因此您可以将以下内容放在useForm钩子下面:
const onSubmit = data => {
console.log(data);
}
然后您将在jsx中拥有
<form onSubmit={handleSubmit(onSubmit)}>
我不确定,因为正如我告诉您的那样,我不使用react-hook-form,但是我认为我看到的另一个错误是您正试图从useForm钩子获取'edit'属性,那将行不通,您未在其中声明变量,而是尝试从useForm钩子访问属性,因此为了跟踪输入的更改,应使用“ register”,我的意思是应该具有以下内容代码:
const { register, handleSubmit } = useForm();
您应该使用以下内容更新jsx:
<input name="name" defaultValue="test" ref={register} />
现在,每次提交时,您都将获得带有我们在onSubmit函数中添加的console.log中所做更改的表单。 您已经将redux与Users组件连接了,我的意思是您正在使用mapDispatchToProps,并且由于在Users组件内部,您将能够访问edit属性以调度editUser动作。因此,为了继续使用redux,您可以通过this.props.editUser将该prop传递给UserForm组件,然后继续。另一个选择是将UserForm组件与redux连接并访问editUser属性。
答案 1 :(得分:0)
我已修改您的代码,更新用户现在可以工作。
// need to pass whole user data as parameter
export const updateUser = data => {
return dispatch => {
axios
// add data into axios second arg
.put(`https://jsonplaceholder.typicode.com/users/${data.id}`, data)
.then(response => {
dispatch(editUser(data.id));
// refresh user list after successfully update
dispatch(fetchUsers());
})
.catch(error => {
const errorMsg = error.message;
dispatch(fetchUsersFailure(errorMsg));
});
};
};
您不需要react-hook-form,只需使用react-redux提供的useDispatch钩子即可。
import React from "react";
import { useDispatch } from "react-redux";
import { editUser, updateUser } from "../redux/acitons/users/Users";
function UserForm({ user }) {
const dispatch = useDispatch();
const [name, setName] = React.useState(user.name);
const handleSubmit = () => {
dispatch(updateUser({ ...user, name }));
};
const handleCancel = () => {
dispatch(editUser(user.id));
};
return (
{/* I modify it to inline edit row */}
<tr>
<td>{user.id}</td>
<td>
<input
defaultValue={user.name}
onChange={e => setName(e.target.value)}
/>
</td>
<td>
<button type="button" className="btn" onClick={handleCancel}>
<i className="material-icons">Cancel</i>
</button>
<button
type="button"
className="btn btn-success btn-link"
onClick={handleSubmit}
>
<i className="material-icons">save</i>
</button>
</td>
</tr>
);
}
export default UserForm;
但是您会注意到,成功更新后,新用户列表仍然很旧,这是正常的 https://github.com/typicode/jsonplaceholder/issues/42#issuecomment-284507310
我建议您按功能将动作/减少器/常量分成一个文件,这在您的应用增长时很有用,当代码库很大时,您可以轻松找到要修改的文件。
例如:
|-- reducers
|---- auth.js
|---- counter.js
|---- index.js
|---- store.js
|---- users.js
这种方法实际上有一个名为duck pattern
的名称。