React提取帖子需要太长
我将Web服务从Angular转换为反应。与我合作的Angular版本为6.0.x,Nodejs版本为10.18.x。我目前正在使用的React版本为16.14.0,Nodejs升级到12.16.2。
在Angular中,我使用了HTTPClient模块(所有CURD),并且简单而快速。我只需要编写查询并发送请求。
我认为这也同样简单,但显然不是。我正在为所有CRUD使用Fetch,因为它不需要第三方库。我想将第三方库的数量保持尽可能低,因为我必须在云中运行该服务(1 CPU和1GB RAM,具有50GB磁盘尺寸,这并不多)。
到目前为止,我所拥有的如下:
// page.jsx
class Page extends React.Component {
toNext() {
const postData = async() => {
const postResponse = await fetch('/post-data', {
method: 'POST',
headers: { 'Content-Type': 'application/json', 'Accept': 'application/json' },
body: JSON.stringify(this.state.data)
});
return await postResponse;
}
// after uploading successfully, move to anotherpage and load data including the one just loaded.
postData().then(res => res.json()).then((data) => { if (!data.result) this.props.history.push('/anotherpage'); });
}
render() {
return(
<TouchableOpacity onPress={this.toNext}>
)
}
}
// index.js where fetch post is defined with url, query, etc
const express = require('express');
const mysql = require('mysql');
const host = 'host';
const user = 'user';
const password = 'password';
const conn = mysql.createPool({
host: host,
user: user,
password: password,
database: 'database'
});
app.post('/post-data', function (req, res) {
let body = req.body;
let isError = false;
const checkError = () => {
isError = true;
}
for (let row of body) {
console.log('one loop started: ', new Date()) // check if the request itself takes too long
conn.getConnection(function (err, connection) {
connection.query(`INSERT INTO TABLE (COL1, COL2, COL3, ...) VALUES ("${row.COL1}", "${row.COL2}", "${row.COL3}", ...)`,
function (error, results, fields) {
if (error) {
console.log(row)
checkError();
throw error;
};
});
});
console.log('one loop ended: ', new Date()) // check if the request itself takes too long
}
res.send({
'result': isError
});
})
我添加的日志显示,请求本身仅需每行1 ms,但是大约需要4分钟才能上传所有数据(44行,17列,每个单元格,大约10个字符) 。在Angular中,仅需几秒钟(最多只有2秒)。
我试图找到实际的邮政编码的外观(app.post in index.js中),但我得到的只是功能代码(JSX或TSX代码)。我应该如何将数据发布到DB?是否需要这么长时间才能通过获取发布数据?
更新: 正如菲尔在评论中所建议的那样 为什么我们不能在Express中执行多个响应。 。因此,我更改了代码,尽管起初看起来它已经解决了原始问题,但是将数据发布到DB(大约4分钟)时仍然存在。
I am converting web service from Angular to React. Angular version I worked with was 6.0.x and nodejs version was 10.18.x. React version that I am currently working with is 16.14.0 and nodejs is upgraded to 12.16.2.
In Angular, I used HttpClient module (for all CRUD), and it was simple and fast. I just had to write query and send request.
I thought it would be just as simple in React as well, but apparently not. I am using fetch for all CRUD, since it does not require third-party library. I want to keep number of third-party libraries as low as possible, since I have to run the service in the cloud (1 CPU and 1GB RAM with 50GB Disk size, which is not much to work with).
What I have so far is like below:
// page.jsx
class Page extends React.Component {
toNext() {
const postData = async() => {
const postResponse = await fetch('/post-data', {
method: 'POST',
headers: { 'Content-Type': 'application/json', 'Accept': 'application/json' },
body: JSON.stringify(this.state.data)
});
return await postResponse;
}
// after uploading successfully, move to anotherpage and load data including the one just loaded.
postData().then(res => res.json()).then((data) => { if (!data.result) this.props.history.push('/anotherpage'); });
}
render() {
return(
<TouchableOpacity onPress={this.toNext}>
)
}
}
// index.js where fetch post is defined with url, query, etc
const express = require('express');
const mysql = require('mysql');
const host = 'host';
const user = 'user';
const password = 'password';
const conn = mysql.createPool({
host: host,
user: user,
password: password,
database: 'database'
});
app.post('/post-data', function (req, res) {
let body = req.body;
let isError = false;
const checkError = () => {
isError = true;
}
for (let row of body) {
console.log('one loop started: ', new Date()) // check if the request itself takes too long
conn.getConnection(function (err, connection) {
connection.query(`INSERT INTO TABLE (COL1, COL2, COL3, ...) VALUES ("${row.COL1}", "${row.COL2}", "${row.COL3}", ...)`,
function (error, results, fields) {
if (error) {
console.log(row)
checkError();
throw error;
};
});
});
console.log('one loop ended: ', new Date()) // check if the request itself takes too long
}
res.send({
'result': isError
});
})
Logs that I added shows that request itself takes only like 1 ms per row, but it takes about 4 minutes to upload all the data (44 rows, 17 columns, each cell with about 10 characters). In Angular, it only took seconds (2 seconds at most).
I tried to find what the actual post code looks like (app.post part in index.js), but all I got was the function code (jsx or tsx code). How should I go about posting data to DB? Does it take this long to post data via fetch?
UPDATE:
As Phil suggested in the comment,
Why can't we do multiple response.send in Express.js? explains that res.send() should be used only once, since it includes res.end(), and only the first res.send() is executed. So, I changed my code, and although at first, it looked like it fixed the original issue, the delay still exists in posting data to DB (about 4 minutes).
如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

绑定邮箱获取回复消息
由于您还没有绑定你的真实邮箱,如果其他用户或者作者回复了您的评论,将不能在第一时间通知您!
发布评论
评论(1)
如果有人遇到类似问题,这就是我发现的。
当我使用 Node 10.18.X,MySQL软件包2.17.1 和Angular时,我在for-loop中行插入了行,并且它没有任何问题。
但是现在我正在使用节点12.16.2,MySQL软件包2.18.1 和React,并且似乎优于逐行插入。尽管逐行插入有效,但它会延迟,并且在一段时间内插入数据(如几分钟)。我仍然必须找出原因,但是与此同时,我使用了散装插入。
我在 bulk-insertion上遵循了此链接。
我的更新的代码看起来像:
res.send()在内部,因此我认为没有问题,因为只有其中一个是在任何时候执行的。而且,发布没有延迟,因此我所有的数据(44行乘17列)都在一秒钟以下插入。
If there is anyone experiencing a similar problem, here is what I have found.
When I was working with Node 10.18.x, mysql package 2.17.1 and Angular, I inserted row by row in for-loop, and it worked without any problems.
But now I am working with Node 12.16.2, mysql package 2.18.1 and React, and it seems bulk-insertion is preferred to row-by-row insertion. Although row-by-row insertion works, it gives delay and data are inserted over a period of time (like few minutes). I still have to find out why, but in the meantime, I used bulk-insertion.
I followed this link on bulk-insertion.
My updated code looks like:
res.send() is inside if else, so I do not think there is a problem since only one of them is executed at any time. And, there is no delay in posting, so all my data (44 rows by 17 columns) are inserted under a second.