Нello,以下是我的代码摘录:
let dirUtility = async (...args) => {
let dir = await require('fs').promises.opendir('/path/to/some/dir...');
let entries = dir.entries();
for await (let childDir of dir) doStuffWithChildDir(childDir);
return entries;
};
这个函数在我的代码中被称为"公平"。我的日志中有以下内容:
(node:7920) Warning: Closing directory handle on garbage collection
(Use `node --trace-warnings ...` to show where the warning was created)
(node:7920) Warning: Closing directory handle on garbage collection
(node:7920) Warning: Closing directory handle on garbage collection
(node:7920) Warning: Closing directory handle on garbage collection
(node:7920) Warning: Closing directory handle on garbage collection
- 这些错误究竟有什么意义
- 它们是否表明存在重大问题?(我应该简单地设法让这些错误安静下来吗?(
- 避免这个问题的最佳方法是什么
谢谢!
Raina77ow的回答告诉您显示警告的原因。
基本上,NodeJS运行时在dir
对象上显式调用close()
方法,但最好的做法是在句柄上显式地调用close()
方法,或者更好地将其封装在try..finally
块中。
像这样:
let dirUtility = async (...args) => {
let dir = await require('fs').promises.opendir('/path/to/some/dir...');
try {
let entries = dir.entries();
for await (let childDir of dir) doStuffWithChildDir(childDir);
return entries;
}
finally {
dir.close();
// return some dummy value, or return undefined.
}
};
引用评论(来源(:
// If the close was successful, we still want to emit a process // warning to notify that the file descriptor was gc'd. We want to be // noisy about this because not explicitly closing the DirHandle is a // bug.
虽然您的代码似乎与本问题中的代码非常相似,但有一点不同:
let entries = dir.entries();
...
return entries;
简而言之,这似乎在目录上创建了一个额外的迭代器,该迭代器作为函数的返回值传递到外部。这个迭代器到底是如何使用的还不清楚(因为你没有显示dirUtility
接下来会发生什么(,但要么在GC付出代价之前它还没有耗尽,要么它的使用方式让NodeJS感到困惑。
总的来说,整个方法对我来说似乎并不正确:该函数似乎既对目录做了一些事情,又从本质上讲,将该目录作为其结果返回,而不关心该对象将如何使用。至少,这看起来像是一个漏洞百出的抽象概念。
因此,您似乎需要决定:如果您实际上不使用dirUtility
的返回值,只需删除相应的代码行即可。但是,如果您确实需要保留开放目录(例如,出于性能原因(,请考虑围绕它创建一个有状态的包装器,封装值。只要相应的对象存在于您的代码中,就应该阻止GC使用此句柄。