node.js - lowDb - 内存不足
问题描述
我在 Node.js 中有一个内存不足的问题,当我检查堆的快照时,我看到很多不能被垃圾收集的大字符串。
我使用lowDB,这些字符串主要是lowDb文件的内容。
原则上的问题...
当我使用 FileAsync (所以写入文件是异步的)并且我做了很多(触发并忘记)写入时......我的堆空间是否有可能充满等待文件系统的等待堆栈条目写完?(并且节点可以为每个完成的写入清除内存)。
当我使用 lowDB 保存我执行的算法的日志消息时,我做了很多写入。稍后我想查找特定执行的日志消息。所以基本上:
{
executions: [
{
id: 1,
logEvents: [...]
},
{
id: 2,
logEvents: [...]
},
...
]
}
我对节点处理的简化图片是:
- 我的脚本是堆栈上的下一个脚本并运行
- 每次写入都有一些东西在等待文件系统返回答案
- 这东西让我的记忆膨胀,每个“东西”都保存了lowdb文件的全部内容(多次?!)
示例打字稿代码尝试一下:
import * as lowDb from 'lowdb';
import * as FileAsync from 'lowdb/adapters/FileAsync';
/* first block just for generating random data... */
const characters = 'ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789';
const charactersLength = characters.length;
const alphanum = (length: number) => {
const result = new Buffer(length);
for (let i = 0; i < length; i++ ) {
result.write(characters.charAt(Math.floor(Math.random() * charactersLength)));
}
return result.toString('utf8');
};
class TestLowDb {
private adapter = new FileAsync('test.json');
private db;
/* starting the db up, loading with Async FileAdapter */
async startDb(): Promise<void> {
return lowDb(this.adapter).then(db => {
this.db = db;
return this.db.defaults({executions: [], dbCreated: new Date()}).write().then(_ => {
console.log('finished with intialization');
})
});
}
/* fill the database with data, fails quite quickly, finally produces a json like the following:
* { "executions": [ { "id": "<ID>", "data": [ <data>, <data>, ... ] }, <nextItem>, ... ] } */
async fill(): Promise<void> {
for (let i = 0; i < 100; i++) {
const id = alphanum(3);
this.start(id); // add the root id for this "execution"
for (let j = 0; j < 100; j++) {
this.fireAndForget(id, alphanum(1000));
// await this.wait(id, alphanum(1000));
}
}
}
/* for the first item in the list add the id with the empty array */
start(id:string): void {
this.db.get('executions')
.push({id, data:[]})
.write();
}
/* ignores the promise and continues to work */
fireAndForget(id:string, data:string): void {
this.db.get('executions')
.find({id})
.get('data')
.push(data)
.write();
}
/* returns the promise that the caller can handle it "properly" */
async wait(id:string, data:string): Promise<void> {
return this.db.get('executions')
.find({id})
.get('data')
.push(data)
.write();
}
}
const instance = new TestLowDb();
instance.startDb().then(_ => {
instance.fill()
});
enter code here
解决方案
推荐阅读
- php - 使用 Laravel Storage 获取文件的完整路径
- javascript - 如何在选择框中添加禁用选项或默认选项?
- wpf - 使用 click、MouseEnter 和 MouseLeave 的按钮/图像切换资源
- java - 从 IDE 运行 Spark SQL 应用程序的 setJars() 方法
- r - Parellize xgboost 建模模拟
- c# - 使用 Entity Framework Core 的 SQL Server 查询中的参数化 OPENJSON
- python - 获取动作计数
- spinnaker - 如何删除附加到集群的 Kubernetes 提供者帐户。(该集群已删除)
- c++ - 该函数应返回 1 但它返回 0
- php - cakephp 3 get 方法不返回字段