我想在NodeJS
中使用reverse interactive search
REPL Ctrl + r
像bash
或irb
一样。如何在NodeJS REPL中使用“反向交互式搜索”?
Ctrl + r
没有触发交互式搜索。有没有办法在Nodejs REPL中使用该函数?
我使用的是MacOS Sierra,NodeJS的版本是v8.5.0
。
我想在NodeJS
中使用reverse interactive search
REPL Ctrl + r
像bash
或irb
一样。如何在NodeJS REPL中使用“反向交互式搜索”?
Ctrl + r
没有触发交互式搜索。有没有办法在Nodejs REPL中使用该函数?
我使用的是MacOS Sierra,NodeJS的版本是v8.5.0
。
这个问题得到回答在最近I pity the foo()博客帖子...
可以反向搜索的命令历史节点的REPL内部使用?
目前看来不可能。 Node REPL允许将历史记录保存到文件中,稍后加载它,但不允许对其进行反向搜索。
所以看起来反向历史搜索并不是REPL原生支持的。
但是,您可以安装rlwrap
实用程序并在Node REPL之上运行它以提供类似的功能。 REPL documentation网站提供了一些基本说明,帮助您启动并运行。我有点好奇,幕后发生了什么,所以多一点谷歌搜索从Learning Node: Moving to the Server Side出来这一部分,这与rlwrap
相关的折衷更详细。例如...
和rlwrap一样有用,每次我们输入一个不返回值的表达式时,我们仍然会以undefined结束。但是,我们可以通过创建自己的定制REPL来调整此功能和其他功能,接下来讨论。
我看到赏金即将结束......我可以拥有吗?如果我告诉你:
跳转到代码部分如果您熟悉历史搜索并希望将其用作替代选项。
您是否熟悉zsh的历史搜索?这几乎就像反向搜索,除了在命令行上输入内容并按方向键up
之后可以开始搜索。我发现它比反向搜索更快,更经常使用它。不利的一面(在我看来是次要的)是你不能在搜索后更新你的原始搜索查询,除非你通过“退后”回到它。例如:
历史(自上而下)
foo
bar
foo-ish
fubar
...
您提示:
> fo
按up
> foo
按up
> foo-ish
按down
> foo
按down
> fo
注意:只要你改变搜索结果,并再次命中up
,改变文字将变为新的查询。
守则
const PROMPT = '> ';
// history search
let input = '';
let searchInput = input;
let searchResults = [];
let searchResultIndex = 0;
process.stdin.on('keypress', (_, key) => {
// update 'input' on changes, excluding history
if (input !== server.line && !['up', 'down'].includes(key.name)) {
input = server.line;
}
// search is initiated if a user presses the 'up' key after having inputted
if (input !== '' && (
key.name === 'up' ||
(key.name === 'down' && searchResultIndex > 0)
)) {
// reset on fresh search or if user changed input during search
if (searchInput !== input) {
searchResultIndex = 0;
// first search result is always user's input
searchResults = [input, ...server.history.filter(item => item.includes(input))];
searchInput = input;
}
const increment = key.name === 'up' ? 1 : -1;
searchResultIndex = Math.min(searchResultIndex + increment, searchResults.length - 1);
server.historyIndex = -1;
server.line = '';
process.stdout.clearLine();
process.stdout.cursorTo(0);
const result = searchResults[searchResultIndex];
process.stdout.write(PROMPT + result);
server.cursor = result.length;
server.line = result;
}
});
奖金 - 要实现持久的历史:
const HISTSIZE = 100;
const server = repl.start({
prompt: PROMPT,
historySize: HISTSIZE,
removeHistoryDuplicates: true,
});
// load history or create file
historyFile = path.join(path.dirname(require.main.filename),
'.repl_history');
try {
fs.statSync(historyFile);
fs.readFileSync(historyFile, 'utf8')
.split('\n')
.filter(line => line.trim())
.map(line => server.history.push(line));
}
catch (e) {
console.log(e);
fs.closeSync(fs.openSync(historyFile, 'w'));
}
server.on('exit',() => {
// save history
fs.writeFileSync(historyFile, server.history.slice(0, HISTSIZE).join('\n'));
console.log('Thank you. Come again.');
process.exit();
});