[jsscripting] Refactor log formatting & Respect toString polyfills (#13844)
* [jsscripting] Refactor log formatting & Respect toString polyfills * [jsscripting] Catch errors in log formatting & Improve handling of Java obj * [jsscripting] Update log format failure message Signed-off-by: Florian Hotze <florianh_dev@icloud.com>
This commit is contained in:
parent
d0b1458e89
commit
bf48eccf8c
@ -19,66 +19,63 @@
|
||||
|
||||
function stringify (value) {
|
||||
try {
|
||||
if (Java.isJavaObject(value) || value instanceof Error) {
|
||||
return value.toString();
|
||||
} else {
|
||||
// special cases
|
||||
if (value === undefined) {
|
||||
return 'undefined';
|
||||
}
|
||||
if (typeof value === 'function') {
|
||||
return '[Function]';
|
||||
}
|
||||
if (value instanceof RegExp) {
|
||||
return value.toString();
|
||||
}
|
||||
// fallback to JSON
|
||||
if (typeof value === 'string') return value;
|
||||
// special cases
|
||||
if (value === undefined) {
|
||||
return 'undefined';
|
||||
}
|
||||
if (value === null) {
|
||||
return 'null';
|
||||
}
|
||||
// JSON.stringify all objects that do not polyfill toString()
|
||||
const str = value.toString();
|
||||
if (typeof value === 'object' && (str === '[object Object]') || str === '[object Java]') {
|
||||
return JSON.stringify(value, null, 2);
|
||||
}
|
||||
return str;
|
||||
} catch (e) {
|
||||
return '[Circular: ' + e + ']';
|
||||
return 'Error: failed to format log message: ' + e;
|
||||
}
|
||||
}
|
||||
|
||||
function format (f) {
|
||||
if (typeof f !== 'string') {
|
||||
const objects = [];
|
||||
for (let index = 0; index < arguments.length; index++) {
|
||||
objects.push(stringify(arguments[index]));
|
||||
}
|
||||
return objects.join(' ');
|
||||
}
|
||||
try {
|
||||
const args = arguments;
|
||||
|
||||
if (arguments.length === 1) return f;
|
||||
// If there is only one argument, stringify and return it
|
||||
if (args.length === 1) return stringify(f);
|
||||
|
||||
let i = 1;
|
||||
const args = arguments;
|
||||
const len = args.length;
|
||||
let str = String(f).replace(formatRegExp, function (x) {
|
||||
if (x === '%%') return '%';
|
||||
if (i >= len) return x;
|
||||
switch (x) {
|
||||
case '%s': return String(args[i++]);
|
||||
case '%d': return Number(args[i++]);
|
||||
case '%j':
|
||||
try {
|
||||
return stringify(args[i++]);
|
||||
} catch (_) {
|
||||
return '[Circular]';
|
||||
// Else if the first arg is string, do regex string formatting
|
||||
// the number of args after the formatted string must match the number of % placeholder
|
||||
let str;
|
||||
let i = 1;
|
||||
if (typeof f === 'string') {
|
||||
str = String(f).replace(formatRegExp, function (x) {
|
||||
if (x === '%%') return '%';
|
||||
if (i >= args.length) return x;
|
||||
switch (x) {
|
||||
case '%s': return String(args[i++]);
|
||||
case '%d': return Number(args[i++]);
|
||||
case '%j':
|
||||
try {
|
||||
return stringify(args[i++]);
|
||||
} catch (e) {
|
||||
return '[Circular]';
|
||||
}
|
||||
// falls through
|
||||
default:
|
||||
return x;
|
||||
}
|
||||
// falls through
|
||||
default:
|
||||
return x;
|
||||
});
|
||||
}
|
||||
});
|
||||
for (let x = args[i]; i < len; x = args[++i]) {
|
||||
if (x === null || (typeof x !== 'object' && typeof x !== 'symbol')) {
|
||||
str += ' ' + x;
|
||||
} else {
|
||||
// Else stringify and join all args
|
||||
for (let x = args[i]; i < args.length; x = args[++i]) {
|
||||
str += ' ' + stringify(x);
|
||||
}
|
||||
return str;
|
||||
} catch (e) {
|
||||
return 'Error: failed to format log message: ' + e;
|
||||
}
|
||||
return str;
|
||||
}
|
||||
|
||||
const counters = {};
|
||||
|
||||
Loading…
x
Reference in New Issue
Block a user