如何暂停节点REPL并在稍后阶段恢复并保留所有环境?

Pee*_*aha 11 javascript node.js read-eval-print-loop

我希望暂停REPL会话,以便我可以关闭系统,然后在以后继续在REPL会话上工作,好像我从未关闭它,即不必丢失所有环境.

我认为可能的解决方案可能是

  1. 快照内存,保存到文件并稍后从文件加载env:我认为这将是最好的解决方案,就像使用Windows的"休眠"功能时一样.我发现这个heapdump实用程序用于获取内存快照以分析内存泄漏,但我不知道你是否可以从该快照中恢复整个环境,我找不到这样做的工具.

  2. 保存命令并重放它们:这种方法的一个主要缺点是虽然它适用于简单的事情var x = "Hello World";,但它不适用于像var reciptId = bankAccount.makePayment(1000);重复每次重放操作而不是保存原始函数调用的细节的事情.

  3. 序列化/反序列化整个环境:这将涉及制作环境中存在的所有对象的列表,然后建立一种机制将每个对象写入文件,即序列化它们,然后创建一个反序列化这些并加载它们的机制在需要的时候.我还没有看到一个干净的方法来序列化和反序列化js变量没有限制.我认为这个方法的主要限制是它无法保留引用,所以对象松散了它们的类,在序列化时必须重复事物并且在反序列化时失去它们的相等性 - 例如 var f = function (x) {...}; var a = {}; a.f = f; a.f === f? //is true, not true if your serialization mechanism saves a function defn for f and a.f separately and deserializes them separately ,循环引用可能不起作用(x = {}; x.cyclic = x;... ).所以这种方法,如果它工作将需要大量的脏工作.

所以问题是,实现我希望实现的目标有多难?有什么其他解决方案可以做到这一点?实现这一目标是否存在重大阻碍?

此外,是否有任何替代节点repl程序(如浏览器中的控制台)可以像这样暂停?

相关:

pet*_*teb 4

因此,如果您希望能够“暂停”REPL 会话,然后在关闭后从上次中断的地方继续,这似乎在 Node.js 的 REPL 中无法直接实现。与此最接近的是 REPL 的持久历史记录功能,它是在 Node 4.2.1 中添加的(我认为)。这将允许您以纯文本形式查看 REPL 中命令的历史记录,但这是 Node.js 开箱即用的最接近的东西。

持久的历史

默认情况下,REPL 将通过保存到用户主目录中的 .node_repl_history 文件来保留节点 REPL 会话之间的历史记录。可以通过设置环境变量 NODE_REPL_HISTORY="" 来禁用此功能。

以前在 Node.js/io.js v2.x 中,REPL 历史记录是通过使用 NODE_REPL_HISTORY_FILE 环境变量来控制的,并且历史记录以 JSON 格式保存。该变量现已被弃用,您的 REPL 历史记录将自动转换为使用纯文本。新文件将保存到您的主目录或由 NODE_REPL_HISTORY 变量定义的目录,如下所述。

REPL 模块的完整文档可在此处获取。

但是,有一个 REPL“包装器”节点模块可以满足您的要求。您可以做的是将 REPL 历史记录保存到文件中,然后在下一个会话中加载历史文件,并在下一个 REPL 会话中访问您保存到文件中的内容。该模块是Nesh。它有很多附加功能,包括配置 shell 和评估不同版本的 JS,例如 ES6/ES7(使用 Babel)和 Coffeescript。

安装内网:

npm install -g nesh

只需键入 即可在终端中启动 nesh nesh。像在任何其他 REPL 会话中一样正常工作,当您想要保存时,可以在 nesh 中键入以下内容,将 REPL 历史记录保存到给定文件中:

.save <filepath>

在下一个 REPL 会话中,即使在关闭后,您也可以通过键入以下内容重新启动 nesh 会话并重新加载历史记录:

.load <filepath>

这将重新评估整个历史文件,并使所有变量或函数在当前 REPL/nesh 会话中可用。

希望这对您有所帮助,并且我认为它满足您的需求。