index.js 1.8 KB

12345678910111213141516171819202122232425262728293031323334353637383940414243444546474849505152535455565758596061626364656667686970717273747576777879808182838485868788
  1. 'use strict';
  2. var has = Object.prototype.hasOwnProperty
  3. , undef;
  4. /**
  5. * Decode a URI encoded string.
  6. *
  7. * @param {String} input The URI encoded string.
  8. * @returns {String} The decoded string.
  9. * @api private
  10. */
  11. function decode(input) {
  12. return decodeURIComponent(input.replace(/\+/g, ' '));
  13. }
  14. /**
  15. * Simple query string parser.
  16. *
  17. * @param {String} query The query string that needs to be parsed.
  18. * @returns {Object}
  19. * @api public
  20. */
  21. function querystring(query) {
  22. var parser = /([^=?&]+)=?([^&]*)/g
  23. , result = {}
  24. , part;
  25. while (part = parser.exec(query)) {
  26. var key = decode(part[1])
  27. , value = decode(part[2]);
  28. //
  29. // Prevent overriding of existing properties. This ensures that build-in
  30. // methods like `toString` or __proto__ are not overriden by malicious
  31. // querystrings.
  32. //
  33. if (key in result) continue;
  34. result[key] = value;
  35. }
  36. return result;
  37. }
  38. /**
  39. * Transform a query string to an object.
  40. *
  41. * @param {Object} obj Object that should be transformed.
  42. * @param {String} prefix Optional prefix.
  43. * @returns {String}
  44. * @api public
  45. */
  46. function querystringify(obj, prefix) {
  47. prefix = prefix || '';
  48. var pairs = []
  49. , value
  50. , key;
  51. //
  52. // Optionally prefix with a '?' if needed
  53. //
  54. if ('string' !== typeof prefix) prefix = '?';
  55. for (key in obj) {
  56. if (has.call(obj, key)) {
  57. value = obj[key];
  58. //
  59. // Edge cases where we actually want to encode the value to an empty
  60. // string instead of the stringified value.
  61. //
  62. if (!value && (value === null || value === undef || isNaN(value))) {
  63. value = '';
  64. }
  65. pairs.push(encodeURIComponent(key) +'='+ encodeURIComponent(value));
  66. }
  67. }
  68. return pairs.length ? prefix + pairs.join('&') : '';
  69. }
  70. //
  71. // Expose the module.
  72. //
  73. exports.stringify = querystringify;
  74. exports.parse = querystring;