tj / node-querystring

querystring parser for node and the browser - supporting nesting (used by Express, Connect, etc)
MIT License
455 stars 66 forks source link

Exception when qs.parse('a[b]=1&a[b][c][d]=2') #100

Open mctep opened 10 years ago

mctep commented 10 years ago

Hello, I'm using express. And when I am trying to get some url like ?a[b]=1&a[b][c][d]=2, it sends 500 with error stack:

TypeError: Object #<ServerResponse> has no method 'status'
  at Object.handle (app/routes/index.js:11:7)
  at next (app/node_modules/express/node_modules/connect/lib/proto.js:188:17)
  at next (app/node_modules/express/node_modules/connect/lib/proto.js:190:11)
  at next (app/node_modules/express/node_modules/connect/lib/proto.js:190:11)
  at next (app/node_modules/express/node_modules/connect/lib/proto.js:190:11)
  at next (app/node_modules/express/node_modules/connect/lib/proto.js:190:11)
  at next (app/node_modules/express/node_modules/connect/lib/proto.js:190:11)
  at next (app/node_modules/express/node_modules/connect/lib/proto.js:190:11)
  at next (app/node_modules/express/node_modules/connect/lib/proto.js:198:7)
  at Function.app.handle (app/node_modules/express/node_modules/connect/lib/proto.js:201:3)
  at Server.app (app/express/node_modules/connect/lib/connect.js:65:37)
  at Server.EventEmitter.emit (events.js:98:17)
  at HTTPParser.parser.onIncoming (http.js:2108:12)
  at HTTPParser.parserOnHeadersComplete [as onHeadersComplete] (http.js:121:23)
  at Socket.socket.ondata (http.js:1966:22)
  at TCP.onread (net.js:525:27)

I tried to get more information about this problem. And I found out that it is problem with qs.

And it is a very strange problem. Look at the code https://github.com/visionmedia/node-querystring/blob/master/index.js#L207

function parseString(str){
  var ret = reduce(String(str).split('&'), function(ret, pair){
    // ... some other code
    return merge(ret, decode(key), decode(val));
  }, { base: {} }).base;

  return compact(ret);
}

When I try to execute:

require('qs').parse('a[b]=1&a[b][c][d]=2');

it throws exception:

test/node_modules/qs/index.js:76
  if (parent[key].length == 0) return parent[key] = {}
                 ^
TypeError: Cannot read property 'length' of undefined
    at promote (test/node_modules/qs/index.js:76:18)
    at parse (test/node_modules/qs/index.js:118:52)
    at parse (test/node_modules/qs/index.js:119:7)
    at parse (test/node_modules/qs/index.js:119:7)
    at parse (test/node_modules/qs/index.js:123:7)
    at merge (test/node_modules/qs/index.js:137:5)
    at reduce.base (test/node_modules/qs/index.js:207:13)
    at Array.reduce (native)
    at reduce (test/node_modules/qs/index.js:63:52)
    at parseString (test/node_modules/qs/index.js:196:13)

But if I change code to qs like this:

function parseString(str){
  var ret = reduce(String(str).split('&'), function(ret, pair){
    // ... some other code
    console.log(merge(ret, decode(key), decode(val)));
    return merge(ret, decode(key), decode(val));
  }, { base: {} }).base;

  return compact(ret);
}

It works without exceptions and returns some parsed object.

Express does not catch this exception and does not initialize the response object correctly in my case, does it? May be it's a second problem.