@thi.ng/router 4.0.5 → 4.0.7
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 +1 -1
- package/README.md +8 -8
- package/package.json +6 -6
- package/basic.d.ts +0 -46
- package/basic.js +0 -233
- package/history.d.ts +0 -31
- package/history.js +0 -91
package/CHANGELOG.md
CHANGED
package/README.md
CHANGED
|
@@ -7,7 +7,7 @@
|
|
|
7
7
|
[](https://mastodon.thi.ng/@toxi)
|
|
8
8
|
|
|
9
9
|
> [!NOTE]
|
|
10
|
-
> This is one of
|
|
10
|
+
> This is one of 192 standalone projects, maintained as part
|
|
11
11
|
> of the [@thi.ng/umbrella](https://github.com/thi-ng/umbrella/) monorepo
|
|
12
12
|
> and anti-framework.
|
|
13
13
|
>
|
|
@@ -57,7 +57,13 @@ Generic trie-based router with support for wildcards, route param validation/coe
|
|
|
57
57
|
yarn add @thi.ng/router
|
|
58
58
|
```
|
|
59
59
|
|
|
60
|
-
|
|
60
|
+
ESM import:
|
|
61
|
+
|
|
62
|
+
```ts
|
|
63
|
+
import * as rou from "@thi.ng/router";
|
|
64
|
+
```
|
|
65
|
+
|
|
66
|
+
Browser ESM import:
|
|
61
67
|
|
|
62
68
|
```html
|
|
63
69
|
<script type="module" src="https://cdn.skypack.dev/@thi.ng/router"></script>
|
|
@@ -65,12 +71,6 @@ ES module import:
|
|
|
65
71
|
|
|
66
72
|
[Skypack documentation](https://docs.skypack.dev/)
|
|
67
73
|
|
|
68
|
-
For Node.js REPL:
|
|
69
|
-
|
|
70
|
-
```js
|
|
71
|
-
const router = await import("@thi.ng/router");
|
|
72
|
-
```
|
|
73
|
-
|
|
74
74
|
Package sizes (brotli'd, pre-treeshake): ESM: 1.94 KB
|
|
75
75
|
|
|
76
76
|
## Dependencies
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@thi.ng/router",
|
|
3
|
-
"version": "4.0.
|
|
3
|
+
"version": "4.0.7",
|
|
4
4
|
"description": "Generic trie-based router with support for wildcards, route param validation/coercion, auth",
|
|
5
5
|
"type": "module",
|
|
6
6
|
"module": "./index.js",
|
|
@@ -36,10 +36,10 @@
|
|
|
36
36
|
"tool:tangle": "../../node_modules/.bin/tangle src/**/*.ts"
|
|
37
37
|
},
|
|
38
38
|
"dependencies": {
|
|
39
|
-
"@thi.ng/api": "^8.
|
|
40
|
-
"@thi.ng/checks": "^3.
|
|
41
|
-
"@thi.ng/equiv": "^2.1.
|
|
42
|
-
"@thi.ng/errors": "^2.5.
|
|
39
|
+
"@thi.ng/api": "^8.10.1",
|
|
40
|
+
"@thi.ng/checks": "^3.6.1",
|
|
41
|
+
"@thi.ng/equiv": "^2.1.55",
|
|
42
|
+
"@thi.ng/errors": "^2.5.4",
|
|
43
43
|
"tslib": "^2.6.2"
|
|
44
44
|
},
|
|
45
45
|
"devDependencies": {
|
|
@@ -98,5 +98,5 @@
|
|
|
98
98
|
],
|
|
99
99
|
"year": 2014
|
|
100
100
|
},
|
|
101
|
-
"gitHead": "
|
|
101
|
+
"gitHead": "18a0c063a7b33d790e5bc2486c106f45f663ac28\n"
|
|
102
102
|
}
|
package/basic.d.ts
DELETED
|
@@ -1,46 +0,0 @@
|
|
|
1
|
-
import type { Event, INotify, IObjectOf, Listener, SomeRequired } from "@thi.ng/api";
|
|
2
|
-
import { type AugmentedRoute, type Route, type RouteMatch, type RouteParamValidator, type RouterEventType, type RouterOpts } from "./api.js";
|
|
3
|
-
import { Trie } from "./trie.js";
|
|
4
|
-
export declare class BasicRouter<T = any> implements INotify<RouterEventType> {
|
|
5
|
-
opts: RouterOpts<T>;
|
|
6
|
-
current: RouteMatch | undefined;
|
|
7
|
-
protected index: Record<string, AugmentedRoute>;
|
|
8
|
-
protected routes: Trie<AugmentedRoute>;
|
|
9
|
-
constructor(config: RouterOpts<T>);
|
|
10
|
-
addListener(id: RouterEventType, fn: Listener<RouterEventType>, scope?: any): boolean;
|
|
11
|
-
removeListener(id: RouterEventType, fn: Listener<RouterEventType>, scope?: any): boolean;
|
|
12
|
-
notify(event: Event<RouterEventType>): boolean;
|
|
13
|
-
start(): void;
|
|
14
|
-
addRoutes(routes: Route[]): void;
|
|
15
|
-
/**
|
|
16
|
-
* Main router function. Attempts to match given input string against all
|
|
17
|
-
* configured routes. Before returning, triggers {@link EVENT_ROUTE_CHANGED}
|
|
18
|
-
* with return value as well. If none of the routes matches, emits
|
|
19
|
-
* {@link EVENT_ROUTE_FAILED} and then falls back to configured default
|
|
20
|
-
* route.
|
|
21
|
-
*
|
|
22
|
-
* @remarks
|
|
23
|
-
* See {@link RouteAuthenticator} for details about `ctx` handling.
|
|
24
|
-
*
|
|
25
|
-
* @param src - route path to match
|
|
26
|
-
* @param ctx - arbitrary user context
|
|
27
|
-
*/
|
|
28
|
-
route(src: string, ctx?: T): RouteMatch | undefined;
|
|
29
|
-
/**
|
|
30
|
-
* Returns a formatted version of given {@link RouteMatch}, incl. any
|
|
31
|
-
* params, or alternatively a registered route ID (and optional route
|
|
32
|
-
* params). Throws an error if an invalid route `id` is provided.
|
|
33
|
-
*
|
|
34
|
-
* @param id -
|
|
35
|
-
* @param params -
|
|
36
|
-
* @param rest -
|
|
37
|
-
*/
|
|
38
|
-
format(id: string, params?: any, rest?: string[]): string;
|
|
39
|
-
format(match: SomeRequired<RouteMatch, "id">): string;
|
|
40
|
-
routeForID(id: string): AugmentedRoute | undefined;
|
|
41
|
-
protected augmentRoute(route: Route): AugmentedRoute;
|
|
42
|
-
protected matchRoutes(src: string, ctx?: T): RouteMatch | undefined;
|
|
43
|
-
protected validateRouteParams(params: any, validators: IObjectOf<Partial<RouteParamValidator>>): boolean;
|
|
44
|
-
protected handleRouteFailure(): boolean;
|
|
45
|
-
}
|
|
46
|
-
//# sourceMappingURL=basic.d.ts.map
|
package/basic.js
DELETED
|
@@ -1,233 +0,0 @@
|
|
|
1
|
-
var __defProp = Object.defineProperty;
|
|
2
|
-
var __getOwnPropDesc = Object.getOwnPropertyDescriptor;
|
|
3
|
-
var __decorateClass = (decorators, target, key, kind) => {
|
|
4
|
-
var result = kind > 1 ? void 0 : kind ? __getOwnPropDesc(target, key) : target;
|
|
5
|
-
for (var i = decorators.length - 1, decorator; i >= 0; i--)
|
|
6
|
-
if (decorator = decorators[i])
|
|
7
|
-
result = (kind ? decorator(target, key, result) : decorator(result)) || result;
|
|
8
|
-
if (kind && result)
|
|
9
|
-
__defProp(target, key, result);
|
|
10
|
-
return result;
|
|
11
|
-
};
|
|
12
|
-
import { INotifyMixin } from "@thi.ng/api/mixins/inotify";
|
|
13
|
-
import { isString } from "@thi.ng/checks/is-string";
|
|
14
|
-
import { equiv } from "@thi.ng/equiv";
|
|
15
|
-
import { assert } from "@thi.ng/errors/assert";
|
|
16
|
-
import { illegalArgs } from "@thi.ng/errors/illegal-arguments";
|
|
17
|
-
import { illegalArity } from "@thi.ng/errors/illegal-arity";
|
|
18
|
-
import { illegalState } from "@thi.ng/errors/illegal-state";
|
|
19
|
-
import {
|
|
20
|
-
EVENT_ROUTE_CHANGED,
|
|
21
|
-
EVENT_ROUTE_FAILED
|
|
22
|
-
} from "./api.js";
|
|
23
|
-
import { Trie } from "./trie.js";
|
|
24
|
-
let BasicRouter = class {
|
|
25
|
-
opts;
|
|
26
|
-
current;
|
|
27
|
-
index = {};
|
|
28
|
-
routes = new Trie();
|
|
29
|
-
constructor(config) {
|
|
30
|
-
this.opts = {
|
|
31
|
-
authenticator: (match) => match,
|
|
32
|
-
prefix: "/",
|
|
33
|
-
separator: "/",
|
|
34
|
-
trim: true,
|
|
35
|
-
...config
|
|
36
|
-
};
|
|
37
|
-
this.addRoutes(this.opts.routes);
|
|
38
|
-
assert(
|
|
39
|
-
this.routeForID(this.opts.default) !== void 0,
|
|
40
|
-
`missing config for default route: '${this.opts.default}'`
|
|
41
|
-
);
|
|
42
|
-
if (config.initial) {
|
|
43
|
-
const route = this.routeForID(config.initial);
|
|
44
|
-
assert(
|
|
45
|
-
route !== void 0,
|
|
46
|
-
`missing config for initial route: ${this.opts.initial}`
|
|
47
|
-
);
|
|
48
|
-
assert(!route.params, "initial route MUST not be parametric");
|
|
49
|
-
}
|
|
50
|
-
}
|
|
51
|
-
// @ts-ignore: arguments
|
|
52
|
-
// prettier-ignore
|
|
53
|
-
addListener(id, fn, scope) {
|
|
54
|
-
}
|
|
55
|
-
// @ts-ignore: arguments
|
|
56
|
-
// prettier-ignore
|
|
57
|
-
removeListener(id, fn, scope) {
|
|
58
|
-
}
|
|
59
|
-
// @ts-ignore: arguments
|
|
60
|
-
notify(event) {
|
|
61
|
-
}
|
|
62
|
-
start() {
|
|
63
|
-
if (this.opts.initial) {
|
|
64
|
-
const route = this.routeForID(this.opts.initial);
|
|
65
|
-
this.current = { id: route.id, params: {} };
|
|
66
|
-
this.notify({ id: EVENT_ROUTE_CHANGED, value: this.current });
|
|
67
|
-
}
|
|
68
|
-
}
|
|
69
|
-
addRoutes(routes) {
|
|
70
|
-
for (let r of routes) {
|
|
71
|
-
try {
|
|
72
|
-
const route = this.augmentRoute(r);
|
|
73
|
-
this.routes.set(route.match, route);
|
|
74
|
-
this.index[route.id] = route;
|
|
75
|
-
} catch (e) {
|
|
76
|
-
illegalArgs(
|
|
77
|
-
`error in route "${r.id}": ${e.origMessage}`
|
|
78
|
-
);
|
|
79
|
-
}
|
|
80
|
-
}
|
|
81
|
-
}
|
|
82
|
-
/**
|
|
83
|
-
* Main router function. Attempts to match given input string against all
|
|
84
|
-
* configured routes. Before returning, triggers {@link EVENT_ROUTE_CHANGED}
|
|
85
|
-
* with return value as well. If none of the routes matches, emits
|
|
86
|
-
* {@link EVENT_ROUTE_FAILED} and then falls back to configured default
|
|
87
|
-
* route.
|
|
88
|
-
*
|
|
89
|
-
* @remarks
|
|
90
|
-
* See {@link RouteAuthenticator} for details about `ctx` handling.
|
|
91
|
-
*
|
|
92
|
-
* @param src - route path to match
|
|
93
|
-
* @param ctx - arbitrary user context
|
|
94
|
-
*/
|
|
95
|
-
route(src, ctx) {
|
|
96
|
-
if (this.opts.trim && src.charAt(src.length - 1) === this.opts.separator) {
|
|
97
|
-
src = src.substring(0, src.length - 1);
|
|
98
|
-
}
|
|
99
|
-
src = src.substring(this.opts.prefix.length);
|
|
100
|
-
let match = this.matchRoutes(src, ctx);
|
|
101
|
-
if (!match) {
|
|
102
|
-
this.notify({ id: EVENT_ROUTE_FAILED, value: src });
|
|
103
|
-
if (!this.handleRouteFailure()) {
|
|
104
|
-
return;
|
|
105
|
-
}
|
|
106
|
-
const route = this.routeForID(this.opts.default);
|
|
107
|
-
match = { id: route.id, redirect: true };
|
|
108
|
-
}
|
|
109
|
-
if (!equiv(match, this.current)) {
|
|
110
|
-
this.current = match;
|
|
111
|
-
this.notify({ id: EVENT_ROUTE_CHANGED, value: match });
|
|
112
|
-
}
|
|
113
|
-
return match;
|
|
114
|
-
}
|
|
115
|
-
format(...args) {
|
|
116
|
-
let [id, params, rest] = args;
|
|
117
|
-
let match;
|
|
118
|
-
switch (args.length) {
|
|
119
|
-
case 3:
|
|
120
|
-
match = { id, params, rest };
|
|
121
|
-
break;
|
|
122
|
-
case 2:
|
|
123
|
-
match = { id, params };
|
|
124
|
-
break;
|
|
125
|
-
case 1:
|
|
126
|
-
match = isString(id) ? { id } : id;
|
|
127
|
-
break;
|
|
128
|
-
default:
|
|
129
|
-
illegalArity(args.length);
|
|
130
|
-
}
|
|
131
|
-
const route = this.routeForID(match.id);
|
|
132
|
-
if (route) {
|
|
133
|
-
const params2 = match.params;
|
|
134
|
-
let parts = route.match.map((x) => {
|
|
135
|
-
if (isRouteParam(x)) {
|
|
136
|
-
const id2 = x.substring(1);
|
|
137
|
-
const p = params2?.[id2];
|
|
138
|
-
if (p == null) {
|
|
139
|
-
illegalArgs(`missing value for param '${id2}'`);
|
|
140
|
-
}
|
|
141
|
-
return p;
|
|
142
|
-
}
|
|
143
|
-
return x;
|
|
144
|
-
});
|
|
145
|
-
if (route.rest >= 0)
|
|
146
|
-
parts = parts.slice(0, route.rest).concat(match.rest || []);
|
|
147
|
-
return this.opts.prefix + parts.join(this.opts.separator);
|
|
148
|
-
} else {
|
|
149
|
-
illegalArgs(`invalid route ID: ${match.id}`);
|
|
150
|
-
}
|
|
151
|
-
}
|
|
152
|
-
routeForID(id) {
|
|
153
|
-
return this.index[id];
|
|
154
|
-
}
|
|
155
|
-
augmentRoute(route) {
|
|
156
|
-
const match = isString(route.match) ? route.match.split(this.opts.separator).filter((x) => !!x) : route.match;
|
|
157
|
-
const existing = this.routes.get(match);
|
|
158
|
-
if (existing) {
|
|
159
|
-
illegalArgs(
|
|
160
|
-
`duplicate route: ${match} (id: ${route.id}, conflicts with: ${existing.id})`
|
|
161
|
-
);
|
|
162
|
-
}
|
|
163
|
-
let hasParams = false;
|
|
164
|
-
const params = match.reduce((acc, x, i) => {
|
|
165
|
-
if (isRouteParam(x)) {
|
|
166
|
-
hasParams = true;
|
|
167
|
-
acc[i] = x.substring(1);
|
|
168
|
-
}
|
|
169
|
-
return acc;
|
|
170
|
-
}, {});
|
|
171
|
-
return {
|
|
172
|
-
...route,
|
|
173
|
-
match,
|
|
174
|
-
params: hasParams ? params : void 0,
|
|
175
|
-
rest: match.indexOf("+")
|
|
176
|
-
};
|
|
177
|
-
}
|
|
178
|
-
matchRoutes(src, ctx) {
|
|
179
|
-
const curr = src.split(this.opts.separator);
|
|
180
|
-
const route = this.routes.get(curr);
|
|
181
|
-
if (!route)
|
|
182
|
-
return;
|
|
183
|
-
let params;
|
|
184
|
-
if (route.params) {
|
|
185
|
-
params = Object.entries(route.params).reduce(
|
|
186
|
-
(acc, [i, k]) => (acc[k] = curr[+i], acc),
|
|
187
|
-
{}
|
|
188
|
-
);
|
|
189
|
-
}
|
|
190
|
-
if (route.validate && !this.validateRouteParams(params, route.validate)) {
|
|
191
|
-
return;
|
|
192
|
-
}
|
|
193
|
-
const rest = route.rest >= 0 ? curr.slice(route.rest) : void 0;
|
|
194
|
-
let match = {
|
|
195
|
-
id: route.id,
|
|
196
|
-
params,
|
|
197
|
-
rest
|
|
198
|
-
};
|
|
199
|
-
if (route.auth) {
|
|
200
|
-
match = this.opts.authenticator(match, route, ctx);
|
|
201
|
-
if (match && !this.index[match.id]) {
|
|
202
|
-
illegalState(
|
|
203
|
-
"auth handler returned invalid route ID: " + match.id
|
|
204
|
-
);
|
|
205
|
-
}
|
|
206
|
-
}
|
|
207
|
-
return match;
|
|
208
|
-
}
|
|
209
|
-
validateRouteParams(params, validators) {
|
|
210
|
-
for (let id in validators) {
|
|
211
|
-
if (params[id] !== void 0) {
|
|
212
|
-
const val = validators[id];
|
|
213
|
-
if (val.coerce) {
|
|
214
|
-
params[id] = val.coerce(params[id]);
|
|
215
|
-
}
|
|
216
|
-
if (val.check && !val.check(params[id])) {
|
|
217
|
-
return false;
|
|
218
|
-
}
|
|
219
|
-
}
|
|
220
|
-
}
|
|
221
|
-
return true;
|
|
222
|
-
}
|
|
223
|
-
handleRouteFailure() {
|
|
224
|
-
return true;
|
|
225
|
-
}
|
|
226
|
-
};
|
|
227
|
-
BasicRouter = __decorateClass([
|
|
228
|
-
INotifyMixin
|
|
229
|
-
], BasicRouter);
|
|
230
|
-
const isRouteParam = (x) => x[0] === "?";
|
|
231
|
-
export {
|
|
232
|
-
BasicRouter
|
|
233
|
-
};
|
package/history.d.ts
DELETED
|
@@ -1,31 +0,0 @@
|
|
|
1
|
-
import type { Fn } from "@thi.ng/api";
|
|
2
|
-
import type { HTMLRouterConfig } from "./api.js";
|
|
3
|
-
import { BasicRouter } from "./basic.js";
|
|
4
|
-
export declare class HTMLRouter<T = any> extends BasicRouter<T> {
|
|
5
|
-
protected currentPath: string;
|
|
6
|
-
protected popHandler: Fn<PopStateEvent, void>;
|
|
7
|
-
protected hashHandler: EventListener;
|
|
8
|
-
protected useFragment: boolean;
|
|
9
|
-
protected ignoreHashChange: boolean;
|
|
10
|
-
constructor(config: HTMLRouterConfig);
|
|
11
|
-
start(): void;
|
|
12
|
-
release(): void;
|
|
13
|
-
/**
|
|
14
|
-
* Like {@link BasicRouter.route}, but takes additional arg to control if
|
|
15
|
-
* this routing operation should manipulate the browser's `history`.
|
|
16
|
-
*
|
|
17
|
-
* @remarks
|
|
18
|
-
* If called from userland, this normally is true (also default). However,
|
|
19
|
-
* we want to avoid this if called from this router's own event handlers.
|
|
20
|
-
*
|
|
21
|
-
* @param src -
|
|
22
|
-
* @param ctx -
|
|
23
|
-
* @param pushState -
|
|
24
|
-
*/
|
|
25
|
-
route(src: string, ctx?: T, pushState?: boolean): import("./api.js").RouteMatch | undefined;
|
|
26
|
-
routeTo(route: string, ctx?: T): void;
|
|
27
|
-
protected handlePopChange(): Fn<PopStateEvent, void>;
|
|
28
|
-
protected handleHashChange(): EventListener;
|
|
29
|
-
protected handleRouteFailure(): boolean;
|
|
30
|
-
}
|
|
31
|
-
//# sourceMappingURL=history.d.ts.map
|
package/history.js
DELETED
|
@@ -1,91 +0,0 @@
|
|
|
1
|
-
import { equiv } from "@thi.ng/equiv";
|
|
2
|
-
import { BasicRouter } from "./basic.js";
|
|
3
|
-
class HTMLRouter extends BasicRouter {
|
|
4
|
-
currentPath;
|
|
5
|
-
popHandler;
|
|
6
|
-
hashHandler;
|
|
7
|
-
useFragment;
|
|
8
|
-
ignoreHashChange;
|
|
9
|
-
constructor(config) {
|
|
10
|
-
super({ prefix: config.useFragment ? "#/" : "/", ...config });
|
|
11
|
-
this.useFragment = config.useFragment !== false;
|
|
12
|
-
this.ignoreHashChange = false;
|
|
13
|
-
}
|
|
14
|
-
start() {
|
|
15
|
-
window.addEventListener("popstate", this.handlePopChange());
|
|
16
|
-
if (this.useFragment) {
|
|
17
|
-
window.addEventListener("hashchange", this.handleHashChange());
|
|
18
|
-
}
|
|
19
|
-
if (this.opts.initial) {
|
|
20
|
-
const route = this.routeForID(this.opts.initial);
|
|
21
|
-
this.route(this.format({ id: route.id }));
|
|
22
|
-
} else {
|
|
23
|
-
this.route(this.useFragment ? location.hash : location.pathname);
|
|
24
|
-
}
|
|
25
|
-
}
|
|
26
|
-
release() {
|
|
27
|
-
window.removeEventListener("popstate", this.popHandler);
|
|
28
|
-
if (this.useFragment) {
|
|
29
|
-
window.removeEventListener("hashchange", this.hashHandler);
|
|
30
|
-
}
|
|
31
|
-
}
|
|
32
|
-
/**
|
|
33
|
-
* Like {@link BasicRouter.route}, but takes additional arg to control if
|
|
34
|
-
* this routing operation should manipulate the browser's `history`.
|
|
35
|
-
*
|
|
36
|
-
* @remarks
|
|
37
|
-
* If called from userland, this normally is true (also default). However,
|
|
38
|
-
* we want to avoid this if called from this router's own event handlers.
|
|
39
|
-
*
|
|
40
|
-
* @param src -
|
|
41
|
-
* @param ctx -
|
|
42
|
-
* @param pushState -
|
|
43
|
-
*/
|
|
44
|
-
route(src, ctx, pushState = true) {
|
|
45
|
-
const old = this.current;
|
|
46
|
-
const route = super.route(src, ctx);
|
|
47
|
-
if (route && !equiv(route, old)) {
|
|
48
|
-
this.currentPath = this.format(route);
|
|
49
|
-
if (pushState) {
|
|
50
|
-
history.pushState(this.currentPath, "", this.currentPath);
|
|
51
|
-
}
|
|
52
|
-
}
|
|
53
|
-
return route;
|
|
54
|
-
}
|
|
55
|
-
routeTo(route, ctx) {
|
|
56
|
-
if (this.useFragment) {
|
|
57
|
-
location.hash = route;
|
|
58
|
-
}
|
|
59
|
-
this.route(route, ctx);
|
|
60
|
-
}
|
|
61
|
-
handlePopChange() {
|
|
62
|
-
return this.popHandler = this.popHandler || ((e) => {
|
|
63
|
-
this.route(
|
|
64
|
-
e.state || (this.useFragment ? location.hash : location.pathname),
|
|
65
|
-
void 0,
|
|
66
|
-
false
|
|
67
|
-
);
|
|
68
|
-
}).bind(this);
|
|
69
|
-
}
|
|
70
|
-
handleHashChange() {
|
|
71
|
-
return this.hashHandler = this.hashHandler || ((e) => {
|
|
72
|
-
if (!this.ignoreHashChange) {
|
|
73
|
-
const hash = e.newURL.substring(e.newURL.indexOf("#"));
|
|
74
|
-
if (hash !== this.currentPath) {
|
|
75
|
-
this.route(hash, void 0, false);
|
|
76
|
-
}
|
|
77
|
-
}
|
|
78
|
-
}).bind(this);
|
|
79
|
-
}
|
|
80
|
-
handleRouteFailure() {
|
|
81
|
-
this.ignoreHashChange = true;
|
|
82
|
-
location.hash = this.format({
|
|
83
|
-
id: this.routeForID(this.opts.default).id
|
|
84
|
-
});
|
|
85
|
-
this.ignoreHashChange = false;
|
|
86
|
-
return true;
|
|
87
|
-
}
|
|
88
|
-
}
|
|
89
|
-
export {
|
|
90
|
-
HTMLRouter
|
|
91
|
-
};
|