我使用 node-influx 和 influx.query(...) 使用太多堆。
在我的应用程序中,我有类似的内容
const data = await influx.query(`SELECT "f_power" as "power", "nature", "scope", "participantId"
FROM "power"
WHERE
"nature" =~ /^Conso$|^Prod$|^Autoconso$/ AND
"source" =~ /^$|^One$|^Two AND
"participantId" =~ /${participantIdFilter.join('|')}/ AND
"time" >= '${req.query.dateFrom}' AND
"time" <= '${req.query.dateTo}'
GROUP BY "timestamp"
`);
wb = dataToWb(data)
XLSX.writeFile(wb, filename);
数据是约50M的结果集( I used this code ) 而该方法使用的堆大约为350M(我使用了process.memoryUsage().heapUsed)
我对这两个值之间的差异感到惊讶...... 那么是否可以减少此查询的资源消耗?
其实我是用data来制作xlsx文件的。而这个文件的生成导致 Node 进程内存不足。 XLSX.writeFile(wb, filename)方法使用了大约100M。那是不够填满我的512M RAM。所以我认为这是流入查询使用的堆,它永远不会被 GC 收集。
其实我不明白为什么这一代人会犯这个错误。为什么 V8 无法释放在另一个上下文之后执行的方法所使用的内存?
最佳答案
node-influx(1.x 客户端)读取整个响应,将其解析为 JSON,并将其转换为结果(数据数组)。在处理响应期间,堆上有更多的中间对象。您还应该在查询之前和之后运行 Node 垃圾收集器,以更好地估计它需要多少堆。现在,您只能通过减少结果列或行(按限制、时间或聚合)来控制结果内存使用情况。您还可以联接结果较小的查询,以减少临时对象导致的最大堆使用量。当然,这是由代码的时间和复杂性付出的代价。
2.x 客户端 ( https://github.com/influxdata/influxdb-client-js ) 的内存使用量预计会更少。它不会创建中间 JSON 对象,在内部处理较小块的结果,它具有类似 observable 的 API,可让用户决定如何表示结果行。它使用 FLUX 作为查询语言,需要 InfluxDB 2.x 或 InfluxDB 1.8(启用 2.x API)。
关于node.js - 查询时node-influx的内存使用情况,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/66747910/