Skip to content

Commit 6f24d7e

Browse files
abhu85jonchurch
andauthored
fix: correct off-by-one error in parameterCount (#716)
* fix: correct off-by-one error in parameterCount The `parameterCount` function was counting `&` characters but returning that count directly. Since the number of parameters equals the number of `&` characters plus one, this caused an off-by-one error. For example, with `a[0]=1&a[1]=2&...&a[199]=200` (200 parameters): - Before: returned 199 (number of `&` chars) - After: returns 200 (actual parameter count) This bug became visible with qs@6.14.2 which changed `arrayLimit` to restrict array length instead of max index. With the buggy count, large arrays would be converted to objects instead of arrays. - Fix `parameterCount` to return the actual count of parameters Fixes #715 * deps(qs): bump to ~6.14.2 * refactor: use 2.x do/while loop for parameterCount The previous while loop counted '&' separators, so the return value was (parameter count - 1). That happened to work because old qs treated `arrayLimit` as a max-index rather than max-length. The limit check itself was always correct, only the return value was off relative to the function's name. Rather than patch with `+1`, port the 2.x version where `count` directly represents parameter count. The do/while runs once unconditionally for the first parameter (before any '&'), then increments per '&' found. do/while is safe because the caller at line 74 guards empty bodies (`body.length ? queryparse(body) : {}`). If that guard were removed, this would incorrectly return 1 for empty input. Simple parser is unaffected, it only checks for `undefined` and discards the count. Only the extended parser consumed the value, as input to qs's `arrayLimit`. * docs: update HISTORY.md --------- Co-authored-by: Jon Church <me@jonchurch.com>
1 parent b849bd5 commit 6f24d7e

3 files changed

Lines changed: 8 additions & 7 deletions

File tree

HISTORY.md

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,8 @@
11
Unreleased
22
===================
33
* refactor(json): simplify strict mode error string construction
4+
* fix: extended urlencoded parsing of arrays with >100 elements (#716)
5+
* deps: qs@~6.14.2
46

57
1.20.4 / 2025-12-01
68
===================

lib/types/urlencoded.js

Lines changed: 5 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -206,16 +206,15 @@ function getCharset (req) {
206206

207207
function parameterCount (body, limit) {
208208
var count = 0
209-
var index = 0
209+
var index = -1
210210

211-
while ((index = body.indexOf('&', index)) !== -1) {
211+
do {
212212
count++
213-
index++
214-
215-
if (count === limit) {
213+
if (count > limit) {
216214
return undefined
217215
}
218-
}
216+
index = body.indexOf('&', index + 1)
217+
} while (index !== -1)
219218

220219
return count
221220
}

package.json

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -17,7 +17,7 @@
1717
"http-errors": "~2.0.1",
1818
"iconv-lite": "~0.4.24",
1919
"on-finished": "~2.4.1",
20-
"qs": "~6.14.1",
20+
"qs": "~6.14.2",
2121
"raw-body": "~2.5.3",
2222
"type-is": "~1.6.18",
2323
"unpipe": "~1.0.0"

0 commit comments

Comments
 (0)