我希望reverse interactive search
使用NodeJS
Ctrl + r
bash
,irb
或Ctrl + r
。
v8.5.0
未触发互动搜索。有没有办法在Nodejs REPL中使用该函数?
我正在使用MacOS Sierra,而NodeJS的版本为bacteria_id generation DNA_vector
213 230 23
254 230 18
256 229 39
289 229 16
310 228 24
324 228 45
。
答案 0 :(得分:1)
最近I pity the foo()博客文章中回答了这个问题......
可以在Node的REPL中使用命令历史中的反向搜索吗?
目前似乎不可能。 Node REPL允许将历史记录保存到文件中,然后加载它,但不允许反向搜索它。
因此看起来REPL本身不支持反向历史搜索。
但是,您可以安装rlwrap
实用程序并在Node REPL之上运行它以提供类似的功能。 REPL documentation网站提供了一些基本说明,可帮助您启动和运行。我有点好奇幕后发生的事情,所以谷歌更多地从Learning Node: Moving to the Server Side出现了这一部分,其中详细介绍了与使用rlwrap
相关的权衡。例如......
与rlwrap一样有用的是,每当我们输入一个不返回值的表达式时,我们仍然会得到undefined。但是,我们可以通过创建我们自己的自定义REPL来调整此功能和其他功能,下面将对此进行讨论。
答案 1 :(得分:1)
我看到赏金即将结束......我可以拥有吗?如果我告诉你怎么办?
如果您熟悉历史搜索并希望将其用作替代方法,请跳至代码部分。
您熟悉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();
});