Я уже давно пытаюсь решить мою проблему без какого-либо успеха. Ни один не нашел я подобный вопрос здесь.
Я сталкиваюсь с проблемой времени отклика, когда я отправляю 20 запросов агрегации в mongod, и для выполнения всех 20 запросов требуется более 5 секунд, в то время как каждая отдельная агрегация решается в течение 1 мс. Я ожидаю, что код будет работать под 50 мс.
Одна из основных проблем заключается в том, что результаты поступают в виде блоковых блоков с явной видимой задержкой в 1 секунду. Я получаю 1 результат за соединение в секунду. Каждую секунду создается дополнительное соединение, поэтому я получаю 1,2,3,4,5 результатов в секунду.
После многих попыток я могу ограничить проблему mongod. Я использовал приведенный ниже код node.js на 3 разных машинах, в то время как на локальном компьютере я получаю эту диспетчеризацию блоков и общее время выполнения более 5 секунд. На двух других машинах результат завершается за <50 мс, без каких-либо блоков и тех 1-секундных задержек в той же базе данных. </p>
//console output - you can see the block dispatch.
//first section connects to mongod and send 20x the same quarry to mongod
18:16:25.440Z INFO WS BOT/test3.js: MONGO SUCCESFULLY CONNECTED!
18:16:25.441Z DEBUG WS BOT/test3.js: 0 Start... %dms
//(...) while loop to send the aggregations to mongod finished in about 10ms - which is fine.
18:16:25.450Z DEBUG WS BOT/test3.js: 18 Start... %dms
18:16:25.451Z DEBUG WS BOT/test3.js: 19 Start... %dms
//now the results of the mongo aggregations should come:
// First Block dispatch - 14ms after the request. Which is fine! But only 1 of 20 request
18:16:25.455Z DEBUG WS BOT/test3.js: 0 End... 0s 14.150247ms
// Second Block dispatch - 1 second 14ms after the request. 2 Results.
18:16:26.475Z DEBUG WS BOT/test3.js: 1 End... 1s 28.834198ms
18:16:26.476Z DEBUG WS BOT/test3.js: 2 End... 1s 28.880778ms
// Third Block dispatch - 2 seconds after the request. 3 Results.
18:16:27.486Z DEBUG WS BOT/test3.js: 3 End... 2s 38.423885ms
18:16:27.487Z DEBUG WS BOT/test3.js: 5 End... 2s 38.926009ms
18:16:27.488Z DEBUG WS BOT/test3.js: 4 End... 2s 40.08026ms
// Fourth Block dispatch - 3 seconds after the request. 4 Results.
18:16:28.502Z DEBUG WS BOT/test3.js: 6 End... 3s 53.779308ms
18:16:28.503Z DEBUG WS BOT/test3.js: 8 End... 3s 54.27472ms
18:16:28.504Z DEBUG WS BOT/test3.js: 9 End... 3s 55.358707ms
18:16:28.505Z DEBUG WS BOT/test3.js: 7 End... 3s 56.856392ms
// now you see each second with increasing results per second
18:16:29.519Z DEBUG WS BOT/test3.js: 13 End... 4s 69.557508ms
18:16:29.520Z DEBUG WS BOT/test3.js: 10 End... 4s 70.682548ms
18:16:29.520Z DEBUG WS BOT/test3.js: 14 End... 4s 70.377011ms
18:16:29.521Z DEBUG WS BOT/test3.js: 11 End... 4s 71.37652ms
18:16:29.535Z DEBUG WS BOT/test3.js: 12 End... 4s 85.550058ms
18:16:30.538Z DEBUG WS BOT/test3.js: 15 End... 5s 87.94975ms
18:16:30.539Z DEBUG WS BOT/test3.js: 16 End... 5s 88.68675ms
18:16:30.540Z DEBUG WS BOT/test3.js: 19 End... 5s 88.786227ms
18:16:30.540Z DEBUG WS BOT/test3.js: 17 End... 5s 90.013903ms
18:16:30.541Z DEBUG WS BOT/test3.js: 18 End... 5s 90.523922ms
Я упростил код и запросил 20 раз один и тот же запрос с таким же медленным ответом.
Это мой код:
const MongoClient = require('mongodb').MongoClient;
const dbName = 'kd';
var db;
//Connect to Mongo first. Once connnected, send 20x the same aggregation.
MongoClient.connect(`mongodb://${config.mongo.user}:${config.mongo.password}@localhost:${config.mongo.port}/${config.mongo.dbname}?authSource=${config.mongo.authSource}`, { useNewUrlParser: true, poolSize: 10 })
.then((data) => {
log.info("MONGO SUCCESFULLY CONNECTED!")
db = data.db(dbName);
for (var i = 0; i < 20; i++) {
aggregation(i)
}
})
.catch(e => { log.error(e)})
// aggregation which will be used (simplified)
function aggregation(i) {
var hrstart = process.hrtime()
log.debug(`${i} Start... %dms`)
db.collection("s.log").aggregate([
{ $match: { "updated_at": { $gte: yesterday } } },
{ $sort: { updated_at: 1 } },
],
function(err, cursor) {
if (err) { log.error(err)}
else {
cursor.toArray(function(err,product) {
hrend = process.hrtime(hrstart)
log.debug(`${i} End... %ds %dms`, hrend[0], hrend[1] / 1000000)
})
}
})
}
Я попытался увеличить poolSize, чтобы у драйвера было больше подключений, и он мог запускать их параллельно, но безуспешно.
Использование Mongoose приводит к такой же низкой производительности.
Я также проверил mongostat, без чего-либо видимого, за исключением того, что соединения увеличиваются на одну в секунду
*0 *0 *0 *0 0 13|0 0.1% 3.4% 0 1.03G 40.0M 0|0 1|0 10.4k 73.4k 3 Mar 22 14:07:52.173
*0 *0 *0 *0 0 12|0 0.1% 3.4% 0 1.03G 40.0M 0|0 1|0 6.72k 66.3k 3 Mar 22 14:07:53.201
*0 *0 *0 *0 0 17|0 0.1% 3.4% 0 1.03G 40.0M 0|0 1|0 7.97k 68.5k 4 Mar 22 14:07:54.210
insert query update delete getmore command dirty used flushes vsize res qrw arw net_in net_out conn time
*0 *0 *0 *0 0 18|0 0.1% 3.4% 0 1.03G 40.0M 0|0 1|0 8.62k 70.4k 5 Mar 22 14:07:55.198
*0 *0 *0 *0 0 20|0 0.1% 3.4% 0 1.03G 40.0M 0|0 1|0 14.0k 74.5k 6 Mar 22 14:07:56.207
*0 *0 *0 *0 0 20|0 0.1% 3.4% 0 1.04G 40.0M 0|0 1|0 9.23k 70.7k 7 Mar 22 14:07:57.198
*0 *0 *0 *0 0 20|0 0.1% 3.4% 0 1.04G 40.0M 0|0 1|0 9.37k 69.7k 8 Mar 22 14:07:58.207
*0 *0 *0 *0 0 22|0 0.1% 3.4% 0 1.04G 40.0M 0|0 1|0 10.0k 71.6k 9 Mar 22 14:07:59.198
*0 *0 *0 *0 0 13|0 0.1% 3.4% 0 1.04G 41.0M 0|0 1|0 6.90k 67.6k 10 Mar 22 14:08:00.206
*0 *0 *0 *0 0 14|0 0.1% 3.4% 0 1.04G 41.0M 0|0 1|0 7.07k 68.7k 10 Mar 22 14:08:01.203
*0 *0 *0 *0 0 13|0 0.1% 3.4% 0 1.04G 41.0M 0|0 1|0 21.0k 84.8k 10 Mar 22 14:08:02.162
*0 *0 *0 *0 0 11|0 0.1% 3.4% 0 1.04G 41.0M 0|0 1|0 1.36k 60.4k 10 Mar 22 14:08:03.200
Это журнал system.profile, который показывает, что каждый запрос выполняется за <1 мс.
Здесь вы также можете увидеть задержку в 1 секунду до того, как mongod выполнит запрос и выполнит 1 операцию на соединение в секунду. </p>
> db.system.profile.find({ns: "kdm.shop.log"}, {ts: 1, millis: 1}).sort({ ts: -1}).limit(20)
{ "millis" : 0, "ts" : ISODate("2019-03-22T18:16:30.538Z") }
{ "millis" : 0, "ts" : ISODate("2019-03-22T18:16:30.538Z") }
{ "millis" : 0, "ts" : ISODate("2019-03-22T18:16:30.537Z") }
{ "millis" : 0, "ts" : ISODate("2019-03-22T18:16:30.536Z") }
{ "millis" : 1, "ts" : ISODate("2019-03-22T18:16:30.535Z") }
{ "millis" : 0, "ts" : ISODate("2019-03-22T18:16:29.534Z") }
{ "millis" : 0, "ts" : ISODate("2019-03-22T18:16:29.519Z") }
{ "millis" : 0, "ts" : ISODate("2019-03-22T18:16:29.519Z") }
{ "millis" : 0, "ts" : ISODate("2019-03-22T18:16:29.518Z") }
{ "millis" : 0, "ts" : ISODate("2019-03-22T18:16:29.518Z") }
{ "millis" : 0, "ts" : ISODate("2019-03-22T18:16:28.504Z") }
{ "millis" : 0, "ts" : ISODate("2019-03-22T18:16:28.503Z") }
{ "millis" : 1, "ts" : ISODate("2019-03-22T18:16:28.502Z") }
{ "millis" : 1, "ts" : ISODate("2019-03-22T18:16:28.501Z") }
{ "millis" : 0, "ts" : ISODate("2019-03-22T18:16:27.488Z") }
{ "millis" : 0, "ts" : ISODate("2019-03-22T18:16:27.487Z") }
{ "millis" : 0, "ts" : ISODate("2019-03-22T18:16:27.486Z") }
{ "millis" : 1, "ts" : ISODate("2019-03-22T18:16:26.476Z") }
{ "millis" : 2, "ts" : ISODate("2019-03-22T18:16:26.474Z") }
{ "millis" : 0, "ts" : ISODate("2019-03-22T18:16:25.453Z") }
У кого-нибудь есть идея, почему она такая медленная и почему задержка отправки блока составляет 1 секунду? Кажется, что он увеличивает количество соединений каждую секунду на 1, но он выполняет только 1 операцию на соединение.
Даже если он использует только одно соединение и выполняет одну операцию каждый раз, это должно быть намного быстрее - как показано на двух других моих системах!
Спасибо за вашу помощь. Если вам нужна дополнительная информация, дайте мне знать!
С уважением,
Meffesino