Node.js:如何重新加载模块

Posted

技术标签:

【中文标题】Node.js:如何重新加载模块【英文标题】:Node.js: how to reload module 【发布时间】:2016-02-06 10:11:36 【问题描述】:

我是 NodeJS 的新手,所以可能我犯了一些错误。

我在一个名为 myapp 的外部文件中编写了一堆代码。我为 windows 启动 NodeJS,并从我输入的解释器窗口:

var myapp = require('d:/myapp.js');

然后我可以在外部模块中使用我的函数和变量。

问题是,如果我更新 myapp 中的代码,则解释器不会重新读取文件,而是使用旧版本。

首先,这正常吗?如何解决这个问题?

P.S.:我在互联网上花费了数小时并在包括这个在内的许多论坛中进行了搜索。这比其他任何事情都更令人困惑。

谢谢。

【问题讨论】:

node.js require() cache - possible to invalidate?的可能重复 你的答案在副本中 哦!小心,接受的答案不正确,我喜欢这个 -> ***.com/a/16060619/1430607 【参考方案1】:

在 cmets 中建议有 some answers here。

但是它们对 REPL 不友好,甚至可能使用额外的模块。

这是一个可以粘贴到 REPL 中的单行解决方案,灵感来自对另一个问题的讨论:

function nocache(module) require("fs").watchFile(require("path").resolve(module), () => delete require.cache[require.resolve(module)])

每次文件更改时,该函数都会从缓存中删除您的模块。 要使用它,只需将其粘贴到 REPL 中,调用nocache("d:/myapp.js"),然后正常使用require

> function nocache(module) require("fs").watchFile(require("path").resolve(module), () => delete require.cache[require.resolve(module)])
> nocache("d:/myapp.js");
> var myapp = require("d:/myapp.js");
......
> myapp = require("d:/myapp.js");
....

【讨论】:

在寻找快速即插即用解决方案一段时间后,我认为您的解决方案是迄今为止最好的解决方案。您可以将此答案复制并粘贴到大量类似的问题中并获得大量积分。 你写“uncache”的地方应该写“nocache”吧? @PedroMachado 这是正确的,更新的答案。感谢您发现它。【参考方案2】:

我通过在require 语句上方添加以下内容解决了这个问题:

Object.keys(require.cache).forEach(function(key)  delete require.cache[key] )

取自@Dancrumb 的评论here

【讨论】:

【参考方案3】:

其他答案(一式两份,由@mihai 提供)都是正确的,但对这个具体示例最直接的答案是

delete require.cache['d:/myapp.js'];

模块缓存在require.cache 中,键控为完整 文件名。在这种特殊情况下,完整的文件名( d:/myapp.js)用于加载,因此问题的解决方案非常简单。

然而,在大多数情况下,完整的文件名是不被使用的,甚至是未知的。例如,require('fs') 将用于加载文件系统模块,但开发人员会丢失完整和正确的文件名。因此,require.resolve('fs') 将返回用作缓存模块的键的文件名。

【讨论】:

我使用了delete require.cache[require.resolve('../path/to/file.js')]; -- 比查找完整文件名更容易

以上是关于Node.js:如何重新加载模块的主要内容,如果未能解决你的问题,请参考以下文章

如何欺骗 Node.js 将 .js 文件加载为 ES6 模块?

Node.js 说它不能加载 sqlite3 模块,但无论如何

如何在不重新加载页面的情况下将任意 JSON 发送到 node.js?

如何让 TypeScript 以生成工作 Node.JS 代码的方式加载 PDF.js NPM 模块和 @types 绑定?

从内存中的字符串加载 node.js 模块

node.js