1 | # Path-to-RegExp
|
2 |
|
3 | > Turn a path string such as `/user/:name` into a regular expression.
|
4 |
|
5 | [![NPM version][npm-image]][npm-url]
|
6 | [![Build status][travis-image]][travis-url]
|
7 | [![Test coverage][coveralls-image]][coveralls-url]
|
8 | [![Dependency Status][david-image]][david-url]
|
9 | [![License][license-image]][license-url]
|
10 | [![Downloads][downloads-image]][downloads-url]
|
11 |
|
12 | ## Installation
|
13 |
|
14 | ```
|
15 | npm install path-to-regexp --save
|
16 | ```
|
17 |
|
18 | ## Usage
|
19 |
|
20 | ```javascript
|
21 | const {
|
22 | pathToRegexp,
|
23 | match,
|
24 | parse,
|
25 | compile,
|
26 | normalizePathname
|
27 | } = require("path-to-regexp");
|
28 |
|
29 | // pathToRegexp(path, keys?, options?)
|
30 | // match(path)
|
31 | // parse(path)
|
32 | // compile(path)
|
33 | // normalizePathname(path)
|
34 | ```
|
35 |
|
36 | - **path** A string, array of strings, or a regular expression.
|
37 | - **keys** An array to populate with keys found in the path.
|
38 | - **options**
|
39 | - **sensitive** When `true` the regexp will be case sensitive. (default: `false`)
|
40 | - **strict** When `true` the regexp allows an optional trailing delimiter to match. (default: `false`)
|
41 | - **end** When `true` the regexp will match to the end of the string. (default: `true`)
|
42 | - **start** When `true` the regexp will match from the beginning of the string. (default: `true`)
|
43 | - **delimiter** The default delimiter for segments. (default: `'/'`)
|
44 | - **endsWith** Optional character, or list of characters, to treat as "end" characters.
|
45 | - **whitelist** List of characters to consider delimiters when parsing. (default: `undefined`, any character)
|
46 |
|
47 | ```javascript
|
48 | const keys = [];
|
49 | const regexp = pathToRegexp("/foo/:bar", keys);
|
50 | // regexp = /^\/foo\/([^\/]+?)\/?$/i
|
51 | // keys = [{ name: 'bar', prefix: '/', delimiter: '/', optional: false, repeat: false, pattern: '[^\\/]+?' }]
|
52 | ```
|
53 |
|
54 | **Please note:** The `RegExp` returned by `path-to-regexp` is intended for ordered data (e.g. pathnames, hostnames). It can not handle arbitrarily ordered data (e.g. query strings, URL fragments, JSON, etc).
|
55 |
|
56 | ### Parameters
|
57 |
|
58 | The path argument is used to define parameters and populate the list of keys.
|
59 |
|
60 | #### Named Parameters
|
61 |
|
62 | Named parameters are defined by prefixing a colon to the parameter name (`:foo`). By default, the parameter will match until the next prefix (e.g. `[^/]+`).
|
63 |
|
64 | ```js
|
65 | const regexp = pathToRegexp("/:foo/:bar");
|
66 | // keys = [{ name: 'foo', prefix: '/', ... }, { name: 'bar', prefix: '/', ... }]
|
67 |
|
68 | regexp.exec("/test/route");
|
69 | //=> [ '/test/route', 'test', 'route', index: 0, input: '/test/route', groups: undefined ]
|
70 | ```
|
71 |
|
72 | **Please note:** Parameter names must use "word characters" (`[A-Za-z0-9_]`).
|
73 |
|
74 | #### Parameter Modifiers
|
75 |
|
76 | ##### Optional
|
77 |
|
78 | Parameters can be suffixed with a question mark (`?`) to make the parameter optional.
|
79 |
|
80 | ```js
|
81 | const regexp = pathToRegexp("/:foo/:bar?");
|
82 | // keys = [{ name: 'foo', ... }, { name: 'bar', delimiter: '/', optional: true, repeat: false }]
|
83 |
|
84 | regexp.exec("/test");
|
85 | //=> [ '/test', 'test', undefined, index: 0, input: '/test', groups: undefined ]
|
86 |
|
87 | regexp.exec("/test/route");
|
88 | //=> [ '/test/route', 'test', 'route', index: 0, input: '/test/route', groups: undefined ]
|
89 | ```
|
90 |
|
91 | **Tip:** The prefix is also optional, escape the prefix `\/` to make it required.
|
92 |
|
93 | ##### Zero or more
|
94 |
|
95 | Parameters can be suffixed with an asterisk (`*`) to denote a zero or more parameter matches. The prefix is used for each match.
|
96 |
|
97 | ```js
|
98 | const regexp = pathToRegexp("/:foo*");
|
99 | // keys = [{ name: 'foo', delimiter: '/', optional: true, repeat: true }]
|
100 |
|
101 | regexp.exec("/");
|
102 | //=> [ '/', undefined, index: 0, input: '/', groups: undefined ]
|
103 |
|
104 | regexp.exec("/bar/baz");
|
105 | //=> [ '/bar/baz', 'bar/baz', index: 0, input: '/bar/baz', groups: undefined ]
|
106 | ```
|
107 |
|
108 | ##### One or more
|
109 |
|
110 | Parameters can be suffixed with a plus sign (`+`) to denote a one or more parameter matches. The prefix is used for each match.
|
111 |
|
112 | ```js
|
113 | const regexp = pathToRegexp("/:foo+");
|
114 | // keys = [{ name: 'foo', delimiter: '/', optional: false, repeat: true }]
|
115 |
|
116 | regexp.exec("/");
|
117 | //=> null
|
118 |
|
119 | regexp.exec("/bar/baz");
|
120 | //=> [ '/bar/baz','bar/baz', index: 0, input: '/bar/baz', groups: undefined ]
|
121 | ```
|
122 |
|
123 | #### Unnamed Parameters
|
124 |
|
125 | It is possible to write an unnamed parameter that only consists of a matching group. It works the same as a named parameter, except it will be numerically indexed.
|
126 |
|
127 | ```js
|
128 | const regexp = pathToRegexp("/:foo/(.*)");
|
129 | // keys = [{ name: 'foo', ... }, { name: 0, ... }]
|
130 |
|
131 | regexp.exec("/test/route");
|
132 | //=> [ '/test/route', 'test', 'route', index: 0, input: '/test/route', groups: undefined ]
|
133 | ```
|
134 |
|
135 | #### Custom Matching Parameters
|
136 |
|
137 | All parameters can have a custom regexp, which overrides the default match (`[^/]+`). For example, you can match digits or names in a path:
|
138 |
|
139 | ```js
|
140 | const regexpNumbers = pathToRegexp("/icon-:foo(\\d+).png");
|
141 | // keys = [{ name: 'foo', ... }]
|
142 |
|
143 | regexpNumbers.exec("/icon-123.png");
|
144 | //=> ['/icon-123.png', '123']
|
145 |
|
146 | regexpNumbers.exec("/icon-abc.png");
|
147 | //=> null
|
148 |
|
149 | const regexpWord = pathToRegexp("/(user|u)");
|
150 | // keys = [{ name: 0, ... }]
|
151 |
|
152 | regexpWord.exec("/u");
|
153 | //=> ['/u', 'u']
|
154 |
|
155 | regexpWord.exec("/users");
|
156 | //=> null
|
157 | ```
|
158 |
|
159 | **Tip:** Backslashes need to be escaped with another backslash in JavaScript strings.
|
160 |
|
161 | ### Match
|
162 |
|
163 | The `match` function will return a function for transforming paths into parameters:
|
164 |
|
165 | ```js
|
166 | const match = match("/user/:id");
|
167 |
|
168 | match("/user/123"); //=> { path: '/user/123', index: 0, params: { id: '123' } }
|
169 | match("/invalid"); //=> false
|
170 | ```
|
171 |
|
172 | ### Normalize Pathname
|
173 |
|
174 | The `normalizePathname` function will return a normalized string for matching with `pathToRegexp`.
|
175 |
|
176 | ```js
|
177 | const re = pathToRegexp("/caf\u00E9");
|
178 | const input = encodeURI("/cafe\u0301");
|
179 |
|
180 | re.test(input); //=> false
|
181 | re.test(normalizePathname(input)); //=> true
|
182 | ```
|
183 |
|
184 | ### Parse
|
185 |
|
186 | The `parse` function will return a list of strings and keys from a path string:
|
187 |
|
188 | ```js
|
189 | const tokens = parse("/route/:foo/(.*)");
|
190 |
|
191 | console.log(tokens[0]);
|
192 | //=> "/route"
|
193 |
|
194 | console.log(tokens[1]);
|
195 | //=> { name: 'foo', prefix: '/', delimiter: '/', optional: false, repeat: false, pattern: '[^\\/]+?' }
|
196 |
|
197 | console.log(tokens[2]);
|
198 | //=> { name: 0, prefix: '/', delimiter: '/', optional: false, repeat: false, pattern: '.*' }
|
199 | ```
|
200 |
|
201 | **Note:** This method only works with strings.
|
202 |
|
203 | ### Compile ("Reverse" Path-To-RegExp)
|
204 |
|
205 | The `compile` function will return a function for transforming parameters into a valid path:
|
206 |
|
207 | ```js
|
208 | const toPath = compile("/user/:id");
|
209 |
|
210 | toPath({ id: 123 }); //=> "/user/123"
|
211 | toPath({ id: "café" }); //=> "/user/caf%C3%A9"
|
212 | toPath({ id: "/" }); //=> "/user/%2F"
|
213 |
|
214 | toPath({ id: ":/" }); //=> "/user/%3A%2F"
|
215 | toPath({ id: ":/" }, { encode: (value, token) => value, validate: false }); //=> "/user/:/"
|
216 |
|
217 | const toPathRepeated = compile("/:segment+");
|
218 |
|
219 | toPathRepeated({ segment: "foo" }); //=> "/foo"
|
220 | toPathRepeated({ segment: ["a", "b", "c"] }); //=> "/a/b/c"
|
221 |
|
222 | const toPathRegexp = compile("/user/:id(\\d+)");
|
223 |
|
224 | toPathRegexp({ id: 123 }); //=> "/user/123"
|
225 | toPathRegexp({ id: "123" }); //=> "/user/123"
|
226 | toPathRegexp({ id: "abc" }); //=> Throws `TypeError`.
|
227 | toPathRegexp({ id: "abc" }, { validate: false }); //=> "/user/abc"
|
228 | ```
|
229 |
|
230 | **Note:** The generated function will throw on invalid input. It will do all necessary checks to ensure the generated path is valid. This method only works with strings.
|
231 |
|
232 | ### Working with Tokens
|
233 |
|
234 | Path-To-RegExp exposes the two functions used internally that accept an array of tokens.
|
235 |
|
236 | - `tokensToRegexp(tokens, keys?, options?)` Transform an array of tokens into a matching regular expression.
|
237 | - `tokensToFunction(tokens)` Transform an array of tokens into a path generator function.
|
238 |
|
239 | #### Token Information
|
240 |
|
241 | - `name` The name of the token (`string` for named or `number` for unnamed index)
|
242 | - `prefix` The prefix character for the segment (e.g. `/`)
|
243 | - `delimiter` The delimiter for the segment (same as prefix or default delimiter)
|
244 | - `optional` Indicates the token is optional (`boolean`)
|
245 | - `repeat` Indicates the token is repeated (`boolean`)
|
246 | - `pattern` The RegExp used to match this token (`string`)
|
247 |
|
248 | ## Compatibility with Express <= 4.x
|
249 |
|
250 | Path-To-RegExp breaks compatibility with Express <= `4.x`:
|
251 |
|
252 | - RegExp special characters can only be used in a parameter
|
253 | - Express.js 4.x supported `RegExp` special characters regardless of position - this is considered a bug
|
254 | - Parameters have suffixes that augment meaning - `*`, `+` and `?`. E.g. `/:user*`
|
255 | - No wildcard asterisk (`*`) - use parameters instead (`(.*)` or `:splat*`)
|
256 |
|
257 | ## Live Demo
|
258 |
|
259 | You can see a live demo of this library in use at [express-route-tester](http://forbeslindesay.github.com/express-route-tester/).
|
260 |
|
261 | ## License
|
262 |
|
263 | MIT
|
264 |
|
265 | [npm-image]: https://img.shields.io/npm/v/path-to-regexp.svg?style=flat
|
266 | [npm-url]: https://npmjs.org/package/path-to-regexp
|
267 | [travis-image]: https://img.shields.io/travis/pillarjs/path-to-regexp.svg?style=flat
|
268 | [travis-url]: https://travis-ci.org/pillarjs/path-to-regexp
|
269 | [coveralls-image]: https://img.shields.io/coveralls/pillarjs/path-to-regexp.svg?style=flat
|
270 | [coveralls-url]: https://coveralls.io/r/pillarjs/path-to-regexp?branch=master
|
271 | [david-image]: http://img.shields.io/david/pillarjs/path-to-regexp.svg?style=flat
|
272 | [david-url]: https://david-dm.org/pillarjs/path-to-regexp
|
273 | [license-image]: http://img.shields.io/npm/l/path-to-regexp.svg?style=flat
|
274 | [license-url]: LICENSE.md
|
275 | [downloads-image]: http://img.shields.io/npm/dm/path-to-regexp.svg?style=flat
|
276 | [downloads-url]: https://npmjs.org/package/path-to-regexp
|
277 |
|
\ | No newline at end of file |