Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
27 changes: 27 additions & 0 deletions lib/internal/console/constructor.js
Original file line number Diff line number Diff line change
Expand Up @@ -28,6 +28,7 @@ const {
SafeArrayIterator,
SafeMap,
SafeWeakMap,
SafeSet,
StringPrototypeIncludes,
StringPrototypePadStart,
StringPrototypeRepeat,
Expand Down Expand Up @@ -687,6 +688,32 @@ Console.prototype.groupCollapsed = Console.prototype.group;
function initializeGlobalConsole(globalConsole) {
globalConsole[kBindStreamsLazy](process);
globalConsole[kBindProperties](true, 'auto');

const {
addSerializeCallback,
isBuildingSnapshot,
} = require('v8').startupSnapshot;

if (!internalBinding('config').hasInspector || !isBuildingSnapshot()) {
return;
}
const { console: consoleFromVM } = internalBinding('inspector');
const nodeConsoleKeys = ObjectKeys(Console.prototype);
const vmConsoleKeys = ObjectKeys(consoleFromVM);
const originalKeys = new SafeSet(vmConsoleKeys.concat(nodeConsoleKeys));
const inspectorConsoleKeys = new SafeSet();
for (const key of ObjectKeys(globalConsole)) {
if (!originalKeys.has(key)) {
inspectorConsoleKeys.add(key);
}
}
// During deserialization these should be reinstalled to console by
// V8 when the inspector client is created.
addSerializeCallback(() => {
for (const key of inspectorConsoleKeys) {
globalConsole[key] = undefined;
}
});
}

module.exports = {
Expand Down
9 changes: 9 additions & 0 deletions test/fixtures/snapshot/console.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,9 @@
const {
setDeserializeMainFunction,
} = require('v8').startupSnapshot;

console.log(JSON.stringify(Object.keys(console), null, 2));

setDeserializeMainFunction(() => {
console.log(JSON.stringify(Object.keys(console), null, 2));
});
62 changes: 62 additions & 0 deletions test/parallel/test-snapshot-console.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,62 @@
'use strict';

// TODO(joyeecheung): remove the flag when it is turned on by default in V8.
// Flags: --experimental-async-stack-tagging-api
// This tests the console works in the deserialized snapshot.

const common = require('../common');
common.skipIfInspectorDisabled();

const assert = require('assert');
const { spawnSync } = require('child_process');
const tmpdir = require('../common/tmpdir');
const fixtures = require('../common/fixtures');
const path = require('path');
const fs = require('fs');

tmpdir.refresh();
const blobPath = path.join(tmpdir.path, 'snapshot.blob');
const entry = fixtures.path('snapshot', 'console.js');

{
const child = spawnSync(process.execPath, [
'--experimental-async-stack-tagging-api',
'--snapshot-blob',
blobPath,
'--build-snapshot',
entry,
], {
cwd: tmpdir.path
});
const stdout = child.stdout.toString();
if (child.status !== 0) {
console.log(stdout);
console.log(child.stderr.toString());
assert.strictEqual(child.status, 0);
}
assert.deepStrictEqual(Object.keys(console), JSON.parse(stdout));
const stats = fs.statSync(path.join(tmpdir.path, 'snapshot.blob'));
assert(stats.isFile());
}

{
const child = spawnSync(process.execPath, [
'--experimental-async-stack-tagging-api',
'--snapshot-blob',
blobPath,
], {
cwd: tmpdir.path,
env: {
...process.env,
}
});

const stdout = child.stdout.toString();
if (child.status !== 0) {
console.log(stdout);
console.log(child.stderr.toString());
assert.strictEqual(child.status, 0);
}
assert.deepStrictEqual(Object.keys(console), JSON.parse(stdout));
assert.strictEqual(child.status, 0);
}