/
matchRequestUrl.ts
73 lines (65 loc) · 2.07 KB
/
matchRequestUrl.ts
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
import { match } from 'path-to-regexp'
import { getCleanUrl } from '@mswjs/interceptors/lib/utils/getCleanUrl.js'
import { normalizePath } from './normalizePath'
export type Path = string | RegExp
export type PathParams<KeyType extends keyof any = string> = {
[ParamName in KeyType]: string | ReadonlyArray<string>
}
export interface Match {
matches: boolean
params?: PathParams
}
/**
* Coerce a path supported by MSW into a path
* supported by "path-to-regexp".
*/
export function coercePath(path: string): string {
return (
path
/**
* Replace wildcards ("*") with unnamed capturing groups
* because "path-to-regexp" doesn't support wildcards.
* Ignore path parameter' modifiers (i.e. ":name*").
*/
.replace(
/([:a-zA-Z_-]*)(\*{1,2})+/g,
(_, parameterName: string | undefined, wildcard: string) => {
const expression = '(.*)'
if (!parameterName) {
return expression
}
return parameterName.startsWith(':')
? `${parameterName}${wildcard}`
: `${parameterName}${expression}`
},
)
/**
* Escape the port so that "path-to-regexp" can match
* absolute URLs including port numbers.
*/
.replace(/([^\/])(:)(?=\d+)/, '$1\\$2')
/**
* Escape the protocol so that "path-to-regexp" could match
* absolute URL.
* @see https://github.com/pillarjs/path-to-regexp/issues/259
*/
.replace(/^([^\/]+)(:)(?=\/\/)/, '$1\\$2')
)
}
/**
* Returns the result of matching given request URL against a mask.
*/
export function matchRequestUrl(url: URL, path: Path, baseUrl?: string): Match {
const normalizedPath = normalizePath(path, baseUrl)
const cleanPath =
typeof normalizedPath === 'string'
? coercePath(normalizedPath)
: normalizedPath
const cleanUrl = getCleanUrl(url)
const result = match(cleanPath, { decode: decodeURIComponent })(cleanUrl)
const params = (result && (result.params as PathParams)) || {}
return {
matches: result !== false,
params,
}
}