Skip to content

Commit 84c426c

Browse files
committed
repl: properly handle repl.repl
The repl property is set so that it's possible to inspect the instances own properties during runtime. This was never tested and it was also only exported in case the instance was started with `.start()` instead of using the constructor directly. In case that more than a single instance was created, all instances got access to the first instance. From now on the repl property is only exported in case the repl is starte as standalone program. PR-URL: #30981 Reviewed-By: James M Snell <[email protected]> Reviewed-By: Rich Trott <[email protected]>
1 parent e65bed1 commit 84c426c

File tree

3 files changed

+37
-14
lines changed

3 files changed

+37
-14
lines changed

lib/repl.js

Lines changed: 10 additions & 12 deletions
Original file line numberDiff line numberDiff line change
@@ -234,10 +234,14 @@ function REPLServer(prompt,
234234
throw new ERR_INVALID_REPL_EVAL_CONFIG();
235235
}
236236

237-
// Add this listener only once and use a WeakSet that contains the REPLs
238-
// domains. Otherwise we'd have to add a single listener to each REPL instance
239-
// and that could trigger the `MaxListenersExceededWarning`.
240-
if (!options[kStandaloneREPL] && !addedNewListener) {
237+
if (options[kStandaloneREPL]) {
238+
// It is possible to introspect the running REPL accessing this variable
239+
// from inside the REPL. This is useful for anyone working on the REPL.
240+
exports.repl = this;
241+
} else if (!addedNewListener) {
242+
// Add this listener only once and use a WeakSet that contains the REPLs
243+
// domains. Otherwise we'd have to add a single listener to each REPL
244+
// instance and that could trigger the `MaxListenersExceededWarning`.
241245
process.prependListener('newListener', (event, listener) => {
242246
if (event === 'uncaughtException' &&
243247
process.domain &&
@@ -895,14 +899,8 @@ exports.start = function(prompt,
895899
useGlobal,
896900
ignoreUndefined,
897901
replMode) {
898-
const repl = new REPLServer(prompt,
899-
source,
900-
eval_,
901-
useGlobal,
902-
ignoreUndefined,
903-
replMode);
904-
if (!exports.repl) exports.repl = repl;
905-
return repl;
902+
return new REPLServer(
903+
prompt, source, eval_, useGlobal, ignoreUndefined, replMode);
906904
};
907905

908906
REPLServer.prototype.setupHistory = function setupHistory(historyFile, cb) {

test/parallel/test-repl-options.js

Lines changed: 25 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -24,6 +24,9 @@ const common = require('../common');
2424
const ArrayStream = require('../common/arraystream');
2525
const assert = require('assert');
2626
const repl = require('repl');
27+
const cp = require('child_process');
28+
29+
assert.strictEqual(repl.repl, undefined);
2730

2831
common.expectWarning({
2932
DeprecationWarning: {
@@ -120,3 +123,25 @@ assert.strictEqual(r4.ignoreUndefined, false);
120123
assert.strictEqual(r4.replMode, repl.REPL_MODE_SLOPPY);
121124
assert.strictEqual(r4.historySize, 30);
122125
r4.close();
126+
127+
// Check the standalone REPL
128+
{
129+
const child = cp.spawn(process.execPath, ['--interactive']);
130+
let output = '';
131+
132+
child.stdout.setEncoding('utf8');
133+
child.stdout.on('data', (data) => {
134+
output += data;
135+
});
136+
137+
child.on('exit', common.mustCall(() => {
138+
const results = output.replace(/^> /mg, '').split('\n').slice(2);
139+
assert.deepStrictEqual(results, ['undefined', '']);
140+
}));
141+
142+
child.stdin.write(
143+
'assert.ok(util.inspect(repl.repl, {depth: -1}).includes("REPLServer"));\n'
144+
);
145+
child.stdin.write('.exit');
146+
child.stdin.end();
147+
}

test/parallel/test-repl-reverse-search.js

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -251,8 +251,8 @@ const tests = [
251251
'\x1B[1G', '\x1B[0J',
252252
`${prompt}ab = "aaaa"`, '\x1B[14G',
253253
'\x1B[1G', '\x1B[0J',
254-
`${prompt}repl.repl.historyIndex`, '\x1B[25G', '\n// -1',
255-
'\x1B[19C\x1B[1A',
254+
`${prompt}repl.repl.historyIndex`, '\x1B[25G', '\n// 8',
255+
'\x1B[20C\x1B[1A',
256256
'\x1B[1B', '\x1B[2K', '\x1B[1A',
257257
'\nfwd-i-search: _', '\x1B[1A', '\x1B[25G',
258258
'\x1B[3G', '\x1B[0J',

0 commit comments

Comments
 (0)