Skip to content

Commit a699808

Browse files
committed
util: add (typed) array length to the default output
Align the inspect output with the one used in the Chrome dev tools. A recent survey outlined that most users prefer to see the number of set and map entries. This should count as well for array sizes. The size is only added to regular arrays in case the constructor is not the default constructor. Typed arrays always indicate their size. PR-URL: #31027 Reviewed-By: Michaël Zasso <[email protected]> Reviewed-By: Rich Trott <[email protected]> Reviewed-By: Anto Aravinth <[email protected]>
1 parent ffbf790 commit a699808

6 files changed

+71
-75
lines changed

lib/internal/util/inspect.js

+27-34
Original file line numberDiff line numberDiff line change
@@ -117,6 +117,9 @@ const setSizeGetter = uncurryThis(
117117
ObjectGetOwnPropertyDescriptor(SetPrototype, 'size').get);
118118
const mapSizeGetter = uncurryThis(
119119
ObjectGetOwnPropertyDescriptor(MapPrototype, 'size').get);
120+
const typedArraySizeGetter = uncurryThis(
121+
ObjectGetOwnPropertyDescriptor(
122+
ObjectGetPrototypeOf(Uint8Array.prototype), 'length').get);
120123

121124
let hexSlice;
122125

@@ -562,18 +565,18 @@ function addPrototypeProperties(ctx, main, obj, recurseTimes, isProto, output) {
562565
} while (++depth !== 3);
563566
}
564567

565-
function getPrefix(constructor, tag, fallback) {
568+
function getPrefix(constructor, tag, fallback, size = '') {
566569
if (constructor === null) {
567570
if (tag !== '') {
568-
return `[${fallback}: null prototype] [${tag}] `;
571+
return `[${fallback}${size}: null prototype] [${tag}] `;
569572
}
570-
return `[${fallback}: null prototype] `;
573+
return `[${fallback}${size}: null prototype] `;
571574
}
572575

573576
if (tag !== '' && constructor !== tag) {
574-
return `${constructor} [${tag}] `;
577+
return `${constructor}${size} [${tag}] `;
575578
}
576-
return `${constructor} `;
579+
return `${constructor}${size} `;
577580
}
578581

579582
// Look up the keys of the object.
@@ -758,58 +761,48 @@ function formatRaw(ctx, value, recurseTimes, typedArray) {
758761
if (value[SymbolIterator] || constructor === null) {
759762
noIterator = false;
760763
if (ArrayIsArray(value)) {
761-
keys = getOwnNonIndexProperties(value, filter);
762764
// Only set the constructor for non ordinary ("Array [...]") arrays.
763-
const prefix = getPrefix(constructor, tag, 'Array');
764-
braces = [`${prefix === 'Array ' ? '' : prefix}[`, ']'];
765+
const prefix = (constructor !== 'Array' || tag !== '') ?
766+
getPrefix(constructor, tag, 'Array', `(${value.length})`) :
767+
'';
768+
keys = getOwnNonIndexProperties(value, filter);
769+
braces = [`${prefix}[`, ']'];
765770
if (value.length === 0 && keys.length === 0 && protoProps === undefined)
766771
return `${braces[0]}]`;
767772
extrasType = kArrayExtrasType;
768773
formatter = formatArray;
769774
} else if (isSet(value)) {
770775
const size = setSizeGetter(value);
776+
const prefix = getPrefix(constructor, tag, 'Set', `(${size})`);
771777
keys = getKeys(value, ctx.showHidden);
772-
let prefix = '';
773-
if (constructor !== null) {
774-
if (constructor === tag)
775-
tag = '';
776-
prefix = getPrefix(`${constructor}(${size})`, tag, '');
777-
formatter = formatSet.bind(null, value, size);
778-
} else {
779-
prefix = getPrefix(constructor, tag, `Set(${size})`);
780-
formatter = formatSet.bind(null, SetPrototypeValues(value), size);
781-
}
778+
formatter = constructor !== null ?
779+
formatSet.bind(null, value) :
780+
formatSet.bind(null, SetPrototypeValues(value));
782781
if (size === 0 && keys.length === 0 && protoProps === undefined)
783782
return `${prefix}{}`;
784783
braces = [`${prefix}{`, '}'];
785784
} else if (isMap(value)) {
786785
const size = mapSizeGetter(value);
786+
const prefix = getPrefix(constructor, tag, 'Map', `(${size})`);
787787
keys = getKeys(value, ctx.showHidden);
788-
let prefix = '';
789-
if (constructor !== null) {
790-
if (constructor === tag)
791-
tag = '';
792-
prefix = getPrefix(`${constructor}(${size})`, tag, '');
793-
formatter = formatMap.bind(null, value, size);
794-
} else {
795-
prefix = getPrefix(constructor, tag, `Map(${size})`);
796-
formatter = formatMap.bind(null, MapPrototypeEntries(value), size);
797-
}
788+
formatter = constructor !== null ?
789+
formatMap.bind(null, value) :
790+
formatMap.bind(null, MapPrototypeEntries(value));
798791
if (size === 0 && keys.length === 0 && protoProps === undefined)
799792
return `${prefix}{}`;
800793
braces = [`${prefix}{`, '}'];
801794
} else if (isTypedArray(value)) {
802795
keys = getOwnNonIndexProperties(value, filter);
803796
let bound = value;
804-
let prefix = '';
797+
let fallback = '';
805798
if (constructor === null) {
806799
const constr = findTypedConstructor(value);
807-
prefix = getPrefix(constructor, tag, constr.name);
800+
fallback = constr.name;
808801
// Reconstruct the array information.
809802
bound = new constr(value);
810-
} else {
811-
prefix = getPrefix(constructor, tag);
812803
}
804+
const size = typedArraySizeGetter(value);
805+
const prefix = getPrefix(constructor, tag, fallback, `(${size})`);
813806
braces = [`${prefix}[`, ']'];
814807
if (value.length === 0 && keys.length === 0 && !ctx.showHidden)
815808
return `${braces[0]}]`;
@@ -1425,7 +1418,7 @@ function formatTypedArray(value, ctx, ignored, recurseTimes) {
14251418
return output;
14261419
}
14271420

1428-
function formatSet(value, size, ctx, ignored, recurseTimes) {
1421+
function formatSet(value, ctx, ignored, recurseTimes) {
14291422
const output = [];
14301423
ctx.indentationLvl += 2;
14311424
for (const v of value) {
@@ -1435,7 +1428,7 @@ function formatSet(value, size, ctx, ignored, recurseTimes) {
14351428
return output;
14361429
}
14371430

1438-
function formatMap(value, size, ctx, ignored, recurseTimes) {
1431+
function formatMap(value, ctx, ignored, recurseTimes) {
14391432
const output = [];
14401433
ctx.indentationLvl += 2;
14411434
for (const [k, v] of value) {

test/parallel/test-assert-deep.js

+4-4
Original file line numberDiff line numberDiff line change
@@ -51,8 +51,8 @@ assert.throws(
5151
{
5252
code: 'ERR_ASSERTION',
5353
message: `${defaultMsgStartFull} ... Lines skipped\n\n` +
54-
'+ Uint8Array [\n' +
55-
'- Buffer [Uint8Array] [\n 120,\n...\n 122,\n 10\n ]'
54+
'+ Uint8Array(4) [\n' +
55+
'- Buffer(4) [Uint8Array] [\n 120,\n...\n 122,\n 10\n ]'
5656
}
5757
);
5858
assert.deepEqual(arr, buf);
@@ -66,7 +66,7 @@ assert.deepEqual(arr, buf);
6666
{
6767
code: 'ERR_ASSERTION',
6868
message: `${defaultMsgStartFull}\n\n` +
69-
' Buffer [Uint8Array] [\n' +
69+
' Buffer(4) [Uint8Array] [\n' +
7070
' 120,\n' +
7171
' 121,\n' +
7272
' 122,\n' +
@@ -86,7 +86,7 @@ assert.deepEqual(arr, buf);
8686
{
8787
code: 'ERR_ASSERTION',
8888
message: `${defaultMsgStartFull}\n\n` +
89-
' Uint8Array [\n' +
89+
' Uint8Array(4) [\n' +
9090
' 120,\n' +
9191
' 121,\n' +
9292
' 122,\n' +

test/parallel/test-buffer-inspect.js

+1-1
Original file line numberDiff line numberDiff line change
@@ -58,7 +58,7 @@ b.inspect = undefined;
5858
b.prop = new Uint8Array(0);
5959
assert.strictEqual(
6060
util.inspect(b),
61-
'<Buffer 31 32, inspect: undefined, prop: Uint8Array []>'
61+
'<Buffer 31 32, inspect: undefined, prop: Uint8Array(0) []>'
6262
);
6363

6464
b = Buffer.alloc(0);

test/parallel/test-fs-read-empty-buffer.js

+3-3
Original file line numberDiff line numberDiff line change
@@ -15,7 +15,7 @@ assert.throws(
1515
{
1616
code: 'ERR_INVALID_ARG_VALUE',
1717
message: 'The argument \'buffer\' is empty and cannot be written. ' +
18-
'Received Uint8Array []'
18+
'Received Uint8Array(0) []'
1919
}
2020
);
2121

@@ -24,7 +24,7 @@ assert.throws(
2424
{
2525
code: 'ERR_INVALID_ARG_VALUE',
2626
message: 'The argument \'buffer\' is empty and cannot be written. ' +
27-
'Received Uint8Array []'
27+
'Received Uint8Array(0) []'
2828
}
2929
);
3030

@@ -35,7 +35,7 @@ assert.throws(
3535
{
3636
code: 'ERR_INVALID_ARG_VALUE',
3737
message: 'The argument \'buffer\' is empty and cannot be written. ' +
38-
'Received Uint8Array []'
38+
'Received Uint8Array(0) []'
3939
}
4040
);
4141
})();

test/parallel/test-util-format.js

+1-1
Original file line numberDiff line numberDiff line change
@@ -158,7 +158,7 @@ assert.strictEqual(util.format('%s', () => 5), '() => 5');
158158
class Foobar extends Array { aaa = true; }
159159
assert.strictEqual(
160160
util.format('%s', new Foobar(5)),
161-
'Foobar [ <5 empty items>, aaa: true ]'
161+
'Foobar(5) [ <5 empty items>, aaa: true ]'
162162
);
163163

164164
// Subclassing:

0 commit comments

Comments
 (0)