Skip to content

Commit 5c9dddf

Browse files
TrottMylesBorins
authored andcommitted
debugger: run last command on presssing enter
PR-URL: #6090 Reviewed-By: James M Snell <[email protected]> Reviewed-By: bnoordhuis - Ben Noordhuis <[email protected]> Reviewed-By: Myles Borins <[email protected]> Reviewed-By: Claudio Rodriguez <[email protected]> Reviewed-By: Colin Ihrig <[email protected]> Fixes: #2895
1 parent 033b21b commit 5c9dddf

File tree

5 files changed

+82
-23
lines changed

5 files changed

+82
-23
lines changed

doc/api/debugger.markdown

+3
Original file line numberDiff line numberDiff line change
@@ -84,6 +84,9 @@ The `repl` command allows code to be evaluated remotely. The `next` command
8484
steps over to the next line. Type `help` to see what other commands are
8585
available.
8686

87+
Pressing `enter` without typing a command will repeat the previous debugger
88+
command.
89+
8790
## Watchers
8891

8992
It is possible to watch expression and variable values while debugging. On

lib/_debugger.js

+7-4
Original file line numberDiff line numberDiff line change
@@ -673,6 +673,9 @@ var helpMessage = 'Commands: ' + commands.map(function(group) {
673673
return group.join(', ');
674674
}).join(',\n');
675675

676+
// Previous command received. Initialize to empty command.
677+
var lastCommand = '\n';
678+
676679

677680
function SourceUnderline(sourceText, position, repl) {
678681
if (!sourceText) return '';
@@ -944,10 +947,10 @@ Interface.prototype.requireConnection = function() {
944947
Interface.prototype.controlEval = function(code, context, filename, callback) {
945948
try {
946949
// Repeat last command if empty line are going to be evaluated
947-
if (this.repl.rli.history && this.repl.rli.history.length > 0) {
948-
if (code === '\n') {
949-
code = this.repl.rli.history[0] + '\n';
950-
}
950+
if (code === '\n') {
951+
code = lastCommand;
952+
} else {
953+
lastCommand = code;
951954
}
952955

953956
// exec process.title => exec("process.title");

lib/repl.js

+19-19
Original file line numberDiff line numberDiff line change
@@ -222,6 +222,10 @@ function REPLServer(prompt,
222222
function defaultEval(code, context, file, cb) {
223223
var err, result, retry = false, input = code, wrappedErr;
224224
// first, create the Script object to check the syntax
225+
226+
if (code === '\n')
227+
return cb(null);
228+
225229
while (true) {
226230
try {
227231
if (!/^\s*$/.test(code) &&
@@ -419,28 +423,24 @@ function REPLServer(prompt,
419423
}
420424
}
421425

422-
if (cmd || self.bufferedCommand) {
423-
var evalCmd = self.bufferedCommand + cmd;
424-
if (/^\s*\{/.test(evalCmd) && /\}\s*$/.test(evalCmd)) {
425-
// It's confusing for `{ a : 1 }` to be interpreted as a block
426-
// statement rather than an object literal. So, we first try
427-
// to wrap it in parentheses, so that it will be interpreted as
428-
// an expression.
429-
evalCmd = '(' + evalCmd + ')\n';
430-
self.wrappedCmd = true;
431-
} else {
432-
// otherwise we just append a \n so that it will be either
433-
// terminated, or continued onto the next expression if it's an
434-
// unexpected end of input.
435-
evalCmd = evalCmd + '\n';
436-
}
437-
438-
debug('eval %j', evalCmd);
439-
self.eval(evalCmd, self.context, 'repl', finish);
426+
var evalCmd = self.bufferedCommand + cmd;
427+
if (/^\s*\{/.test(evalCmd) && /\}\s*$/.test(evalCmd)) {
428+
// It's confusing for `{ a : 1 }` to be interpreted as a block
429+
// statement rather than an object literal. So, we first try
430+
// to wrap it in parentheses, so that it will be interpreted as
431+
// an expression.
432+
evalCmd = '(' + evalCmd + ')\n';
433+
self.wrappedCmd = true;
440434
} else {
441-
finish(null);
435+
// otherwise we just append a \n so that it will be either
436+
// terminated, or continued onto the next expression if it's an
437+
// unexpected end of input.
438+
evalCmd = evalCmd + '\n';
442439
}
443440

441+
debug('eval %j', evalCmd);
442+
self.eval(evalCmd, self.context, 'repl', finish);
443+
444444
function finish(e, ret) {
445445
debug('finish', e, ret);
446446
self.memory(cmd);

test/fixtures/debugger-repeat-last.js

+7
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,7 @@
1+
var a = 1;
2+
3+
var b = 2;
4+
5+
var c = 3;
6+
7+
b = c;
+46
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,46 @@
1+
'use strict';
2+
const path = require('path');
3+
const spawn = require('child_process').spawn;
4+
const assert = require('assert');
5+
6+
const common = require('../common');
7+
8+
const fixture = path.join(
9+
common.fixturesDir,
10+
'debugger-repeat-last.js'
11+
);
12+
13+
const args = [
14+
'debug',
15+
fixture
16+
];
17+
18+
const proc = spawn(process.execPath, args, { stdio: 'pipe' });
19+
proc.stdout.setEncoding('utf8');
20+
21+
var stdout = '';
22+
23+
var sentCommand = false;
24+
var sentEmpty = false;
25+
var sentExit = false;
26+
27+
proc.stdout.on('data', (data) => {
28+
stdout += data;
29+
if (!sentCommand && stdout.includes('> 1')) {
30+
setImmediate(() => {proc.stdin.write('n\n');});
31+
return sentCommand = true;
32+
}
33+
if (!sentEmpty && stdout.includes('> 3')) {
34+
setImmediate(() => {proc.stdin.write('\n');});
35+
return sentEmpty = true;
36+
}
37+
if (!sentExit && sentCommand && sentEmpty) {
38+
setTimeout(() => {proc.stdin.write('\n\n\n.exit\n\n\n');}, 1);
39+
return sentExit = true;
40+
}
41+
});
42+
43+
process.on('exit', (exitCode) => {
44+
assert.strictEqual(exitCode, 0);
45+
console.log(stdout);
46+
});

0 commit comments

Comments
 (0)