Skip to content

Commit f73ec6c

Browse files
committed
Adds strict mode, redos script, improved separator and delimiter
1 parent eaed1fc commit f73ec6c

File tree

7 files changed

+3527
-3013
lines changed

7 files changed

+3527
-3013
lines changed

Readme.md

+4-3
Original file line numberDiff line numberDiff line change
@@ -32,12 +32,12 @@ The `pathToRegexp` function returns a regular expression with `keys` as a proper
3232
- **path** A string.
3333
- **options** _(optional)_
3434
- **sensitive** Regexp will be case sensitive. (default: `false`)
35-
- **trailing** Regexp allows an optional trailing delimiter to match. (default: `true`)
35+
- **trailing** Allows optional trailing delimiter to match. (default: `true`)
3636
- **end** Match to the end of the string. (default: `true`)
3737
- **start** Match from the beginning of the string. (default: `true`)
38-
- **loose** Allow the delimiter to be repeated an arbitrary number of times. (default: `true`)
38+
- **loose** Allow the delimiter to be arbitrarily repeated, e.g. `/` or `///`. (default: `true`)
3939
- **delimiter** The default delimiter for segments, e.g. `[^/]` for `:named` parameters. (default: `'/'`)
40-
- **encodePath** A function to encode strings before inserting into `RegExp`. (default: `x => x`, recommended: [`encodeurl`](https://github.com/pillarjs/encodeurl))
40+
- **encodePath** A function for encoding input strings. (default: `x => x`, recommended: [`encodeurl`](https://github.com/pillarjs/encodeurl) for unicode encoding)
4141

4242
```js
4343
const regexp = pathToRegexp("/foo/:bar");
@@ -247,6 +247,7 @@ toPathRegexp({ id: "123" }); //=> "/user/123"
247247
- If you are rewriting paths with match and compiler, consider using `encode: false` and `decode: false` to keep raw paths passed around.
248248
- To ensure matches work on paths containing characters usually encoded, consider using [encodeurl](https://github.com/pillarjs/encodeurl) for `encodePath`.
249249
- If matches are intended to be exact, you need to set `loose: false`, `trailing: false`, and `sensitive: true`.
250+
- Enable `strict: true` to detect ReDOS issues.
250251

251252
### Parse
252253

package-lock.json

+109-7
Some generated files are not rendered by default. Learn more about customizing how changed files appear on GitHub.

package.json

+2-1
Original file line numberDiff line numberDiff line change
@@ -34,8 +34,9 @@
3434
"@types/node": "^20.4.9",
3535
"@types/semver": "^7.3.1",
3636
"@vitest/coverage-v8": "^1.4.0",
37+
"recheck": "^4.4.5",
3738
"size-limit": "^11.1.2",
38-
"typescript": "^5.1.6"
39+
"typescript": "^5.5.3"
3940
},
4041
"engines": {
4142
"node": ">=16"

scripts/redos.ts

+36
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,36 @@
1+
import { checkSync } from "recheck";
2+
import { pathToRegexp } from "../src/index.js";
3+
4+
const TESTS = [
5+
"/abc{abc:foo}?",
6+
"/:foo{abc:foo}?",
7+
"{:attr1}?{:attr2/}?",
8+
"{:attr1/}?{:attr2/}?",
9+
"{:foo.}?{:bar.}?",
10+
"{:foo([^\\.]+).}?{:bar.}?",
11+
":foo(a+):bar(b+)",
12+
];
13+
14+
for (const path of TESTS) {
15+
try {
16+
const re = pathToRegexp(path, { strict: true });
17+
const result = checkSync(re.source, re.flags);
18+
if (result.status === "safe") {
19+
console.log("Safe:", path, String(re));
20+
} else {
21+
console.log("Fail:", path, String(re));
22+
}
23+
} catch (err) {
24+
try {
25+
const re = pathToRegexp(path);
26+
const result = checkSync(re.source, re.flags);
27+
if (result.status === "safe") {
28+
console.log("Invalid:", path, String(re));
29+
} else {
30+
console.log("Pass:", path, String(re));
31+
}
32+
} catch (err) {
33+
console.log("Error:", path, err.message);
34+
}
35+
}
36+
}

0 commit comments

Comments
 (0)