qs 6.2.3 → 6.3.2

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/.eslintrc CHANGED
@@ -1,19 +1,19 @@
1
1
  {
2
- "root": true,
2
+ "root": true,
3
3
 
4
- "extends": "@ljharb",
4
+ "extends": "@ljharb",
5
5
 
6
- "rules": {
7
- "complexity": [2, 22],
8
- "consistent-return": [1],
9
- "id-length": [2, { "min": 1, "max": 25, "properties": "never" }],
10
- "indent": [2, 4],
11
- "max-params": [2, 9],
12
- "max-statements": [2, 36],
13
- "no-extra-parens": [1],
14
- "no-continue": [1],
15
- "no-magic-numbers": 0,
16
- "no-restricted-syntax": [2, "BreakStatement", "DebuggerStatement", "ForInStatement", "LabeledStatement", "WithStatement"],
17
- "operator-linebreak": 1
18
- }
6
+ "rules": {
7
+ "complexity": [2, 25],
8
+ "consistent-return": 1,
9
+ "id-length": [2, { "min": 1, "max": 25, "properties": "never" }],
10
+ "indent": [2, 4],
11
+ "max-params": [2, 11],
12
+ "max-statements": [2, 42],
13
+ "no-extra-parens": 1,
14
+ "no-continue": 1,
15
+ "no-magic-numbers": 0,
16
+ "no-restricted-syntax": [2, "BreakStatement", "DebuggerStatement", "ForInStatement", "LabeledStatement", "WithStatement"],
17
+ "operator-linebreak": 1
18
+ }
19
19
  }
package/CHANGELOG.md CHANGED
@@ -1,11 +1,35 @@
1
- ## **6.2.3**
1
+ ## **6.3.2**
2
2
  - [Fix] follow `allowPrototypes` option during merge (#201, #200)
3
+ - [Dev Deps] update `eslint`
3
4
  - [Fix] chmod a-x
4
5
  - [Fix] support keys starting with brackets (#202, #200)
5
6
  - [Tests] up to `node` `v7.7`, `v6.10`,` v4.8`; disable osx builds since they block linux builds
6
7
 
7
- ## **6.2.2**
8
- - [Fix] ensure that `allowPrototypes: false` does not ever shadow Object.prototype properties
8
+ ## **6.3.1**
9
+ - [Fix] ensure that `allowPrototypes: false` does not ever shadow Object.prototype properties (thanks, @snyk!)
10
+ - [Dev Deps] update `eslint`, `@ljharb/eslint-config`, `browserify`, `iconv-lite`, `qs-iconv`, `tape`
11
+ - [Tests] on all node minors; improve test matrix
12
+ - [Docs] document stringify option `allowDots` (#195)
13
+ - [Docs] add empty object and array values example (#195)
14
+ - [Docs] Fix minor inconsistency/typo (#192)
15
+ - [Docs] document stringify option `sort` (#191)
16
+ - [Refactor] `stringify`: throw faster with an invalid encoder
17
+ - [Refactor] remove unnecessary escapes (#184)
18
+ - Remove contributing.md, since `qs` is no longer part of `hapi` (#183)
19
+
20
+ ## **6.3.0**
21
+ - [New] Add support for RFC 1738 (#174, #173)
22
+ - [New] `stringify`: Add `serializeDate` option to customize Date serialization (#159)
23
+ - [Fix] ensure `utils.merge` handles merging two arrays
24
+ - [Refactor] only constructors should be capitalized
25
+ - [Refactor] capitalized var names are for constructors only
26
+ - [Refactor] avoid using a sparse array
27
+ - [Robustness] `formats`: cache `String#replace`
28
+ - [Dev Deps] update `browserify`, `eslint`, `@ljharb/eslint-config`; add `safe-publish-latest`
29
+ - [Tests] up to `node` `v6.8`, `v4.6`; improve test matrix
30
+ - [Tests] flesh out arrayLimit/arrayFormat tests (#107)
31
+ - [Tests] skip Object.create tests when null objects are not available
32
+ - [Tests] Turn on eslint for test files (#175)
9
33
 
10
34
  ## **6.2.1**
11
35
  - [Fix] ensure `key[]=x&key[]&key[]=y` results in 3, not 2, values
package/README.md CHANGED
@@ -39,11 +39,11 @@ assert.deepEqual(qs.parse('foo[bar]=baz'), {
39
39
  });
40
40
  ```
41
41
 
42
- When using the `plainObjects` option the parsed value is returned as a plain object, created via `Object.create(null)` and as such you should be aware that prototype methods will not exist on it and a user may set those names to whatever value they like:
42
+ When using the `plainObjects` option the parsed value is returned as a null object, created via `Object.create(null)` and as such you should be aware that prototype methods will not exist on it and a user may set those names to whatever value they like:
43
43
 
44
44
  ```javascript
45
- var plainObject = qs.parse('a[hasOwnProperty]=b', { plainObjects: true });
46
- assert.deepEqual(plainObject, { a: { hasOwnProperty: 'b' } });
45
+ var nullObject = qs.parse('a[hasOwnProperty]=b', { plainObjects: true });
46
+ assert.deepEqual(nullObject, { a: { hasOwnProperty: 'b' } });
47
47
  ```
48
48
 
49
49
  By default parameters that would overwrite properties on the object prototype are ignored, if you wish to keep the data from those fields either use `plainObjects` as mentioned above, or set `allowPrototypes` to `true` which will allow user input to overwrite those properties. *WARNING* It is generally a bad idea to enable this option as it can cause problems when attempting to use the properties that have been overwritten. Always be careful with this option.
@@ -261,7 +261,7 @@ qs.stringify({ a: ['b', 'c', 'd'] }, { indices: false });
261
261
  // 'a=b&a=c&a=d'
262
262
  ```
263
263
 
264
- You may use the `arrayFormat` option to specify the format of the output array
264
+ You may use the `arrayFormat` option to specify the format of the output array:
265
265
 
266
266
  ```javascript
267
267
  qs.stringify({ a: ['b', 'c'] }, { arrayFormat: 'indices' })
@@ -272,12 +272,36 @@ qs.stringify({ a: ['b', 'c'] }, { arrayFormat: 'repeat' })
272
272
  // 'a=b&a=c'
273
273
  ```
274
274
 
275
+ When objects are stringified, by default they use bracket notation:
276
+
277
+ ```javascript
278
+ qs.stringify({ a: { b: { c: 'd', e: 'f' } } });
279
+ // 'a[b][c]=d&a[b][e]=f'
280
+ ```
281
+
282
+ You may override this to use dot notation by setting the `allowDots` option to `true`:
283
+
284
+ ```javascript
285
+ qs.stringify({ a: { b: { c: 'd', e: 'f' } } }, { allowDots: true });
286
+ // 'a.b.c=d&a.b.e=f'
287
+ ```
288
+
275
289
  Empty strings and null values will omit the value, but the equals sign (=) remains in place:
276
290
 
277
291
  ```javascript
278
292
  assert.equal(qs.stringify({ a: '' }), 'a=');
279
293
  ```
280
294
 
295
+ Key with no values (such as an empty object or array) will return nothing:
296
+
297
+ ```javascript
298
+ assert.equal(qs.stringify({ a: [] }), '');
299
+ assert.equal(qs.stringify({ a: {} }), '');
300
+ assert.equal(qs.stringify({ a: [{}] }), '');
301
+ assert.equal(qs.stringify({ a: { b: []} }), '');
302
+ assert.equal(qs.stringify({ a: { b: {}} }), '');
303
+ ```
304
+
281
305
  Properties that are set to `undefined` will be omitted entirely:
282
306
 
283
307
  ```javascript
@@ -290,6 +314,26 @@ The delimiter may be overridden with stringify as well:
290
314
  assert.equal(qs.stringify({ a: 'b', c: 'd' }, { delimiter: ';' }), 'a=b;c=d');
291
315
  ```
292
316
 
317
+ If you only want to override the serialization of `Date` objects, you can provide a `serializeDate` option:
318
+
319
+ ```javascript
320
+ var date = new Date(7);
321
+ assert.equal(qs.stringify({ a: date }), 'a=1970-01-01T00:00:00.007Z'.replace(/:/g, '%3A'));
322
+ assert.equal(
323
+ qs.stringify({ a: date }, { serializeDate: function (d) { return d.getTime(); } }),
324
+ 'a=7'
325
+ );
326
+ ```
327
+
328
+ You may use the `sort` option to affect the order of parameter keys:
329
+
330
+ ```javascript
331
+ function alphabeticalSort(a, b) {
332
+ return a.localeCompare(b);
333
+ }
334
+ assert.equal(qs.stringify({ a: 'c', z: 'y', b : 'f' }, { sort: alphabeticalSort }), 'a=c&b=f&z=y');
335
+ ```
336
+
293
337
  Finally, you can use the `filter` option to restrict which keys will be included in the stringified output.
294
338
  If you pass a function, it will be called for each key to obtain the replacement value. Otherwise, if you
295
339
  pass an array, it will be used to select properties and array indices for stringification:
@@ -374,3 +418,14 @@ var decoder = require('qs-iconv/decoder')('shift_jis');
374
418
  var obj = qs.parse('a=%82%B1%82%F1%82%C9%82%BF%82%CD%81I', { decoder: decoder });
375
419
  assert.deepEqual(obj, { a: 'こんにちは!' });
376
420
  ```
421
+
422
+ ### RFC 3986 and RFC 1738 space encoding
423
+
424
+ RFC3986 used as default option and encodes ' ' to *%20* which is backward compatible.
425
+ In the same time, output can be stringified as per RFC1738 with ' ' equal to '+'.
426
+
427
+ ```
428
+ assert.equal(qs.stringify({ a: 'b c' }), 'a=b%20c');
429
+ assert.equal(qs.stringify({ a: 'b c' }, { format : 'RFC3986' }), 'a=b%20c');
430
+ assert.equal(qs.stringify({ a: 'b c' }, { format : 'RFC1738' }), 'a=b+c');
431
+ ```
package/dist/qs.js CHANGED
@@ -1,34 +1,56 @@
1
1
  (function(f){if(typeof exports==="object"&&typeof module!=="undefined"){module.exports=f()}else if(typeof define==="function"&&define.amd){define([],f)}else{var g;if(typeof window!=="undefined"){g=window}else if(typeof global!=="undefined"){g=global}else if(typeof self!=="undefined"){g=self}else{g=this}g.Qs = f()}})(function(){var define,module,exports;return (function e(t,n,r){function s(o,u){if(!n[o]){if(!t[o]){var a=typeof require=="function"&&require;if(!u&&a)return a(o,!0);if(i)return i(o,!0);var f=new Error("Cannot find module '"+o+"'");throw f.code="MODULE_NOT_FOUND",f}var l=n[o]={exports:{}};t[o][0].call(l.exports,function(e){var n=t[o][1][e];return s(n?n:e)},l,l.exports,e,t,n,r)}return n[o].exports}var i=typeof require=="function"&&require;for(var o=0;o<r.length;o++)s(r[o]);return s})({1:[function(require,module,exports){
2
2
  'use strict';
3
3
 
4
- var Stringify = require('./stringify');
5
- var Parse = require('./parse');
4
+ var replace = String.prototype.replace;
5
+ var percentTwenties = /%20/g;
6
6
 
7
7
  module.exports = {
8
- stringify: Stringify,
9
- parse: Parse
8
+ 'default': 'RFC3986',
9
+ formatters: {
10
+ RFC1738: function (value) {
11
+ return replace.call(value, percentTwenties, '+');
12
+ },
13
+ RFC3986: function (value) {
14
+ return value;
15
+ }
16
+ },
17
+ RFC1738: 'RFC1738',
18
+ RFC3986: 'RFC3986'
19
+ };
20
+
21
+ },{}],2:[function(require,module,exports){
22
+ 'use strict';
23
+
24
+ var stringify = require('./stringify');
25
+ var parse = require('./parse');
26
+ var formats = require('./formats');
27
+
28
+ module.exports = {
29
+ formats: formats,
30
+ parse: parse,
31
+ stringify: stringify
10
32
  };
11
33
 
12
- },{"./parse":2,"./stringify":3}],2:[function(require,module,exports){
34
+ },{"./formats":1,"./parse":3,"./stringify":4}],3:[function(require,module,exports){
13
35
  'use strict';
14
36
 
15
- var Utils = require('./utils');
37
+ var utils = require('./utils');
16
38
 
17
39
  var has = Object.prototype.hasOwnProperty;
18
40
 
19
41
  var defaults = {
42
+ allowDots: false,
43
+ allowPrototypes: false,
44
+ arrayLimit: 20,
45
+ decoder: utils.decode,
20
46
  delimiter: '&',
21
47
  depth: 5,
22
- arrayLimit: 20,
23
48
  parameterLimit: 1000,
24
- strictNullHandling: false,
25
49
  plainObjects: false,
26
- allowPrototypes: false,
27
- allowDots: false,
28
- decoder: Utils.decode
50
+ strictNullHandling: false
29
51
  };
30
52
 
31
- var parseValues = function parseValues(str, options) {
53
+ var parseValues = function parseQueryStringValues(str, options) {
32
54
  var obj = {};
33
55
  var parts = str.split(options.delimiter, options.parameterLimit === Infinity ? undefined : options.parameterLimit);
34
56
 
@@ -54,7 +76,7 @@ var parseValues = function parseValues(str, options) {
54
76
  return obj;
55
77
  };
56
78
 
57
- var parseObject = function parseObject(chain, val, options) {
79
+ var parseObject = function parseObjectRecursive(chain, val, options) {
58
80
  if (!chain.length) {
59
81
  return val;
60
82
  }
@@ -86,7 +108,7 @@ var parseObject = function parseObject(chain, val, options) {
86
108
  return obj;
87
109
  };
88
110
 
89
- var parseKeys = function parseKeys(givenKey, val, options) {
111
+ var parseKeys = function parseQueryStringKeys(givenKey, val, options) {
90
112
  if (!givenKey) {
91
113
  return;
92
114
  }
@@ -148,7 +170,7 @@ module.exports = function (str, opts) {
148
170
  throw new TypeError('Decoder has to be a function.');
149
171
  }
150
172
 
151
- options.delimiter = typeof options.delimiter === 'string' || Utils.isRegExp(options.delimiter) ? options.delimiter : defaults.delimiter;
173
+ options.delimiter = typeof options.delimiter === 'string' || utils.isRegExp(options.delimiter) ? options.delimiter : defaults.delimiter;
152
174
  options.depth = typeof options.depth === 'number' ? options.depth : defaults.depth;
153
175
  options.arrayLimit = typeof options.arrayLimit === 'number' ? options.arrayLimit : defaults.arrayLimit;
154
176
  options.parseArrays = options.parseArrays !== false;
@@ -172,43 +194,61 @@ module.exports = function (str, opts) {
172
194
  for (var i = 0; i < keys.length; ++i) {
173
195
  var key = keys[i];
174
196
  var newObj = parseKeys(key, tempObj[key], options);
175
- obj = Utils.merge(obj, newObj, options);
197
+ obj = utils.merge(obj, newObj, options);
176
198
  }
177
199
 
178
- return Utils.compact(obj);
200
+ return utils.compact(obj);
179
201
  };
180
202
 
181
- },{"./utils":4}],3:[function(require,module,exports){
203
+ },{"./utils":5}],4:[function(require,module,exports){
182
204
  'use strict';
183
205
 
184
- var Utils = require('./utils');
206
+ var utils = require('./utils');
207
+ var formats = require('./formats');
185
208
 
186
209
  var arrayPrefixGenerators = {
187
- brackets: function brackets(prefix) {
210
+ brackets: function brackets(prefix) { // eslint-disable-line func-name-matching
188
211
  return prefix + '[]';
189
212
  },
190
- indices: function indices(prefix, key) {
213
+ indices: function indices(prefix, key) { // eslint-disable-line func-name-matching
191
214
  return prefix + '[' + key + ']';
192
215
  },
193
- repeat: function repeat(prefix) {
216
+ repeat: function repeat(prefix) { // eslint-disable-line func-name-matching
194
217
  return prefix;
195
218
  }
196
219
  };
197
220
 
221
+ var toISO = Date.prototype.toISOString;
222
+
198
223
  var defaults = {
199
224
  delimiter: '&',
200
- strictNullHandling: false,
201
- skipNulls: false,
202
225
  encode: true,
203
- encoder: Utils.encode
226
+ encoder: utils.encode,
227
+ serializeDate: function serializeDate(date) { // eslint-disable-line func-name-matching
228
+ return toISO.call(date);
229
+ },
230
+ skipNulls: false,
231
+ strictNullHandling: false
204
232
  };
205
233
 
206
- var stringify = function stringify(object, prefix, generateArrayPrefix, strictNullHandling, skipNulls, encoder, filter, sort, allowDots) {
234
+ var stringify = function stringify( // eslint-disable-line func-name-matching
235
+ object,
236
+ prefix,
237
+ generateArrayPrefix,
238
+ strictNullHandling,
239
+ skipNulls,
240
+ encoder,
241
+ filter,
242
+ sort,
243
+ allowDots,
244
+ serializeDate,
245
+ formatter
246
+ ) {
207
247
  var obj = object;
208
248
  if (typeof filter === 'function') {
209
249
  obj = filter(prefix, obj);
210
250
  } else if (obj instanceof Date) {
211
- obj = obj.toISOString();
251
+ obj = serializeDate(obj);
212
252
  } else if (obj === null) {
213
253
  if (strictNullHandling) {
214
254
  return encoder ? encoder(prefix) : prefix;
@@ -217,11 +257,11 @@ var stringify = function stringify(object, prefix, generateArrayPrefix, strictNu
217
257
  obj = '';
218
258
  }
219
259
 
220
- if (typeof obj === 'string' || typeof obj === 'number' || typeof obj === 'boolean' || Utils.isBuffer(obj)) {
260
+ if (typeof obj === 'string' || typeof obj === 'number' || typeof obj === 'boolean' || utils.isBuffer(obj)) {
221
261
  if (encoder) {
222
- return [encoder(prefix) + '=' + encoder(obj)];
262
+ return [formatter(encoder(prefix)) + '=' + formatter(encoder(obj))];
223
263
  }
224
- return [prefix + '=' + String(obj)];
264
+ return [formatter(prefix) + '=' + formatter(String(obj))];
225
265
  }
226
266
 
227
267
  var values = [];
@@ -246,9 +286,33 @@ var stringify = function stringify(object, prefix, generateArrayPrefix, strictNu
246
286
  }
247
287
 
248
288
  if (Array.isArray(obj)) {
249
- values = values.concat(stringify(obj[key], generateArrayPrefix(prefix, key), generateArrayPrefix, strictNullHandling, skipNulls, encoder, filter, sort, allowDots));
289
+ values = values.concat(stringify(
290
+ obj[key],
291
+ generateArrayPrefix(prefix, key),
292
+ generateArrayPrefix,
293
+ strictNullHandling,
294
+ skipNulls,
295
+ encoder,
296
+ filter,
297
+ sort,
298
+ allowDots,
299
+ serializeDate,
300
+ formatter
301
+ ));
250
302
  } else {
251
- values = values.concat(stringify(obj[key], prefix + (allowDots ? '.' + key : '[' + key + ']'), generateArrayPrefix, strictNullHandling, skipNulls, encoder, filter, sort, allowDots));
303
+ values = values.concat(stringify(
304
+ obj[key],
305
+ prefix + (allowDots ? '.' + key : '[' + key + ']'),
306
+ generateArrayPrefix,
307
+ strictNullHandling,
308
+ skipNulls,
309
+ encoder,
310
+ filter,
311
+ sort,
312
+ allowDots,
313
+ serializeDate,
314
+ formatter
315
+ ));
252
316
  }
253
317
  }
254
318
 
@@ -258,6 +322,11 @@ var stringify = function stringify(object, prefix, generateArrayPrefix, strictNu
258
322
  module.exports = function (object, opts) {
259
323
  var obj = object;
260
324
  var options = opts || {};
325
+
326
+ if (options.encoder !== null && options.encoder !== undefined && typeof options.encoder !== 'function') {
327
+ throw new TypeError('Encoder has to be a function.');
328
+ }
329
+
261
330
  var delimiter = typeof options.delimiter === 'undefined' ? defaults.delimiter : options.delimiter;
262
331
  var strictNullHandling = typeof options.strictNullHandling === 'boolean' ? options.strictNullHandling : defaults.strictNullHandling;
263
332
  var skipNulls = typeof options.skipNulls === 'boolean' ? options.skipNulls : defaults.skipNulls;
@@ -265,18 +334,22 @@ module.exports = function (object, opts) {
265
334
  var encoder = encode ? (typeof options.encoder === 'function' ? options.encoder : defaults.encoder) : null;
266
335
  var sort = typeof options.sort === 'function' ? options.sort : null;
267
336
  var allowDots = typeof options.allowDots === 'undefined' ? false : options.allowDots;
337
+ var serializeDate = typeof options.serializeDate === 'function' ? options.serializeDate : defaults.serializeDate;
338
+ if (typeof options.format === 'undefined') {
339
+ options.format = formats.default;
340
+ } else if (!Object.prototype.hasOwnProperty.call(formats.formatters, options.format)) {
341
+ throw new TypeError('Unknown format option provided.');
342
+ }
343
+ var formatter = formats.formatters[options.format];
268
344
  var objKeys;
269
345
  var filter;
270
346
 
271
- if (options.encoder !== null && options.encoder !== undefined && typeof options.encoder !== 'function') {
272
- throw new TypeError('Encoder has to be a function.');
273
- }
274
-
275
347
  if (typeof options.filter === 'function') {
276
348
  filter = options.filter;
277
349
  obj = filter('', obj);
278
350
  } else if (Array.isArray(options.filter)) {
279
- objKeys = filter = options.filter;
351
+ filter = options.filter;
352
+ objKeys = filter;
280
353
  }
281
354
 
282
355
  var keys = [];
@@ -311,28 +384,40 @@ module.exports = function (object, opts) {
311
384
  continue;
312
385
  }
313
386
 
314
- keys = keys.concat(stringify(obj[key], key, generateArrayPrefix, strictNullHandling, skipNulls, encoder, filter, sort, allowDots));
387
+ keys = keys.concat(stringify(
388
+ obj[key],
389
+ key,
390
+ generateArrayPrefix,
391
+ strictNullHandling,
392
+ skipNulls,
393
+ encoder,
394
+ filter,
395
+ sort,
396
+ allowDots,
397
+ serializeDate,
398
+ formatter
399
+ ));
315
400
  }
316
401
 
317
402
  return keys.join(delimiter);
318
403
  };
319
404
 
320
- },{"./utils":4}],4:[function(require,module,exports){
405
+ },{"./formats":1,"./utils":5}],5:[function(require,module,exports){
321
406
  'use strict';
322
407
 
408
+ var has = Object.prototype.hasOwnProperty;
409
+
323
410
  var hexTable = (function () {
324
- var array = new Array(256);
411
+ var array = [];
325
412
  for (var i = 0; i < 256; ++i) {
326
- array[i] = '%' + ((i < 16 ? '0' : '') + i.toString(16)).toUpperCase();
413
+ array.push('%' + ((i < 16 ? '0' : '') + i.toString(16)).toUpperCase());
327
414
  }
328
415
 
329
416
  return array;
330
417
  }());
331
418
 
332
- var has = Object.prototype.hasOwnProperty;
333
-
334
419
  exports.arrayToObject = function (source, options) {
335
- var obj = options.plainObjects ? Object.create(null) : {};
420
+ var obj = options && options.plainObjects ? Object.create(null) : {};
336
421
  for (var i = 0; i < source.length; ++i) {
337
422
  if (typeof source[i] !== 'undefined') {
338
423
  obj[i] = source[i];
@@ -370,10 +455,25 @@ exports.merge = function (target, source, options) {
370
455
  mergeTarget = exports.arrayToObject(target, options);
371
456
  }
372
457
 
458
+ if (Array.isArray(target) && Array.isArray(source)) {
459
+ source.forEach(function (item, i) {
460
+ if (has.call(target, i)) {
461
+ if (target[i] && typeof target[i] === 'object') {
462
+ target[i] = exports.merge(target[i], item, options);
463
+ } else {
464
+ target.push(item);
465
+ }
466
+ } else {
467
+ target[i] = item;
468
+ }
469
+ });
470
+ return target;
471
+ }
472
+
373
473
  return Object.keys(source).reduce(function (acc, key) {
374
474
  var value = source[key];
375
475
 
376
- if (has.call(acc, key)) {
476
+ if (Object.prototype.hasOwnProperty.call(acc, key)) {
377
477
  acc[key] = exports.merge(acc[key], value, options);
378
478
  } else {
379
479
  acc[key] = value;
@@ -433,7 +533,7 @@ exports.encode = function (str) {
433
533
 
434
534
  i += 1;
435
535
  c = 0x10000 + (((c & 0x3FF) << 10) | (string.charCodeAt(i) & 0x3FF));
436
- out += hexTable[0xF0 | (c >> 18)] + hexTable[0x80 | ((c >> 12) & 0x3F)] + hexTable[0x80 | ((c >> 6) & 0x3F)] + hexTable[0x80 | (c & 0x3F)];
536
+ out += hexTable[0xF0 | (c >> 18)] + hexTable[0x80 | ((c >> 12) & 0x3F)] + hexTable[0x80 | ((c >> 6) & 0x3F)] + hexTable[0x80 | (c & 0x3F)]; // eslint-disable-line max-len
437
537
  }
438
538
 
439
539
  return out;
@@ -467,10 +567,9 @@ exports.compact = function (obj, references) {
467
567
  }
468
568
 
469
569
  var keys = Object.keys(obj);
470
- for (var j = 0; j < keys.length; ++j) {
471
- var key = keys[j];
570
+ keys.forEach(function (key) {
472
571
  obj[key] = exports.compact(obj[key], refs);
473
- }
572
+ });
474
573
 
475
574
  return obj;
476
575
  };
@@ -487,5 +586,5 @@ exports.isBuffer = function (obj) {
487
586
  return !!(obj.constructor && obj.constructor.isBuffer && obj.constructor.isBuffer(obj));
488
587
  };
489
588
 
490
- },{}]},{},[1])(1)
589
+ },{}]},{},[2])(2)
491
590
  });
package/lib/formats.js ADDED
@@ -0,0 +1,18 @@
1
+ 'use strict';
2
+
3
+ var replace = String.prototype.replace;
4
+ var percentTwenties = /%20/g;
5
+
6
+ module.exports = {
7
+ 'default': 'RFC3986',
8
+ formatters: {
9
+ RFC1738: function (value) {
10
+ return replace.call(value, percentTwenties, '+');
11
+ },
12
+ RFC3986: function (value) {
13
+ return value;
14
+ }
15
+ },
16
+ RFC1738: 'RFC1738',
17
+ RFC3986: 'RFC3986'
18
+ };
package/lib/index.js CHANGED
@@ -1,9 +1,11 @@
1
1
  'use strict';
2
2
 
3
- var Stringify = require('./stringify');
4
- var Parse = require('./parse');
3
+ var stringify = require('./stringify');
4
+ var parse = require('./parse');
5
+ var formats = require('./formats');
5
6
 
6
7
  module.exports = {
7
- stringify: Stringify,
8
- parse: Parse
8
+ formats: formats,
9
+ parse: parse,
10
+ stringify: stringify
9
11
  };
package/lib/parse.js CHANGED
@@ -1,22 +1,22 @@
1
1
  'use strict';
2
2
 
3
- var Utils = require('./utils');
3
+ var utils = require('./utils');
4
4
 
5
5
  var has = Object.prototype.hasOwnProperty;
6
6
 
7
7
  var defaults = {
8
+ allowDots: false,
9
+ allowPrototypes: false,
10
+ arrayLimit: 20,
11
+ decoder: utils.decode,
8
12
  delimiter: '&',
9
13
  depth: 5,
10
- arrayLimit: 20,
11
14
  parameterLimit: 1000,
12
- strictNullHandling: false,
13
15
  plainObjects: false,
14
- allowPrototypes: false,
15
- allowDots: false,
16
- decoder: Utils.decode
16
+ strictNullHandling: false
17
17
  };
18
18
 
19
- var parseValues = function parseValues(str, options) {
19
+ var parseValues = function parseQueryStringValues(str, options) {
20
20
  var obj = {};
21
21
  var parts = str.split(options.delimiter, options.parameterLimit === Infinity ? undefined : options.parameterLimit);
22
22
 
@@ -42,7 +42,7 @@ var parseValues = function parseValues(str, options) {
42
42
  return obj;
43
43
  };
44
44
 
45
- var parseObject = function parseObject(chain, val, options) {
45
+ var parseObject = function parseObjectRecursive(chain, val, options) {
46
46
  if (!chain.length) {
47
47
  return val;
48
48
  }
@@ -74,7 +74,7 @@ var parseObject = function parseObject(chain, val, options) {
74
74
  return obj;
75
75
  };
76
76
 
77
- var parseKeys = function parseKeys(givenKey, val, options) {
77
+ var parseKeys = function parseQueryStringKeys(givenKey, val, options) {
78
78
  if (!givenKey) {
79
79
  return;
80
80
  }
@@ -136,7 +136,7 @@ module.exports = function (str, opts) {
136
136
  throw new TypeError('Decoder has to be a function.');
137
137
  }
138
138
 
139
- options.delimiter = typeof options.delimiter === 'string' || Utils.isRegExp(options.delimiter) ? options.delimiter : defaults.delimiter;
139
+ options.delimiter = typeof options.delimiter === 'string' || utils.isRegExp(options.delimiter) ? options.delimiter : defaults.delimiter;
140
140
  options.depth = typeof options.depth === 'number' ? options.depth : defaults.depth;
141
141
  options.arrayLimit = typeof options.arrayLimit === 'number' ? options.arrayLimit : defaults.arrayLimit;
142
142
  options.parseArrays = options.parseArrays !== false;
@@ -160,8 +160,8 @@ module.exports = function (str, opts) {
160
160
  for (var i = 0; i < keys.length; ++i) {
161
161
  var key = keys[i];
162
162
  var newObj = parseKeys(key, tempObj[key], options);
163
- obj = Utils.merge(obj, newObj, options);
163
+ obj = utils.merge(obj, newObj, options);
164
164
  }
165
165
 
166
- return Utils.compact(obj);
166
+ return utils.compact(obj);
167
167
  };