Skip to content

Commit 828f032

Browse files
Implement skips for stringify array format comma (#304)
Co-authored-by: Sindre Sorhus <sindresorhus@gmail.com>
1 parent 44abc66 commit 828f032

File tree

5 files changed

+67
-9
lines changed

5 files changed

+67
-9
lines changed

index.d.ts

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -229,6 +229,11 @@ export interface StringifyOptions {
229229
230230
queryString.stringify({foo: [1, 2, 3]}, {arrayFormat: 'comma'});
231231
//=> 'foo=1,2,3'
232+
233+
queryString.stringify({foo: [1, null, '']}, {arrayFormat: 'comma'});
234+
//=> 'foo=1,,'
235+
// Note that typing information for null values is lost
236+
// and `.parse('foo=1,,')` would return `{foo: [1, '', '']}`.
232237
```
233238
234239
- `separator`: Serialize arrays by separating elements with character:

index.js

Lines changed: 10 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -50,12 +50,20 @@ function encoderForArrayFormat(options) {
5050
case 'comma':
5151
case 'separator':
5252
return key => (result, value) => {
53-
if (value === null || value === undefined || value.length === 0) {
53+
if (
54+
value === undefined ||
55+
(options.skipNull && value === null) ||
56+
(options.skipEmptyString && value === '')
57+
) {
5458
return result;
5559
}
5660

5761
if (result.length === 0) {
58-
return [[encode(key, options), '=', encode(value, options)].join('')];
62+
return [[encode(key, options), '=', encode(value === null ? '' : value, options)].join('')];
63+
}
64+
65+
if (value === null || value === '') {
66+
return [[result, ''].join(options.arrayFormatSeparator)];
5967
}
6068

6169
return [[result, encode(value, options)].join(options.arrayFormatSeparator)];

readme.md

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -241,6 +241,11 @@ const queryString = require('query-string');
241241

242242
queryString.stringify({foo: [1, 2, 3]}, {arrayFormat: 'comma'});
243243
//=> 'foo=1,2,3'
244+
245+
queryString.stringify({foo: [1, null, '']}, {arrayFormat: 'comma'});
246+
//=> 'foo=1,,'
247+
// Note that typing information for null values is lost
248+
// and `.parse('foo=1,,')` would return `{foo: [1, '', '']}`.
244249
```
245250

246251
- `'none'`: Serialize arrays by using duplicate keys:

test/parse.js

Lines changed: 29 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -218,7 +218,7 @@ test('query strings having ordered index arrays and format option as `index`', t
218218
}), {bat: 'buz', foo: ['zero', 'two', 'one', 'three']});
219219
});
220220

221-
test('circuit parse -> stringify', t => {
221+
test('circuit parse stringify', t => {
222222
const original = 'foo[3]=foo&foo[2]&foo[1]=one&foo[0]=&bat=buz';
223223
const sortedOriginal = 'bat=buz&foo[0]=&foo[1]=one&foo[2]&foo[3]=foo';
224224
const expected = {bat: 'buz', foo: ['', 'one', null, 'foo']};
@@ -231,7 +231,7 @@ test('circuit parse -> stringify', t => {
231231
t.is(queryString.stringify(expected, options), sortedOriginal);
232232
});
233233

234-
test('circuit original -> parse - > stringify -> sorted original', t => {
234+
test('circuit original parse stringify sorted original', t => {
235235
const original = 'foo[21474836471]=foo&foo[21474836470]&foo[1]=one&foo[0]=&bat=buz';
236236
const sortedOriginal = 'bat=buz&foo[0]=&foo[1]=one&foo[2]&foo[3]=foo';
237237
const options = {
@@ -241,6 +241,33 @@ test('circuit original -> parse - > stringify -> sorted original', t => {
241241
t.deepEqual(queryString.stringify(queryString.parse(original, options), options), sortedOriginal);
242242
});
243243

244+
test('circuit parse → stringify with array commas', t => {
245+
const original = 'c=,a,,&b=&a=';
246+
const sortedOriginal = 'a=&b=&c=,a,,';
247+
const expected = {
248+
c: ['', 'a', '', ''],
249+
b: '',
250+
a: ''
251+
};
252+
const options = {
253+
arrayFormat: 'comma'
254+
};
255+
256+
t.deepEqual(queryString.parse(original, options), expected);
257+
258+
t.is(queryString.stringify(expected, options), sortedOriginal);
259+
});
260+
261+
test('circuit original → parse → stringify with array commas → sorted original', t => {
262+
const original = 'c=,a,,&b=&a=';
263+
const sortedOriginal = 'a=&b=&c=,a,,';
264+
const options = {
265+
arrayFormat: 'comma'
266+
};
267+
268+
t.deepEqual(queryString.stringify(queryString.parse(original, options), options), sortedOriginal);
269+
});
270+
244271
test('decode keys and values', t => {
245272
t.deepEqual(queryString.parse('st%C3%A5le=foo'), {ståle: 'foo'});
246273
t.deepEqual(queryString.parse('foo=%7B%ab%%7C%de%%7D+%%7Bst%C3%A5le%7D%'), {foo: '{%ab%|%de%} %{ståle}%'});

test/stringify.js

Lines changed: 18 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -126,13 +126,26 @@ test('array stringify representation with array commas', t => {
126126
}), 'bar=one,two&foo');
127127
});
128128

129-
test('array stringify representation with array commas and null value', t => {
129+
test('array stringify representation with array commas, null & empty string', t => {
130130
t.is(queryString.stringify({
131-
foo: [null, 'a', null, ''],
132-
bar: [null]
131+
c: [null, 'a', '', null],
132+
b: [null],
133+
a: ['']
134+
}, {
135+
arrayFormat: 'comma'
136+
}), 'a=&b=&c=,a,,');
137+
});
138+
139+
test('array stringify representation with array commas, null & empty string (skip both)', t => {
140+
t.is(queryString.stringify({
141+
c: [null, 'a', '', null],
142+
b: [null],
143+
a: ['']
133144
}, {
145+
skipNull: true,
146+
skipEmptyString: true,
134147
arrayFormat: 'comma'
135-
}), 'foo=a');
148+
}), 'c=a');
136149
});
137150

138151
test('array stringify representation with array commas and 0 value', t => {
@@ -141,7 +154,7 @@ test('array stringify representation with array commas and 0 value', t => {
141154
bar: [null]
142155
}, {
143156
arrayFormat: 'comma'
144-
}), 'foo=a,0');
157+
}), 'bar=&foo=a,,0');
145158
});
146159

147160
test('array stringify representation with a bad array format', t => {

0 commit comments

Comments
 (0)