javascript - 反应:为什么我的 id 未定义?axios.post 请求删除数据而不是更新
问题描述
感谢社区,我解决了 axios.get 的动态 ID 问题,${this.props.match.params.id}
我可以访问每个产品的编辑表单。
不幸的是,这个技巧对于发布请求似乎效率低下,我被卡住了。当我提交我的表单时axios.post
,我handleSubmit
会删除我以前的数据,而不是用新的数据进行更新。我可以看到 sql 请求有未定义的数据,尤其是id
,我不明白为什么..
我是 React 的新手,所以你能建议我如何修复我的帖子请求。
我为您提供了我的编辑表单,并且返回的一些节点可能是相关的。
编辑表格
import React, { Component } from 'react';
import { withRouter } from 'react-router';
import axios from 'axios';
import Navbar from 'react-bootstrap/Navbar';
import Nav from 'react-bootstrap/Nav';
import Form from 'react-bootstrap/Form';
import Col from 'react-bootstrap/Col';
import FormControl from 'react-bootstrap/FormControl';
import Button from 'react-bootstrap/Button';
class EditForm extends React.Component {
constructor(props) {
super(props);
this.state = { product: [] };
this.handleChange = this.handleChange.bind(this);
this.handleSubmit = this.handleSubmit.bind(this);
};
componentDidMount = () => {
axios
.get(`/products/edit-form/${this.props.match.params.id}`)
.then(response => {
console.log(response.data.products);
this.setState({
product: response.data.products
})
});
};
handleChange(e) {
this.setState({id: e.target.value})
this.setState({reference: e.target.value})
this.setState({designation: e.target.value})
}
handleSubmit(e) {
e.preventDefault();
const data = {
id: this.state.id,
reference: this.state.reference,
designation: this.state.designation
}
axios
.post(`/products/${data.id}`, data )
.then(res => console.log(res))
.catch(err => console.log(err));
};
renderForm() {
return this.state.product.map((product, index) => {
const { id,reference,designation } = product
return(
<>
<Form className="post" onSubmit={this.handleSubmit}>
<Form.Row>
<Form.Group as={Col} controlId="formGridReference">
<Form.Label>Reference</Form.Label>
<Form.Control type="text" value={reference}
onChange={this.handleChange} name="reference" />
</Form.Group>
<Form.Group as={Col} controlId="formGridDesignation">
<Form.Label>Designation</Form.Label>
<Form.Control type="text" value={designation}
onChange={this.handleChange} name="designation" />
</Form.Group>
</Form.Row>
<Button variant="primary" type="submit">
Submit
</Button>
</Form>
</>
);
})
}
render() {
return (
<div>
<h1>Formulaire de modification</h1>
{this.renderForm()}
</div>
);
}
}
export default withRouter(EditForm);
产品
import React, { Component } from 'react';
import Table from 'react-bootstrap/Table';
import Button from 'react-bootstrap/Button';
import { Link } from 'react-router-dom';
import axios from 'axios';
const headings = [
'id','reference','designation'
];
export default class Products extends Component {
constructor(props) {
super(props);
this.state = {
products: []
};
};
componentDidMount = () => {
axios.get("/products").then(response => {
console.log(response.data.products);
this.setState({
products: response.data.products
})
});
};
renderTableHeader() {
return headings.map((key, index) => {
return <th key={index}>{key.toUpperCase()}</th>
})
}
renderProductData() {
return this.state.products.map((product, index) => {
const { id,reference,designation } = product
return (
<tr key={id}>
<td>
{id}
<Link to={`/edit-form/${id}`}>Modifier</Link>
</td>
<td>{reference}</td>
<td>{designation}</td>
</tr>
)
})
}
render() {
return (
<div>
<h1 id='title'>Produits</h1>
<Table striped bordered hover id='products'>
<thead>
{this.renderTableHeader()}
</thead>
<tbody>
{this.renderProductData()}
</tbody>
</Table>
</div>
);
}
}
应用程序.js
class App extends Component {
render() {
return (
<React.Fragment>
<NavBar />
<Router>
<Route exact path="/" component={Products}/>
<Route path="/edit-form/:id" component={EditForm}/>
</Router>
</React.Fragment>
);
}
}
节点后端
//routes.js
// Get All
router.get('/products', getProducts.getProducts);
// Get sorted
// router.get('/products/:param', getProducts.getProductsSorted);
// Get single
router.get('/products/edit-form/:productId', getProducts.getProduct);
// Update
router.post('/products/:productId', getProducts.postProduct);
// productController.js
const getProduct = async (req, res) =>
{
const { productId } = req.params;
const product = await productDb.getProduct(productId);
res.status(200).send({ products: product.rows });
};
const postProduct = async (req, res) =>
{
const { productId } = req.params;
const { reference,designation } = req.body;
await productDb.updateProduct(productId, reference, designation);
res.status(200).send(`Le produit reference ${reference} a été modifié`);
console.log(`Le produit reference ${reference} a été modifié`);
// productDb.js
const getProduct = async (id) =>
{
const connection = new DbConnection();
return await connection.performQuery(`SELECT * FROM produits WHERE id=${id}`);
};
const updateProduct = async (id, reference, designation) =>
{
const connection = new DbConnection();
await connection.performQuery("UPDATE produits SET reference=?, designation=? WHERE id=?",
[reference, designation, id]);
};
谢谢
解决方案
我会考虑检查状态:
axios
.get(`/products/edit-form/${this.props.match.params.id}`)
.then(response => {
console.log(response.data.products);
this.setState({
product: response.data.products
})
});
这设置product
为一系列产品
handleChange(e) {
this.setState({id: e.target.value})
this.setState({reference: e.target.value})
this.setState({designation: e.target.value})
}
这会设置状态id, reference, designation
- 但请注意它从相同的目标值读取 - 因此,如果参考文本字段发生更改,它将根据 @Asutosh 的评论将 id 和 designation 更改为相同的值。
handleSubmit(e) {
e.preventDefault();
const data = {
id: this.state.product.id,
reference: this.state.product.reference,
designation: this.state.product.designation
};
axios
.post(`/products/${this.props.match.params.id}`, data )
.then(res => console.log(res))
.catch(err => console.log(err));
};
这从产品中读取,但产品是一个数组。但是,这并不能反映在根handleChange
中设置的内容。id, reference, designation
这将导致 id、reference、designation 未定义,因为this.state.product
它是一个数组。
可以做的一个可能的改变是handleChange
:
const data = {
id: this.state.id,
reference: this.state.reference,
designation: this.state.designation
};
但这只有在用户更改了表单中的某些内容时才有效。我们还需要考虑用户可能只是点击提交的事实。
另外,我注意到另一个错误(可能不相关?-阅读评论):
renderForm() {
return this.state.product.map((product, index) => {
const { id,reference,designation } = product // is this used?
return(
<>
<Form className="post" onSubmit={this.handleSubmit}>
<Form.Row>
<Form.Group as={Col} controlId="formGridReference">
<Form.Label>Reference</Form.Label>
{/* this should be reference instead of this.state.product.reference? why is it set as placeholder? */}
<Form.Control type="text" value={this.state.product.reference}
onChange={this.handleChange} name="reference" placeholder={reference} />
</Form.Group>
<Form.Group as={Col} controlId="formGridDesignation">
<Form.Label>Designation</Form.Label>
{/* this should be designation instead of this.state.product.designation? Why is designation set as a placeholder instead? */}
<Form.Control type="text" value={this.state.product.designation}
onChange={this.handleChange} name="designation" placeholder={designation} />
</Form.Group>
</Form.Row>
<Button variant="primary" type="submit">
Submit
</Button>
</Form>
</>
);
})
}
另外,如果目标是基于产品的单个产品提交更改,我会考虑创建一个ProductsList
组件,它保持componentDidMount
,然后创建一个Product
具有handleChange
和的组件handleSubmit
推荐阅读
- php - Prestashop module - Requires PHP 7.1 at least
- join - 不同类型的内连接及其名称
- python - Calculating the overlap area of two sloped rectangles using Python
- javascript - 在另一个之后启动异步功能
- azure - Azure iot edge modules development autoreload
- yii2 - JsTrans Yii Configuration
- java - How to obtain response data in HandlerInterceptor‘s afterCompletion()
- pygame - background not moving in pygame
- python - 移动 Panda Dataframe Python
- python - C# RijndaelManaged vs Python Crypto.Cipher AES + CBC