Make console work with JS engines which use print

Reviewed By: javache

Differential Revision: D5586381

fbshipit-source-id: e40dea048129bef6755817297a7d9eb701f71d41
This commit is contained in:
Riley Dulin 2017-08-09 17:58:38 -07:00 committed by Facebook Github Bot
parent 046f600cc2
commit de4e51beaf
1 changed files with 103 additions and 69 deletions

View File

@ -9,6 +9,7 @@
* @providesModule console * @providesModule console
* @polyfill * @polyfill
* @nolint * @nolint
* @format
*/ */
/* eslint-disable */ /* eslint-disable */
@ -44,7 +45,7 @@ const inspect = (function() {
function inspect(obj, opts) { function inspect(obj, opts) {
var ctx = { var ctx = {
seen: [], seen: [],
stylize: stylizeNoColor stylize: stylizeNoColor,
}; };
return formatValue(ctx, obj, opts.depth); return formatValue(ctx, obj, opts.depth);
} }
@ -63,7 +64,6 @@ const inspect = (function() {
return hash; return hash;
} }
function formatValue(ctx, value, recurseTimes) { function formatValue(ctx, value, recurseTimes) {
// Primitive types cannot have properties // Primitive types cannot have properties
var primitive = formatPrimitive(ctx, value); var primitive = formatPrimitive(ctx, value);
@ -77,8 +77,10 @@ const inspect = (function() {
// IE doesn't make error fields non-enumerable // IE doesn't make error fields non-enumerable
// http://msdn.microsoft.com/en-us/library/ie/dww52sbt(v=vs.94).aspx // http://msdn.microsoft.com/en-us/library/ie/dww52sbt(v=vs.94).aspx
if (isError(value) if (
&& (keys.indexOf('message') >= 0 || keys.indexOf('description') >= 0)) { isError(value) &&
(keys.indexOf('message') >= 0 || keys.indexOf('description') >= 0)
) {
return formatError(value); return formatError(value);
} }
@ -99,7 +101,9 @@ const inspect = (function() {
} }
} }
var base = '', array = false, braces = ['{', '}']; var base = '',
array = false,
braces = ['{', '}'];
// Make Array say that they are Array // Make Array say that they are Array
if (isArray(value)) { if (isArray(value)) {
@ -147,7 +151,14 @@ const inspect = (function() {
output = formatArray(ctx, value, recurseTimes, visibleKeys, keys); output = formatArray(ctx, value, recurseTimes, visibleKeys, keys);
} else { } else {
output = keys.map(function(key) { output = keys.map(function(key) {
return formatProperty(ctx, value, recurseTimes, visibleKeys, key, array); return formatProperty(
ctx,
value,
recurseTimes,
visibleKeys,
key,
array,
);
}); });
} }
@ -156,51 +167,56 @@ const inspect = (function() {
return reduceToSingleString(output, base, braces); return reduceToSingleString(output, base, braces);
} }
function formatPrimitive(ctx, value) { function formatPrimitive(ctx, value) {
if (isUndefined(value)) if (isUndefined(value)) return ctx.stylize('undefined', 'undefined');
return ctx.stylize('undefined', 'undefined');
if (isString(value)) { if (isString(value)) {
var simple = '\'' + JSON.stringify(value).replace(/^"|"$/g, '') var simple =
"'" +
JSON.stringify(value)
.replace(/^"|"$/g, '')
.replace(/'/g, "\\'") .replace(/'/g, "\\'")
.replace(/\\"/g, '"') + '\''; .replace(/\\"/g, '"') +
"'";
return ctx.stylize(simple, 'string'); return ctx.stylize(simple, 'string');
} }
if (isNumber(value)) if (isNumber(value)) return ctx.stylize('' + value, 'number');
return ctx.stylize('' + value, 'number'); if (isBoolean(value)) return ctx.stylize('' + value, 'boolean');
if (isBoolean(value))
return ctx.stylize('' + value, 'boolean');
// For some reason typeof null is "object", so special case here. // For some reason typeof null is "object", so special case here.
if (isNull(value)) if (isNull(value)) return ctx.stylize('null', 'null');
return ctx.stylize('null', 'null');
} }
function formatError(value) { function formatError(value) {
return '[' + Error.prototype.toString.call(value) + ']'; return '[' + Error.prototype.toString.call(value) + ']';
} }
function formatArray(ctx, value, recurseTimes, visibleKeys, keys) { function formatArray(ctx, value, recurseTimes, visibleKeys, keys) {
var output = []; var output = [];
for (var i = 0, l = value.length; i < l; ++i) { for (var i = 0, l = value.length; i < l; ++i) {
if (hasOwnProperty(value, String(i))) { if (hasOwnProperty(value, String(i))) {
output.push(formatProperty(ctx, value, recurseTimes, visibleKeys, output.push(
String(i), true)); formatProperty(
ctx,
value,
recurseTimes,
visibleKeys,
String(i),
true,
),
);
} else { } else {
output.push(''); output.push('');
} }
} }
keys.forEach(function(key) { keys.forEach(function(key) {
if (!key.match(/^\d+$/)) { if (!key.match(/^\d+$/)) {
output.push(formatProperty(ctx, value, recurseTimes, visibleKeys, output.push(
key, true)); formatProperty(ctx, value, recurseTimes, visibleKeys, key, true),
);
} }
}); });
return output; return output;
} }
function formatProperty(ctx, value, recurseTimes, visibleKeys, key, array) { function formatProperty(ctx, value, recurseTimes, visibleKeys, key, array) {
var name, str, desc; var name, str, desc;
desc = Object.getOwnPropertyDescriptor(value, key) || {value: value[key]}; desc = Object.getOwnPropertyDescriptor(value, key) || {value: value[key]};
@ -227,13 +243,22 @@ const inspect = (function() {
} }
if (str.indexOf('\n') > -1) { if (str.indexOf('\n') > -1) {
if (array) { if (array) {
str = str.split('\n').map(function(line) { str = str
.split('\n')
.map(function(line) {
return ' ' + line; return ' ' + line;
}).join('\n').substr(2); })
.join('\n')
.substr(2);
} else { } else {
str = '\n' + str.split('\n').map(function(line) { str =
'\n' +
str
.split('\n')
.map(function(line) {
return ' ' + line; return ' ' + line;
}).join('\n'); })
.join('\n');
} }
} }
} else { } else {
@ -249,7 +274,8 @@ const inspect = (function() {
name = name.substr(1, name.length - 2); name = name.substr(1, name.length - 2);
name = ctx.stylize(name, 'name'); name = ctx.stylize(name, 'name');
} else { } else {
name = name.replace(/'/g, "\\'") name = name
.replace(/'/g, "\\'")
.replace(/\\"/g, '"') .replace(/\\"/g, '"')
.replace(/(^"|"$)/g, "'"); .replace(/(^"|"$)/g, "'");
name = ctx.stylize(name, 'string'); name = ctx.stylize(name, 'string');
@ -259,7 +285,6 @@ const inspect = (function() {
return name + ': ' + str; return name + ': ' + str;
} }
function reduceToSingleString(output, base, braces) { function reduceToSingleString(output, base, braces) {
var numLinesEst = 0; var numLinesEst = 0;
var length = output.reduce(function(prev, cur) { var length = output.reduce(function(prev, cur) {
@ -269,18 +294,19 @@ const inspect = (function() {
}, 0); }, 0);
if (length > 60) { if (length > 60) {
return braces[0] + return (
braces[0] +
(base === '' ? '' : base + '\n ') + (base === '' ? '' : base + '\n ') +
' ' + ' ' +
output.join(',\n ') + output.join(',\n ') +
' ' + ' ' +
braces[1]; braces[1]
);
} }
return braces[0] + base + ' ' + output.join(', ') + ' ' + braces[1]; return braces[0] + base + ' ' + output.join(', ') + ' ' + braces[1];
} }
// NOTE: These type checking functions intentionally don't use `instanceof` // NOTE: These type checking functions intentionally don't use `instanceof`
// because it is fragile and can be easily faked with `Object.create()`. // because it is fragile and can be easily faked with `Object.create()`.
function isArray(ar) { function isArray(ar) {
@ -328,8 +354,10 @@ const inspect = (function() {
} }
function isError(e) { function isError(e) {
return isObject(e) && return (
(objectToString(e) === '[object Error]' || e instanceof Error); isObject(e) &&
(objectToString(e) === '[object Error]' || e instanceof Error)
);
} }
function isFunction(arg) { function isFunction(arg) {
@ -337,12 +365,14 @@ const inspect = (function() {
} }
function isPrimitive(arg) { function isPrimitive(arg) {
return arg === null || return (
arg === null ||
typeof arg === 'boolean' || typeof arg === 'boolean' ||
typeof arg === 'number' || typeof arg === 'number' ||
typeof arg === 'string' || typeof arg === 'string' ||
typeof arg === 'symbol' || // ES6 symbol typeof arg === 'symbol' || // ES6 symbol
typeof arg === 'undefined'; typeof arg === 'undefined'
);
} }
function objectToString(o) { function objectToString(o) {
@ -356,13 +386,12 @@ const inspect = (function() {
return inspect; return inspect;
})(); })();
const OBJECT_COLUMN_NAME = '(index)'; const OBJECT_COLUMN_NAME = '(index)';
const LOG_LEVELS = { const LOG_LEVELS = {
trace: 0, trace: 0,
info: 1, info: 1,
warn: 2, warn: 2,
error: 3 error: 3,
}; };
const INSPECTOR_LEVELS = []; const INSPECTOR_LEVELS = [];
INSPECTOR_LEVELS[LOG_LEVELS.trace] = 'debug'; INSPECTOR_LEVELS[LOG_LEVELS.trace] = 'debug';
@ -381,9 +410,11 @@ if (global.nativeLoggingHook) {
if (arguments.length === 1 && typeof arguments[0] === 'string') { if (arguments.length === 1 && typeof arguments[0] === 'string') {
str = arguments[0]; str = arguments[0];
} else { } else {
str = Array.prototype.map.call(arguments, function(arg) { str = Array.prototype.map
.call(arguments, function(arg) {
return inspect(arg, {depth: 10}); return inspect(arg, {depth: 10});
}).join(', '); })
.join(', ');
} }
let logLevel = level; let logLevel = level;
@ -398,15 +429,18 @@ if (global.nativeLoggingHook) {
INSPECTOR_LEVELS[logLevel], INSPECTOR_LEVELS[logLevel],
str, str,
[].slice.call(arguments), [].slice.call(arguments),
INSPECTOR_FRAMES_TO_SKIP); INSPECTOR_FRAMES_TO_SKIP,
);
} }
global.nativeLoggingHook(str, logLevel); global.nativeLoggingHook(str, logLevel);
}; };
} }
function repeat(element, n) { function repeat(element, n) {
return Array.apply(null, Array(n)).map(function() { return element; }); return Array.apply(null, Array(n)).map(function() {
}; return element;
});
}
function consoleTablePolyfill(rows) { function consoleTablePolyfill(rows) {
// convert object -> array // convert object -> array
@ -451,7 +485,7 @@ if (global.nativeLoggingHook) {
}); });
space = space || ' '; space = space || ' ';
return cells.join(space + '|' + space); return cells.join(space + '|' + space);
}; }
var separators = columnWidths.map(function(columnWidth) { var separators = columnWidths.map(function(columnWidth) {
return repeat('-', columnWidth).join(''); return repeat('-', columnWidth).join('');
@ -479,7 +513,7 @@ if (global.nativeLoggingHook) {
warn: getNativeLogFunction(LOG_LEVELS.warn), warn: getNativeLogFunction(LOG_LEVELS.warn),
trace: getNativeLogFunction(LOG_LEVELS.trace), trace: getNativeLogFunction(LOG_LEVELS.trace),
debug: getNativeLogFunction(LOG_LEVELS.trace), debug: getNativeLogFunction(LOG_LEVELS.trace),
table: consoleTablePolyfill table: consoleTablePolyfill,
}; };
// If available, also call the original `console` method since that is // If available, also call the original `console` method since that is
@ -503,14 +537,14 @@ if (global.nativeLoggingHook) {
}); });
} }
} else if (!global.console) { } else if (!global.console) {
function consoleLoggingStub() {}; const log = global.print || function consoleLoggingStub() {};
global.console = { global.console = {
error: consoleLoggingStub, error: log,
info: consoleLoggingStub, info: log,
log: consoleLoggingStub, log: log,
warn: consoleLoggingStub, warn: log,
trace: consoleLoggingStub, trace: log,
debug: consoleLoggingStub, debug: log,
table: consoleLoggingStub table: log,
}; };
} }