decode.js
1 // Copyright Joyent, Inc. and other Node contributors. 2 // 3 // Permission is hereby granted, free of charge, to any person obtaining a 4 // copy of this software and associated documentation files (the 5 // "Software"), to deal in the Software without restriction, including 6 // without limitation the rights to use, copy, modify, merge, publish, 7 // distribute, sublicense, and/or sell copies of the Software, and to permit 8 // persons to whom the Software is furnished to do so, subject to the 9 // following conditions: 10 // 11 // The above copyright notice and this permission notice shall be included 12 // in all copies or substantial portions of the Software. 13 // 14 // THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS 15 // OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF 16 // MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN 17 // NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, 18 // DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR 19 // OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE 20 // USE OR OTHER DEALINGS IN THE SOFTWARE. 21 22 'use strict'; 23 24 // If obj.hasOwnProperty has been overridden, then calling 25 // obj.hasOwnProperty(prop) will break. 26 // See: https://github.com/joyent/node/issues/1707 27 function hasOwnProperty(obj, prop) { 28 return Object.prototype.hasOwnProperty.call(obj, prop); 29 } 30 31 module.exports = function(qs, sep, eq, options) { 32 sep = sep || '&'; 33 eq = eq || '='; 34 var obj = {}; 35 36 if (typeof qs !== 'string' || qs.length === 0) { 37 return obj; 38 } 39 40 var regexp = /\+/g; 41 qs = qs.split(sep); 42 43 var maxKeys = 1000; 44 if (options && typeof options.maxKeys === 'number') { 45 maxKeys = options.maxKeys; 46 } 47 48 var len = qs.length; 49 // maxKeys <= 0 means that we should not limit keys count 50 if (maxKeys > 0 && len > maxKeys) { 51 len = maxKeys; 52 } 53 54 for (var i = 0; i < len; ++i) { 55 var x = qs[i].replace(regexp, '%20'), 56 idx = x.indexOf(eq), 57 kstr, vstr, k, v; 58 59 if (idx >= 0) { 60 kstr = x.substr(0, idx); 61 vstr = x.substr(idx + 1); 62 } else { 63 kstr = x; 64 vstr = ''; 65 } 66 67 k = decodeURIComponent(kstr); 68 v = decodeURIComponent(vstr); 69 70 if (!hasOwnProperty(obj, k)) { 71 obj[k] = v; 72 } else if (Array.isArray(obj[k])) { 73 obj[k].push(v); 74 } else { 75 obj[k] = [obj[k], v]; 76 } 77 } 78 79 return obj; 80 };