@sap/cds-dk 10.2.0 → 10.2.1
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/CHANGELOG.md +13 -0
- package/bin/bind.js +5 -4
- package/bin/completion/scripts/cds.fish +4 -3
- package/bin/completion/scripts/cds.ps1 +4 -4
- package/bin/completion/scripts/cds.sh +4 -4
- package/bin/completion/scripts/cds.zsh +4 -4
- package/bin/debug.js +3 -3
- package/bin/deploy/index.js +2 -2
- package/bin/deploy/to-hana/hana.js +1 -1
- package/bin/deploy/to-hana/hdiDeployUtil.js +25 -14
- package/bin/up.js +3 -3
- package/bin/version.js +1 -1
- package/bin/watch/vite-watch.js +12 -6
- package/lib/bind/shared.js +1 -1
- package/lib/init/index.js +1 -0
- package/lib/init/projectReader.js +3 -2
- package/lib/init/template/approuter/files/values.yaml.hbs +0 -9
- package/lib/init/template/approuter/files/xs-app.json.hbs +0 -22
- package/lib/init/template/approuter/index.js +8 -9
- package/lib/init/template/html5-repo/index.js +12 -0
- package/lib/init/template/react/files/vite.config.{{extension}}.hbs +2 -3
- package/lib/init/template/react/index.js +1 -3
- package/lib/init/template/sample/files/app/index.html.hbs +18 -0
- package/lib/init/template/sample/index.js +1 -0
- package/lib/init/template/vue/files/vite.config.{{extension}}.hbs +2 -3
- package/lib/init/template/vue/index.js +1 -3
- package/lib/mtx/push.js +7 -1
- package/node_modules/@cap-js/asyncapi/README.md +4 -14
- package/node_modules/@cap-js/asyncapi/cds-plugin.js +12 -0
- package/node_modules/@cap-js/asyncapi/index.js +3 -2
- package/node_modules/@cap-js/asyncapi/lib/compile/components/messages/index.js +4 -2
- package/node_modules/@cap-js/asyncapi/lib/compile/components/schemas/definition.js +11 -1
- package/node_modules/@cap-js/asyncapi/lib/compile/components/schemas/utils.js +16 -0
- package/node_modules/@cap-js/asyncapi/lib/compile/utils.js +4 -3
- package/node_modules/@cap-js/asyncapi/lib/import/importAsyncAPI.js +34 -0
- package/node_modules/@cap-js/asyncapi/lib/import/index.js +18 -0
- package/node_modules/@cap-js/asyncapi/lib/import/message.js +9 -0
- package/node_modules/@cap-js/asyncapi/lib/import/parserContext.js +368 -0
- package/node_modules/@cap-js/asyncapi/lib/import/utils.js +85 -0
- package/node_modules/@cap-js/asyncapi/package.json +89 -1
- package/node_modules/@sap/cds/CHANGELOG.md +10 -0
- package/node_modules/@sap/cds/app/index.js +1 -1
- package/node_modules/@sap/cds/lib/env/schemas/cds-package.js +0 -2
- package/node_modules/@sap/cds/lib/env/schemas/cds-rc.js +3 -3
- package/node_modules/@sap/cds/lib/env/schemas/index.js +4 -4
- package/node_modules/@sap/cds/lib/utils/cds-utils.js +21 -8
- package/node_modules/@sap/cds/libx/_runtime/messaging/common-utils/connections.js +45 -39
- package/node_modules/@sap/cds/libx/odata/ODataAdapter.js +1 -1
- package/node_modules/@sap/cds/libx/queue/TaskRunner.js +22 -5
- package/node_modules/@sap/cds/package.json +1 -1
- package/node_modules/@sap/cds-mtxs/CHANGELOG.md +8 -0
- package/node_modules/@sap/cds-mtxs/package.json +1 -1
- package/node_modules/@sap/cds-mtxs/srv/extensibility-service.js +57 -41
- package/node_modules/@sap/cds-mtxs/srv/jobs-service.js +27 -12
- package/node_modules/@sap/cds-mtxs/srv/plugins/hana.js +31 -25
- package/node_modules/body-parser/README.md +17 -13
- package/node_modules/body-parser/lib/read.js +74 -57
- package/node_modules/body-parser/lib/types/json.js +11 -11
- package/node_modules/body-parser/lib/types/urlencoded.js +5 -5
- package/node_modules/body-parser/lib/utils.js +0 -15
- package/node_modules/body-parser/package.json +7 -12
- package/node_modules/encodeurl/README.md +14 -0
- package/node_modules/encodeurl/index.js +5 -10
- package/node_modules/encodeurl/package.json +10 -6
- package/node_modules/on-finished/index.js +14 -2
- package/node_modules/on-finished/package.json +11 -7
- package/node_modules/qs/.editorconfig +1 -1
- package/node_modules/qs/CHANGELOG.md +87 -22
- package/node_modules/qs/README.md +63 -10
- package/node_modules/qs/dist/qs.js +17 -17
- package/node_modules/qs/eslint.config.mjs +61 -50
- package/node_modules/qs/lib/formats.js +7 -2
- package/node_modules/qs/lib/parse.js +29 -10
- package/node_modules/qs/lib/stringify.js +5 -3
- package/node_modules/qs/lib/utils.js +28 -9
- package/node_modules/qs/package.json +6 -6
- package/node_modules/qs/test/parse.js +335 -2
- package/node_modules/qs/test/stringify.js +222 -0
- package/node_modules/qs/test/utils.js +61 -3
- package/node_modules/semver/classes/range.js +2 -2
- package/node_modules/semver/internal/constants.js +30 -0
- package/node_modules/semver/internal/trim-comparator-whitespace.js +438 -0
- package/node_modules/semver/package.json +1 -1
- package/node_modules/ws/README.md +21 -29
- package/node_modules/ws/lib/buffer-util.js +13 -2
- package/node_modules/ws/lib/sender.js +4 -1
- package/node_modules/ws/lib/websocket.js +8 -3
- package/node_modules/ws/package.json +1 -1
- package/package.json +1 -1
- package/node_modules/on-finished/HISTORY.md +0 -98
|
@@ -65,10 +65,11 @@ function onFinished (msg, listener) {
|
|
|
65
65
|
|
|
66
66
|
function isFinished (msg) {
|
|
67
67
|
var socket = msg.socket
|
|
68
|
+
var finished = writableEnded(msg)
|
|
68
69
|
|
|
69
|
-
if (typeof
|
|
70
|
+
if (typeof finished === 'boolean') {
|
|
70
71
|
// OutgoingMessage
|
|
71
|
-
return Boolean(
|
|
72
|
+
return Boolean(finished || (socket && !socket.writable))
|
|
72
73
|
}
|
|
73
74
|
|
|
74
75
|
if (typeof msg.complete === 'boolean') {
|
|
@@ -232,3 +233,14 @@ function wrap (fn) {
|
|
|
232
233
|
// return bound function
|
|
233
234
|
return res.runInAsyncScope.bind(res, fn, null)
|
|
234
235
|
}
|
|
236
|
+
|
|
237
|
+
/**
|
|
238
|
+
* Determines if a writable stream has finished.
|
|
239
|
+
*
|
|
240
|
+
* @param {Object} res
|
|
241
|
+
* @returns {boolean}
|
|
242
|
+
* @private
|
|
243
|
+
*/
|
|
244
|
+
function writableEnded (res) {
|
|
245
|
+
return typeof res.writableEnded === 'boolean' ? res.writableEnded : res.finished
|
|
246
|
+
}
|
|
@@ -1,38 +1,42 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "on-finished",
|
|
3
3
|
"description": "Execute a callback when a request closes, finishes, or errors",
|
|
4
|
-
"version": "2.4.
|
|
4
|
+
"version": "2.4.2",
|
|
5
5
|
"contributors": [
|
|
6
6
|
"Douglas Christopher Wilson <doug@somethingdoug.com>",
|
|
7
7
|
"Jonathan Ong <me@jongleberry.com> (http://jongleberry.com)"
|
|
8
8
|
],
|
|
9
9
|
"license": "MIT",
|
|
10
10
|
"repository": "jshttp/on-finished",
|
|
11
|
+
"funding": {
|
|
12
|
+
"type": "opencollective",
|
|
13
|
+
"url": "https://opencollective.com/express"
|
|
14
|
+
},
|
|
15
|
+
"type": "commonjs",
|
|
11
16
|
"dependencies": {
|
|
12
17
|
"ee-first": "1.1.1"
|
|
13
18
|
},
|
|
14
19
|
"devDependencies": {
|
|
15
|
-
"eslint": "
|
|
20
|
+
"eslint": "8.17.0",
|
|
16
21
|
"eslint-config-standard": "14.1.1",
|
|
17
|
-
"eslint-plugin-import": "2.
|
|
22
|
+
"eslint-plugin-import": "2.26.0",
|
|
18
23
|
"eslint-plugin-markdown": "2.2.1",
|
|
19
24
|
"eslint-plugin-node": "11.1.0",
|
|
20
|
-
"eslint-plugin-promise": "
|
|
25
|
+
"eslint-plugin-promise": "6.0.0",
|
|
21
26
|
"eslint-plugin-standard": "4.1.0",
|
|
22
|
-
"mocha": "
|
|
27
|
+
"mocha": "12.0.3",
|
|
23
28
|
"nyc": "15.1.0"
|
|
24
29
|
},
|
|
25
30
|
"engines": {
|
|
26
31
|
"node": ">= 0.8"
|
|
27
32
|
},
|
|
28
33
|
"files": [
|
|
29
|
-
"HISTORY.md",
|
|
30
34
|
"LICENSE",
|
|
31
35
|
"index.js"
|
|
32
36
|
],
|
|
33
37
|
"scripts": {
|
|
34
38
|
"lint": "eslint .",
|
|
35
|
-
"test": "mocha --reporter spec --
|
|
39
|
+
"test": "mocha --reporter spec --check-leaks test/",
|
|
36
40
|
"test-ci": "nyc --reporter=lcovonly --reporter=text npm test",
|
|
37
41
|
"test-cov": "nyc --reporter=html --reporter=text npm test"
|
|
38
42
|
}
|
|
@@ -1,26 +1,64 @@
|
|
|
1
|
+
## **6.17.1**
|
|
2
|
+
- [Fix] `parse`: `interpretNumericEntities`: decode code points above U+FFFF as surrogate pairs (#640)
|
|
3
|
+
- [Fix] `parse`: respect `plainObjects` for `[]` with `parseArrays: false` (#639)
|
|
4
|
+
- [Fix] `utils`: `merge`: count the elements of a sparse array against `arrayLimit`, not its holes
|
|
5
|
+
- [Fix] `parse`: guard bracket-wrapped prototype keys at depth 0 (#638)
|
|
6
|
+
- [Refactor] `parse`: extract wrapping-bracket stripping helper
|
|
7
|
+
- [readme] document that `depth: 0` and `depth: false` keep keys flat
|
|
8
|
+
- [Tests] `parse`: pin depth-0 bracket stripping and prototype keys kept by `allowPrototypes`/`plainObjects`
|
|
9
|
+
|
|
10
|
+
## **6.17.0**
|
|
11
|
+
- [New] `stringify`: add `WHATWG` format (#623)
|
|
12
|
+
- [Fix] `stringify`: do not sort the caller's `filter` array in place (#637)
|
|
13
|
+
- [Fix] `parse`: copy an own `__proto__` key as data (#636)
|
|
14
|
+
- [Fix] `parse`: decode percent-encoded dots case-insensitively (#635)
|
|
15
|
+
- [Fix] `stringify`: encode keys when `allowEmptyArrays` is set (#561)
|
|
16
|
+
- [Fix] `parse`: preserve comma arrays when interpreting numeric entities (#630)
|
|
17
|
+
- [Fix] `parse`: allow scalar fields with a zero array limit (#627)
|
|
18
|
+
- [Fix] `parse`: do not count an existing comma array toward `arrayLimit` when `duplicates` discards or replaces it
|
|
19
|
+
- [Fix] `utils`: `encode`: encode lone surrogates as U+FFFD instead of consuming the next code unit (#624)
|
|
20
|
+
- [eslint] fix indentation
|
|
21
|
+
- [readme] document the encoder's `format` argument
|
|
22
|
+
- [meta] add changelog acknowledgement
|
|
23
|
+
- [meta] fix changelog indents
|
|
24
|
+
- [Dev Deps] update `eslint`, `evalmd`, `npmignore`
|
|
25
|
+
- [Tests] `stringify`: pin `allowEmptyArrays` output for keys that need no encoding
|
|
26
|
+
- [Tests] `stringify`: pin `sort` order for nested keys selected by an array `filter`
|
|
27
|
+
- [Tests] `parse`: cover `interpretNumericEntities` across value shapes, keys, and the charset sentinel
|
|
28
|
+
- [Tests] `parse`: cover more input that builds no array at a zero or negative `arrayLimit`
|
|
29
|
+
- [Tests] `parse`: cover `comma` with a zero or negative `arrayLimit`, and combining a full comma array
|
|
30
|
+
- [Tests] `parse`: pin the behavior of a zero or negative `arrayLimit`
|
|
31
|
+
- [Tests] `utils`/`stringify`: pin `~`, `*`, and parens encoding in RFC3986 and RFC1738
|
|
32
|
+
|
|
33
|
+
## **6.16.2**
|
|
34
|
+
- [Fix] `stringify`: encode keys when `allowEmptyArrays` is set (#561)
|
|
35
|
+
- [meta] use double quotes for better OS support
|
|
36
|
+
- [Dev Deps] update `evalmd`, `npmignore`
|
|
37
|
+
- [Tests] `stringify`: pin `allowEmptyArrays` output for keys that need no encoding
|
|
38
|
+
|
|
1
39
|
## **6.16.1**
|
|
2
|
-
|
|
3
|
-
|
|
4
|
-
|
|
5
|
-
|
|
6
|
-
|
|
7
|
-
|
|
8
|
-
|
|
9
|
-
|
|
10
|
-
|
|
11
|
-
|
|
12
|
-
|
|
13
|
-
|
|
14
|
-
|
|
15
|
-
|
|
16
|
-
|
|
17
|
-
|
|
18
|
-
|
|
19
|
-
|
|
20
|
-
|
|
21
|
-
|
|
22
|
-
|
|
23
|
-
|
|
40
|
+
- [Fix] `parse`: do not mutate an object input
|
|
41
|
+
- [Fix] `stringify`: stop re-encoding structural separator dots when `encodeDotInKeys` is set (#564)
|
|
42
|
+
- [Fix] `stringify`: `arrayFormat: 'comma'`: pass the full encoder arguments with `encodeValuesOnly`
|
|
43
|
+
- [Fix] `utils`: encode `+` as `%2B` in iso-8859-1 mode so values round-trip (#565)
|
|
44
|
+
- [Fix] parse: only convert top-level dots to brackets when allowDots is on (#621)
|
|
45
|
+
- [Fix] `stringify`: ignore inherited array format names (#622)
|
|
46
|
+
- [Fix] `stringify`: `arrayFormat: 'comma'`: do not throw on elements with no callable `toString`
|
|
47
|
+
- [Fix] `utils`: `merge`: seed an overflow container's index from its own keys, not just the source
|
|
48
|
+
- [Fix] `utils`: `merge`: keep a `strictMerge` conflict container's index and `arrayLimit` correct
|
|
49
|
+
- [Fix] `parse`: only treat `[]` as array syntax when it ends the key
|
|
50
|
+
- [Perf] `decode`: skip decoders when there is no percent sign (#583)
|
|
51
|
+
- [Robustness] `utils`: `merge`: apply `arrayLimit` to the two-element array built for colliding values
|
|
52
|
+
- [Robustness] `parse`: bound the nesting added by repeated `strictMerge` conflicts (credit @Yeaseen)
|
|
53
|
+
- [Docs] document that `qs` and flat parsers disagree about parameter names
|
|
54
|
+
- [Docs] clarify that `throwOnLimitExceeded` limits each array, not the total number of values
|
|
55
|
+
- [Docs] clarify 6.14.1/6.15.2 parse bracket behavior change (#567, #568)
|
|
56
|
+
- [meta] fix changelog indents
|
|
57
|
+
- [actions] set least-privilege `cache-mode`
|
|
58
|
+
- [Tests] `utils`: `decode`: add missing cases
|
|
59
|
+
- [Tests] `parse`: characterize the `]=` split when an `=` precedes any bracket group (#620)
|
|
60
|
+
- [Tests] `parse`: `allowDots`: cover stray close brackets before a dot
|
|
61
|
+
- [Dev Deps] update `@ljharb/eslint-config`, `eslint`, `tape`
|
|
24
62
|
|
|
25
63
|
## **6.16.0**
|
|
26
64
|
- [New] `stringify`: add a `depth` option to bound recursion depth (default `Infinity`)
|
|
@@ -37,6 +75,12 @@
|
|
|
37
75
|
- [Dev Deps] update `@ljharb/eslint-config`, `eslint`
|
|
38
76
|
- [Dev Deps] update `eslint`, `evalmd`
|
|
39
77
|
|
|
78
|
+
## **6.15.4**
|
|
79
|
+
- [Fix] `stringify`: encode keys when `allowEmptyArrays` is set (#561)
|
|
80
|
+
- [meta] use double quotes for better OS support
|
|
81
|
+
- [Dev Deps] update `@ljharb/eslint-config`, `evalmd`, `npmignore`, `tape`
|
|
82
|
+
- [Tests] `stringify`: pin `allowEmptyArrays` output for keys that need no encoding
|
|
83
|
+
|
|
40
84
|
## **6.15.3**
|
|
41
85
|
- [Fix] `parse`: enforce `throwOnLimitExceeded` for cumulative array growth via `combine`/`merge`
|
|
42
86
|
- [Fix] `utils`: respect encoding of surrogate pairs across chunks (#559)
|
|
@@ -68,6 +112,13 @@
|
|
|
68
112
|
- [New] `parse`: add `strictMerge` option to wrap object/primitive conflicts in an array (#425, #122)
|
|
69
113
|
- [Fix] `duplicates` option should not apply to bracket notation keys (#514)
|
|
70
114
|
|
|
115
|
+
## **6.14.3**
|
|
116
|
+
- [Fix] `stringify`: encode keys when `allowEmptyArrays` is set (#561)
|
|
117
|
+
- [meta] use double quotes for better OS support
|
|
118
|
+
- [Deps] update `side-channel`
|
|
119
|
+
- [Dev Deps] update `@ljharb/eslint-config`, `es-value-fixtures`, `eslint`, `evalmd`, `mock-property`, `npmignore`, `tape`
|
|
120
|
+
- [Tests] `stringify`: pin `allowEmptyArrays` output for keys that need no encoding
|
|
121
|
+
|
|
71
122
|
## **6.14.2**
|
|
72
123
|
- [Fix] `parse`: mark overflow objects for indexed notation exceeding `arrayLimit` (#546)
|
|
73
124
|
- [Fix] `arrayLimit` means max count, not max index, in `combine`/`merge`/`parseArrayValue`
|
|
@@ -100,6 +151,13 @@
|
|
|
100
151
|
- [Dev Deps] update `es-value-fixtures`, `has-bigints`, `has-proto`, `has-symbols`
|
|
101
152
|
- [Tests] increase coverage
|
|
102
153
|
|
|
154
|
+
## **6.13.4**
|
|
155
|
+
- [Fix] `stringify`: encode keys when `allowEmptyArrays` is set (#561)
|
|
156
|
+
- [meta] use double quotes for better OS support
|
|
157
|
+
- [Deps] update `side-channel`
|
|
158
|
+
- [Dev Deps] update `@ljharb/eslint-config`, `es-value-fixtures`, `eslint`, `evalmd`, `for-each`, `has-symbols`, `mock-property`, `npmignore`, `object-inspect`, `tape`
|
|
159
|
+
- [Tests] `stringify`: pin `allowEmptyArrays` output for keys that need no encoding
|
|
160
|
+
|
|
103
161
|
## **6.13.3**
|
|
104
162
|
[Fix] fix regressions from robustness refactor
|
|
105
163
|
[actions] update reusable workflows
|
|
@@ -127,6 +185,13 @@
|
|
|
127
185
|
- [New] `parse`: add `strictDepth` option (#511)
|
|
128
186
|
- [Tests] use `npm audit` instead of `aud`
|
|
129
187
|
|
|
188
|
+
## **6.12.6**
|
|
189
|
+
- [Fix] `stringify`: encode keys when `allowEmptyArrays` is set (#561)
|
|
190
|
+
- [meta] use `npm audit` instead of `aud`
|
|
191
|
+
- [Deps] update `side-channel`
|
|
192
|
+
- [Dev Deps] update `@ljharb/eslint-config`, `es-value-fixtures`, `eslint`, `evalmd`, `for-each`, `has-symbols`, `mock-property`, `npmignore`, `object-inspect`, `tape`
|
|
193
|
+
- [Tests] `stringify`: pin `allowEmptyArrays` output for keys that need no encoding
|
|
194
|
+
|
|
130
195
|
## **6.12.5**
|
|
131
196
|
- [Fix] fix regressions from robustness refactor
|
|
132
197
|
- [actions] update reusable workflows
|
|
@@ -85,7 +85,9 @@ assert.deepEqual(qs.parse('foo[bar][baz]=foobarbaz'), {
|
|
|
85
85
|
});
|
|
86
86
|
```
|
|
87
87
|
|
|
88
|
-
Since v6.14.1 and v6.15.2, `parse` interprets nested bracket groups more consistently.
|
|
88
|
+
Since v6.14.1 and v6.15.2, `parse` interprets nested bracket groups more consistently.
|
|
89
|
+
Query strings with unbalanced `[`/`]` can produce different results than in 6.15.1;
|
|
90
|
+
see [#558](https://github.com/ljharb/qs/issues/558).
|
|
89
91
|
|
|
90
92
|
Because of that bracket grammar,
|
|
91
93
|
**qs** does not agree with `URLSearchParams`,
|
|
@@ -132,6 +134,15 @@ var deep = qs.parse('a[b][c][d][e][f][g][h][i]=j', { depth: 1 });
|
|
|
132
134
|
assert.deepEqual(deep, { a: { b: { '[c][d][e][f][g][h][i]': 'j' } } });
|
|
133
135
|
```
|
|
134
136
|
|
|
137
|
+
Setting `depth` to `0` or `false` turns off nesting,
|
|
138
|
+
so keys are never split into nested objects or arrays,
|
|
139
|
+
whether or not their brackets are percent-encoded:
|
|
140
|
+
|
|
141
|
+
```javascript
|
|
142
|
+
assert.deepEqual(qs.parse('a[b][c]=d', { depth: 0 }), { 'a[b][c]': 'd' });
|
|
143
|
+
assert.deepEqual(qs.parse('a%5Bb%5D=c', { depth: false }), { 'a[b]': 'c' });
|
|
144
|
+
```
|
|
145
|
+
|
|
135
146
|
You can configure **qs** to throw an error when parsing nested input beyond this depth using the `strictDepth` option (defaulted to false):
|
|
136
147
|
|
|
137
148
|
```javascript
|
|
@@ -143,16 +154,22 @@ try {
|
|
|
143
154
|
}
|
|
144
155
|
```
|
|
145
156
|
|
|
146
|
-
The depth limit helps mitigate abuse when **qs** is used to parse user input,
|
|
157
|
+
The depth limit helps mitigate abuse when **qs** is used to parse user input,
|
|
158
|
+
and it is recommended to keep it a reasonably small number.
|
|
159
|
+
The strictDepth option adds a layer of protection by throwing an error when the limit is exceeded,
|
|
160
|
+
allowing you to catch and handle such cases.
|
|
147
161
|
|
|
148
|
-
For similar reasons, by default **qs** will only parse up to 1000 parameters.
|
|
162
|
+
For similar reasons, by default **qs** will only parse up to 1000 parameters.
|
|
163
|
+
This can be overridden by passing a `parameterLimit` option:
|
|
149
164
|
|
|
150
165
|
```javascript
|
|
151
166
|
var limited = qs.parse('a=b&c=d', { parameterLimit: 1 });
|
|
152
167
|
assert.deepEqual(limited, { a: 'b' });
|
|
153
168
|
```
|
|
154
169
|
|
|
155
|
-
If you want an error to be thrown whenever a limit is exceeded (eg, `parameterLimit`, `arrayLimit`),
|
|
170
|
+
If you want an error to be thrown whenever a limit is exceeded (eg, `parameterLimit`, `arrayLimit`),
|
|
171
|
+
set the `throwOnLimitExceeded` option to `true`.
|
|
172
|
+
This option will generate a descriptive error if the query string exceeds a configured limit.
|
|
156
173
|
```javascript
|
|
157
174
|
try {
|
|
158
175
|
qs.parse('a=1&b=2&c=3&d=4', { parameterLimit: 3, throwOnLimitExceeded: true });
|
|
@@ -164,7 +181,10 @@ try {
|
|
|
164
181
|
|
|
165
182
|
When `throwOnLimitExceeded` is set to `false` (default), **qs** will parse up to the specified `parameterLimit` and ignore the rest without throwing an error.
|
|
166
183
|
|
|
167
|
-
Note that `parameterLimit` only bounds the number of `&`-delimited parameters; it does not limit how many values a single parameter expands into.
|
|
184
|
+
Note that `parameterLimit` only bounds the number of `&`-delimited parameters; it does not limit how many values a single parameter expands into.
|
|
185
|
+
In particular, when `comma: true` is enabled, a single parameter's value is split on commas into arbitrarily many elements, which `parameterLimit` does not constrain.
|
|
186
|
+
Setting `throwOnLimitExceeded: true` (see `arrayLimit` below) makes **qs** reject a query string with more than `parameterLimit` parameters, one that uses an array index of `arrayLimit` or greater, or one that would produce any array longer than `arrayLimit`, including an array produced by comma splitting.
|
|
187
|
+
`arrayLimit` applies to each array separately, including each parameter's comma-split value, so the total number of values across all parameters can still reach `parameterLimit` times `arrayLimit`, which is 20,000 at the default limits; always bound the input size at the transport layer as well (e.g. an HTTP body-size limit).
|
|
168
188
|
|
|
169
189
|
To bypass the leading question mark, use `ignoreQueryPrefix`:
|
|
170
190
|
|
|
@@ -324,7 +344,8 @@ var withArrayLimit = qs.parse('a[1]=b', { arrayLimit: 0 });
|
|
|
324
344
|
assert.deepEqual(withArrayLimit, { a: { '1': 'b' } });
|
|
325
345
|
```
|
|
326
346
|
|
|
327
|
-
If you want to throw an error whenever the array limit is exceeded, set the `throwOnLimitExceeded` option to `true`.
|
|
347
|
+
If you want to throw an error whenever the array limit is exceeded, set the `throwOnLimitExceeded` option to `true`.
|
|
348
|
+
This option will generate a descriptive error if the query string exceeds a configured limit.
|
|
328
349
|
```javascript
|
|
329
350
|
try {
|
|
330
351
|
qs.parse('a[1]=b', { arrayLimit: 0, throwOnLimitExceeded: true });
|
|
@@ -336,7 +357,11 @@ try {
|
|
|
336
357
|
|
|
337
358
|
When `throwOnLimitExceeded` is set to `false` (default), **qs** will parse up to the specified `arrayLimit` and if the limit is exceeded, the array will instead be converted to an object with the index as the key.
|
|
338
359
|
|
|
339
|
-
Note that `arrayLimit` is a *representation* threshold that controls when a numerically-indexed collection switches from an array to an object; it is **not** a hard cap on the total number of elements parsed.
|
|
360
|
+
Note that `arrayLimit` is a *representation* threshold that controls when a numerically-indexed collection switches from an array to an object; it is **not** a hard cap on the total number of elements parsed.
|
|
361
|
+
With the default `throwOnLimitExceeded: false`, exceeding `arrayLimit` never rejects or truncates input; it only changes the container type, and the resulting object still holds every element (so its size stays proportional to the input).
|
|
362
|
+
This conversion is itself a safeguard: it avoids allocating a huge sparse array for input like `a[999999999]`.
|
|
363
|
+
If you need a hard limit that rejects oversized arrays in untrusted query strings, set `throwOnLimitExceeded: true`.
|
|
364
|
+
`throwOnLimitExceeded` still limits each array separately, not the total: with `comma: true`, each comma-separated group under `a[]=` counts as one element of the outer array, and can itself hold up to `arrayLimit` elements.
|
|
340
365
|
|
|
341
366
|
To prevent array syntax (`a[]`, `a[0]`) from being parsed as arrays, set `parseArrays` to `false`.
|
|
342
367
|
Note that duplicate keys (e.g. `a=b&a=c`) may still produce arrays when `duplicates` is `'combine'` (the default).
|
|
@@ -408,7 +433,8 @@ If you wish to auto-convert values which look like numbers, booleans, and other
|
|
|
408
433
|
qs.stringify(object, [options]);
|
|
409
434
|
```
|
|
410
435
|
|
|
411
|
-
When stringifying, **qs** by default URI encodes output.
|
|
436
|
+
When stringifying, **qs** by default URI encodes output.
|
|
437
|
+
Objects are stringified as you would expect:
|
|
412
438
|
|
|
413
439
|
```javascript
|
|
414
440
|
assert.equal(qs.stringify({ a: 'b' }), 'a=b');
|
|
@@ -477,6 +503,20 @@ var encoded = qs.stringify({ a: { b: 'c' } }, { encoder: function (str, defaultE
|
|
|
477
503
|
}})
|
|
478
504
|
```
|
|
479
505
|
|
|
506
|
+
The encoder also receives the `format` option as a fifth argument.
|
|
507
|
+
An encoder that wraps `defaultEncoder` should pass all of its arguments through,
|
|
508
|
+
since the default encoding depends on `format` (for example, RFC1738 leaves parentheses unencoded):
|
|
509
|
+
|
|
510
|
+
```javascript
|
|
511
|
+
var wrapped = qs.stringify({ a: 'b(c)' }, {
|
|
512
|
+
format: 'RFC1738',
|
|
513
|
+
encoder: function (str, defaultEncoder, charset, type, format) {
|
|
514
|
+
return defaultEncoder(str, defaultEncoder, charset, type, format);
|
|
515
|
+
}
|
|
516
|
+
});
|
|
517
|
+
assert.equal(wrapped, 'a=b(c)');
|
|
518
|
+
```
|
|
519
|
+
|
|
480
520
|
The type argument is also provided to the decoder:
|
|
481
521
|
|
|
482
522
|
```javascript
|
|
@@ -690,7 +730,8 @@ var equalsInsensitive = qs.parse('a&b=');
|
|
|
690
730
|
assert.deepEqual(equalsInsensitive, { a: '', b: '' });
|
|
691
731
|
```
|
|
692
732
|
|
|
693
|
-
To distinguish between `null` values and empty strings use the `strictNullHandling` flag.
|
|
733
|
+
To distinguish between `null` values and empty strings use the `strictNullHandling` flag.
|
|
734
|
+
In the result string the `null`
|
|
694
735
|
values have no `=` sign:
|
|
695
736
|
|
|
696
737
|
```javascript
|
|
@@ -758,7 +799,8 @@ var obj = qs.parse('a=%82%B1%82%F1%82%C9%82%BF%82%CD%81I', { decoder: decoder })
|
|
|
758
799
|
assert.deepEqual(obj, { a: 'こんにちは!' });
|
|
759
800
|
```
|
|
760
801
|
|
|
761
|
-
|
|
802
|
+
<a name="rfc-3986-and-rfc-1738-space-encoding"></a>
|
|
803
|
+
### Encoding formats: RFC 3986, RFC 1738, and WHATWG
|
|
762
804
|
|
|
763
805
|
RFC3986 used as default option and encodes ' ' to *%20* which is backward compatible.
|
|
764
806
|
In the same time, output can be stringified as per RFC1738 with ' ' equal to '+'.
|
|
@@ -769,6 +811,17 @@ assert.equal(qs.stringify({ a: 'b c' }, { format : 'RFC3986' }), 'a=b%20c');
|
|
|
769
811
|
assert.equal(qs.stringify({ a: 'b c' }, { format : 'RFC1738' }), 'a=b+c');
|
|
770
812
|
```
|
|
771
813
|
|
|
814
|
+
To percent-encode keys and values the same way as the [WHATWG `application/x-www-form-urlencoded` serializer](https://url.spec.whatwg.org/#concept-urlencoded-serializer) (what `URLSearchParams` and HTML form submission use), use the `WHATWG` format.
|
|
815
|
+
Like RFC1738 it encodes ' ' as '+'; it also leaves `*` unencoded, but percent-encodes `~`, `(`, and `)`.
|
|
816
|
+
It only affects encoding; how `null`, dates, arrays, and objects are serialized is unchanged:
|
|
817
|
+
|
|
818
|
+
```javascript
|
|
819
|
+
assert.equal(qs.stringify({ a: 'b c~*()' }, { format: 'WHATWG' }), 'a=b+c%7E*%28%29');
|
|
820
|
+
```
|
|
821
|
+
|
|
822
|
+
_(Note: the `WHATWG` format matches `URLSearchParams` encoding only with the default `utf-8` charset, and only when keys are encoded too, so not with `encodeValuesOnly`.
|
|
823
|
+
With `charset: 'iso-8859-1'`, every format uses the same `escape`-based encoding, which leaves characters like `@` and `/` unencoded; only the space handling differs)_
|
|
824
|
+
|
|
772
825
|
## Security
|
|
773
826
|
|
|
774
827
|
Please email [@ljharb](https://github.com/ljharb) or see https://tidelift.com/security if you have a potential security vulnerability to report.
|