Uh oh!
There was an error while loading. Please reload this page.
util: compact inspect() for sparse arrays - #5070
Conversation
Trott
commented
Feb 4, 2016
Thanks for the fix!
|
There was a problem hiding this comment.
This has to be explained in the comments. How this calculation determines if the array is sparse or not?
There was a problem hiding this comment.
@thefourtheye added a comment. If less than 1/10th of the slots in an array are populated, util.inspect / console.log now renders it compactly
var arr = []
arr[100] = 1
console.log(arr)
Before:[ , , , , , (lots of commas) , 1 ]
After:[ 100:1 ]
6c3bd3a to
d7b8af2Comparedcposch
commented
Feb 4, 2016
@Trott@thefourtheye sounds good, fixed |
65033e3 to
6821944Comparedcposch
commented
Feb 4, 2016
@Trott added test cases, LMK if these look dece vararr=[];arr[2]=1;// expect util.inspect() to return [ , , 1 ]arr[1000]=1;// expect [ 2: 1, 1000: 1, <sparse array, length 1001> ]')arr['foo']='bar';// expect [ 2: 1, 1000: 1, foo: 'bar', <sparse array, length 1001> ]arr=newArray(1000000);// expect [ <empty array, length 1000000> ] |
This prevents `console.log(arr)` from crashing node when given a sparse array with large length. Fixesnodejs#4905
6821944 to
d257683Comparethefourtheye
commented
Feb 4, 2016
I think the sparse arrays are used only to prove the point. What happens when you use a dense array? |
dcposch
commented
Feb 4, 2016
@thefourtheye no, I think it's specifically about sparse arrays, where a small object can potentially lead to a huge
...by contrast there are lots of ways to make a large JSON produce a large |
dcposch
commented
Feb 4, 2016
Say you can crash a server by sending a 10GB POST, I think the fix is just to set request length limits. If you can crash a server by sending a 1KB POST which turns into a 10GB string internally, that's a bigger problem. |
thefourtheye
commented
Feb 4, 2016
Fair enough. But I am not sure if it is acceptable to special case it in the order of 10 like this. Lets hear from @nodejs/collaborators. |
mscdex
commented
Feb 4, 2016
Perhaps have something configurable like with |
thefourtheye
commented
Feb 4, 2016
+1 to @mscdex 's idea. If users want to see more data, they can explicitly adjust the value and invoke |
mcollina
commented
Feb 4, 2016
👍 for @mscdex idea, but with a default, something like |
vkurchatkin
commented
Feb 4, 2016
-1. We shouldn't treat sparse arrays differently |
mik01aj
commented
Feb 4, 2016
@vkurchatkin how would you fix the crash issue then? |
rvagg
commented
Feb 4, 2016
Not sure how I feel about this, surprising behaviour if you accidentally ran into it and I'm not sure it's intuitive although I guess the message helps. @vkurchatkin given that sparse arrays can kill Node, and this is an even more surprising and destructive behaviour, I'm not sure there's anything else we can do than treat large arrays differently. In terms of this actually fixing said issue, it only deals with sparse arrays, not large arrays. Consider: That won't be solved here |
mik01aj
commented
Feb 4, 2016
Maybe we should treat large (and not sparse) arrays differently. E.g.: if the array has more than 1000 elements, print a |
vkurchatkin
commented
Feb 4, 2016
exactly. printing very large array to console is not useful anyway |
dcposch
commented
Feb 4, 2016
I also think adding an What I was saying above is, that will not just apply to arrays -- it'll have to limit output of strings and objects as well. Doable but a bit involved, esp since To give an example of what that would entail, I think we'd have to add a functionformatProperty(ctx,value,recurseTimes,visibleKeys,key,array){varname,str,desc;desc=Object.getOwnPropertyDescriptor(value,key)||{value: value[key]};if(desc.get){if(desc.set){str=ctx.stylize('[Getter/Setter]','special');}else{str=ctx.stylize('[Getter]','special');}}else{if(desc.set){str=ctx.stylize('[Setter]','special');}}if(!hasOwnProperty(visibleKeys,key)){if(typeofkey==='symbol'){name='['+ctx.stylize(key.toString(),'symbol')+']';}else{name='['+key+']';}}if(!str){if(ctx.seen.indexOf(desc.value)<0){if(recurseTimes===null){str=formatValue(ctx,desc.value,null);}else{str=formatValue(ctx,desc.value,recurseTimes-1);}if(str.indexOf('\n')>-1){if(array){str=str.replace(/\n/g,'\n ');}else{str=str.replace(/(^|\n)/g,'\n ');}}}else{str=ctx.stylize('[Circular]','special');}}if(name===undefined){if(array&&key.match(/^\d+$/)){returnstr;}name=JSON.stringify(''+key);if(name.match(/^"([a-zA-Z_][a-zA-Z_0-9]*)"$/)){name=name.substr(1,name.length-2);name=ctx.stylize(name,'name');}else{name=name.replace(/'/g,"\\'").replace(/\\"/g,'"').replace(/(^"|"$)/g,"'").replace(/\\\\/g,'\\');name=ctx.stylize(name,'string');}}returnname+': '+str;} |
dcposch
commented
Feb 4, 2016
This change is smaller and at least covers the small-HTTP-POST-crashing-node case. |
cjihrig
commented
Feb 4, 2016
That might not be a bad thing. The current algorithm for identifying sparse arrays seems pretty arbitrary. And, as pointed out, it doesn't do anything about large arrays. |
Trott
commented
Feb 4, 2016
This change is similar to the behavior of Chrome's console with sparse arrays. It may be useful to look and see what Blink/Chrome does to decide whether to do this special rendering or the usual expected rendering. EDIT: Specifically, how does Chrome/Blink decide that an array requires special rendering? |
jasnell
commented
Feb 4, 2016
curious if this would be a feature change or a fix? minor or patch? lts or no? |
cjihrig
commented
Feb 4, 2016
IMO it's a breaking change. |
dcposch
commented
Feb 8, 2016
@Trott just did some experimenting. In Chrome: So it looks like it prints a normal dense array for all indices starting from 0, then as soon as it gets to an index that is not set (which is not the same as an index whose corresponding value is If you want I can change this PR slightly to match that behavior. |
Trott
commented
Feb 8, 2016
@dcposch I don't have an opinion on that one way or the other, but someone else might. |
domenic
commented
Feb 8, 2016
Personally I can't understand how this is minor---what new feature does it introduce? It's either major (breaking change to existing feature) or patch (bugfix to existing feature). |
dcposch
commented
Feb 19, 2016
rvagg
commented
Feb 19, 2016
I'm finding it hard to conjure up much of an opinion on this one. @nodejs/collaborators anyone else want to champion this one through? I'd like to fix the crashes but am also concerned about how people might already be relying on |
mscdex
commented
Feb 19, 2016
As I previously mentioned, I wouldn't mind having a |
tunniclm
commented
Mar 21, 2016
EDIT: Oops, posted the comment to the wrong place. Moved to: #4905 (comment) |
rvagg
commented
Mar 22, 2016
Building on @tunniclm's suggestion that he's since moved, perhaps the easiest path forward on this one is to add an option to |
jasnell
commented
Apr 21, 2016
Looking at this again, I would find it difficult to justify leaving the current crash behavior as the default.
|
jasnell
commented
Apr 21, 2016
I've opened an alternative PR that takes a slightly different approach to this. See #6334 |
7da4fd4 to
c7066fbComparebenjamingr
commented
Apr 30, 2016
I think consensus is going towards #6334 - is this still being pursued? |
I'd recommend closing this in favor of #6334 (but I'm a bit biased lol) |
benjamingr
commented
Apr 30, 2016
I think we can close this now and it can always be reopened. It seems stalled and there seems to be consensus is with the other proposal anyway. Feel free to reopen. |
As an alternative to nodejs#5070, set the max length of Arrays/TypedArrays in util.inspect() to `100` and provide a `maxArrayLength` option to override.
As an alternative to #5070, set the max length of Arrays/TypedArrays in util.inspect() to `100` and provide a `maxArrayLength` option to override. PR-URL: #6334 Reviewed-By: Anna Henningsen <anna@addaleax.net> Reviewed-By: Matteo Collina <matteo.collina@gmail.com> Reviewed-By: Jeremiah Senkpiel <fishrock123@rocketmail.com> Reviewed-By: Roman Reiss <me@silverwind.io>
As an alternative to #5070, set the max length of Arrays/TypedArrays in util.inspect() to `100` and provide a `maxArrayLength` option to override. PR-URL: #6334 Reviewed-By: Anna Henningsen <anna@addaleax.net> Reviewed-By: Matteo Collina <matteo.collina@gmail.com> Reviewed-By: Jeremiah Senkpiel <fishrock123@rocketmail.com> Reviewed-By: Roman Reiss <me@silverwind.io>
As an alternative to nodejs#5070, set the max length of Arrays/TypedArrays in util.inspect() to `100` and provide a `maxArrayLength` option to override. PR-URL: nodejs#6334 Reviewed-By: Anna Henningsen <anna@addaleax.net> Reviewed-By: Matteo Collina <matteo.collina@gmail.com> Reviewed-By: Jeremiah Senkpiel <fishrock123@rocketmail.com> Reviewed-By: Roman Reiss <me@silverwind.io>
This prevents
console.log(arr)from crashing node when given a small sparse array with large lengthFixes#4905