From 9f71dbc33466f26f3fa9a797ace8aa1f285cb890 Mon Sep 17 00:00:00 2001 From: Ruben Bridgewater Date: Tue, 14 May 2019 02:53:22 +0200 Subject: util: include reference anchor for circular structures This adds a reference anchor to circular structures when using `util.inspect`. That way it's possible to identify with what object the circular reference corresponds too. PR-URL: https://github.com/nodejs/node/pull/27685 Reviewed-By: Anna Henningsen Reviewed-By: Benjamin Gruenbaum Reviewed-By: Rich Trott Reviewed-By: Anto Aravinth Reviewed-By: James M Snell Reviewed-By: Jeremiah Senkpiel --- lib/internal/util/inspect.js | 27 +++++++++++++++++++++++++-- 1 file changed, 25 insertions(+), 2 deletions(-) (limited to 'lib/internal/util/inspect.js') diff --git a/lib/internal/util/inspect.js b/lib/internal/util/inspect.js index e46a18633c..8735c40ac0 100644 --- a/lib/internal/util/inspect.js +++ b/lib/internal/util/inspect.js @@ -563,8 +563,19 @@ function formatValue(ctx, value, recurseTimes, typedArray) { // Using an array here is actually better for the average case than using // a Set. `seen` will only check for the depth and will never grow too large. - if (ctx.seen.includes(value)) - return ctx.stylize('[Circular]', 'special'); + if (ctx.seen.includes(value)) { + let index = 1; + if (ctx.circular === undefined) { + ctx.circular = new Map([[value, index]]); + } else { + index = ctx.circular.get(value); + if (index === undefined) { + index = ctx.circular.size + 1; + ctx.circular.set(value, index); + } + } + return ctx.stylize(`[Circular *${index}]`, 'special'); + } return formatRaw(ctx, value, recurseTimes, typedArray); } @@ -766,6 +777,18 @@ function formatRaw(ctx, value, recurseTimes, typedArray) { const constructorName = getCtxStyle(value, constructor, tag).slice(0, -1); return handleMaxCallStackSize(ctx, err, constructorName, indentationLvl); } + if (ctx.circular !== undefined) { + const index = ctx.circular.get(value); + if (index !== undefined) { + const reference = ctx.stylize(``, 'special'); + // Add reference always to the very beginning of the output. + if (ctx.compact !== true) { + base = base === '' ? reference : `${reference} ${base}`; + } else { + braces[0] = `${reference} ${braces[0]}`; + } + } + } ctx.seen.pop(); if (ctx.sorted) { -- cgit v1.2.3