@esportsplus/routing 0.0.9 → 0.0.10
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/build/hash.d.ts +70 -0
- package/build/hash.js +75 -0
- package/build/index.d.ts +6 -92
- package/build/index.js +6 -8
- package/build/middleware/dispatch.d.ts +5 -0
- package/build/middleware/dispatch.js +7 -0
- package/build/middleware/factory.d.ts +3 -3
- package/build/middleware/factory.js +13 -13
- package/build/middleware/index.d.ts +24 -47
- package/build/middleware/index.js +5 -4
- package/build/middleware/match.d.ts +10 -0
- package/build/middleware/match.js +23 -0
- package/build/router/index.d.ts +36 -0
- package/build/router/index.js +182 -0
- package/build/router/node.d.ts +17 -0
- package/build/router/node.js +93 -0
- package/build/router/path.d.ts +14 -0
- package/build/router/path.js +21 -0
- package/build/slugify.d.ts +2 -0
- package/build/slugify.js +3 -0
- package/build/symbols.d.ts +4 -0
- package/build/symbols.js +4 -0
- package/build/types.d.ts +12 -26
- package/build/types.js +2 -1
- package/package.json +2 -3
- package/readme.md +1 -0
- package/src/hash.ts +106 -0
- package/src/index.ts +4 -6
- package/src/middleware/dispatch.ts +12 -0
- package/src/middleware/factory.ts +10 -9
- package/src/middleware/index.ts +4 -3
- package/src/middleware/match.ts +41 -0
- package/src/router/index.ts +237 -0
- package/src/router/node.ts +141 -0
- package/src/router/path.ts +29 -0
- package/src/slugify.ts +4 -0
- package/src/symbols.ts +8 -0
- package/src/types.ts +9 -26
- package/tsconfig.json +5 -19
- package/build/group.d.ts +0 -3
- package/build/group.js +0 -8
- package/build/listener.d.ts +0 -4
- package/build/listener.js +0 -13
- package/build/middleware/common/dispatch.d.ts +0 -3
- package/build/middleware/common/dispatch.js +0 -11
- package/build/middleware/common/index.d.ts +0 -29
- package/build/middleware/common/index.js +0 -3
- package/build/middleware/common/match.d.ts +0 -3
- package/build/middleware/common/match.js +0 -12
- package/build/redirect.d.ts +0 -2
- package/build/redirect.js +0 -10
- package/build/routes.d.ts +0 -20
- package/build/routes.js +0 -45
- package/build/url.d.ts +0 -30
- package/build/url.js +0 -22
- package/src/group.ts +0 -11
- package/src/listener.ts +0 -24
- package/src/middleware/common/dispatch.ts +0 -17
- package/src/middleware/common/index.ts +0 -5
- package/src/middleware/common/match.ts +0 -24
- package/src/redirect.ts +0 -16
- package/src/routes.ts +0 -68
- package/src/url.ts +0 -30
|
@@ -0,0 +1,141 @@
|
|
|
1
|
+
import { PLACEHOLDER, STATIC, WILDCARD } from "~/symbols";
|
|
2
|
+
import { Route } from './index';
|
|
3
|
+
|
|
4
|
+
|
|
5
|
+
class Node {
|
|
6
|
+
children: Map<string | number, Node> | null = null;
|
|
7
|
+
parent: Node | null = null;
|
|
8
|
+
path: string | null = null;
|
|
9
|
+
property: string | null = null;
|
|
10
|
+
route: Route | null = null;
|
|
11
|
+
type: number | null = null;
|
|
12
|
+
|
|
13
|
+
|
|
14
|
+
constructor(parent: Node['parent'] = null) {
|
|
15
|
+
this.parent = parent;
|
|
16
|
+
}
|
|
17
|
+
|
|
18
|
+
|
|
19
|
+
add(path: string, route: Route) {
|
|
20
|
+
let node: Node | undefined = this,
|
|
21
|
+
segments = path.split('/'),
|
|
22
|
+
type: Node['type'] = STATIC,
|
|
23
|
+
unnamed = 0;
|
|
24
|
+
|
|
25
|
+
for (let i = 0, n = segments.length; i < n; i++) {
|
|
26
|
+
let child: Node | undefined = node.children?.get(segments[i]);
|
|
27
|
+
|
|
28
|
+
if (!child) {
|
|
29
|
+
let segment = segments[i],
|
|
30
|
+
symbol = segment[0];
|
|
31
|
+
|
|
32
|
+
if (!node.children) {
|
|
33
|
+
node.children = new Map();
|
|
34
|
+
}
|
|
35
|
+
|
|
36
|
+
node.children.set(segment, (child = new Node(node)));
|
|
37
|
+
|
|
38
|
+
// Named property
|
|
39
|
+
if (symbol === ':') {
|
|
40
|
+
child.property = segment.slice(1) || `${unnamed++}`;
|
|
41
|
+
node.children.set(PLACEHOLDER, child);
|
|
42
|
+
type = null;
|
|
43
|
+
}
|
|
44
|
+
// "*:" Wildcard property
|
|
45
|
+
else if (symbol === '*') {
|
|
46
|
+
child.property = segment.slice(2) || `${unnamed++}`;
|
|
47
|
+
node.children.set(WILDCARD, child);
|
|
48
|
+
type = null;
|
|
49
|
+
}
|
|
50
|
+
}
|
|
51
|
+
|
|
52
|
+
node = child;
|
|
53
|
+
}
|
|
54
|
+
|
|
55
|
+
node.path = path;
|
|
56
|
+
node.route = route;
|
|
57
|
+
node.type = type;
|
|
58
|
+
|
|
59
|
+
return node;
|
|
60
|
+
}
|
|
61
|
+
|
|
62
|
+
find(path: string): {
|
|
63
|
+
parameters?: Record<PropertyKey, unknown>;
|
|
64
|
+
route?: Route;
|
|
65
|
+
} {
|
|
66
|
+
let node: Node | undefined = this,
|
|
67
|
+
parameters: Record<PropertyKey, unknown> = {},
|
|
68
|
+
segments = path.split('/'),
|
|
69
|
+
wildcard: { node: Node, value: string } | null = null;
|
|
70
|
+
|
|
71
|
+
for (let i = 0, n = segments.length; i < n; i++) {
|
|
72
|
+
let segment = segments[i],
|
|
73
|
+
wc = node.children?.get(WILDCARD);
|
|
74
|
+
|
|
75
|
+
if (wc) {
|
|
76
|
+
wildcard = {
|
|
77
|
+
node: wc,
|
|
78
|
+
value: segments.slice(i).join('/')
|
|
79
|
+
};
|
|
80
|
+
}
|
|
81
|
+
|
|
82
|
+
// Exact matches take precedence over placeholders
|
|
83
|
+
let next: Node | undefined = node.children?.get(segment);
|
|
84
|
+
|
|
85
|
+
if (next) {
|
|
86
|
+
node = next;
|
|
87
|
+
}
|
|
88
|
+
else {
|
|
89
|
+
node = node.children?.get(PLACEHOLDER);
|
|
90
|
+
|
|
91
|
+
if (!node) {
|
|
92
|
+
break;
|
|
93
|
+
}
|
|
94
|
+
|
|
95
|
+
parameters[ node.property! ] = segment;
|
|
96
|
+
}
|
|
97
|
+
}
|
|
98
|
+
|
|
99
|
+
if ((!node || !node.route) && wildcard) {
|
|
100
|
+
node = wildcard.node;
|
|
101
|
+
parameters[ node.property! ] = wildcard.value;
|
|
102
|
+
}
|
|
103
|
+
|
|
104
|
+
if (!node) {
|
|
105
|
+
return {};
|
|
106
|
+
}
|
|
107
|
+
|
|
108
|
+
return {
|
|
109
|
+
parameters,
|
|
110
|
+
route: node.route!
|
|
111
|
+
};
|
|
112
|
+
}
|
|
113
|
+
|
|
114
|
+
remove(path: string) {
|
|
115
|
+
let node: Node | undefined = this,
|
|
116
|
+
segments = path.split('/');
|
|
117
|
+
|
|
118
|
+
for (let i = 0, n = segments.length; i < n; i++) {
|
|
119
|
+
node = node.children?.get( segments[i] );
|
|
120
|
+
|
|
121
|
+
if (!node) {
|
|
122
|
+
return;
|
|
123
|
+
}
|
|
124
|
+
}
|
|
125
|
+
|
|
126
|
+
if (!node?.children?.size) {
|
|
127
|
+
let parent = node.parent;
|
|
128
|
+
|
|
129
|
+
if (parent && parent.children) {
|
|
130
|
+
parent.children.delete( segments[segments.length - 1] );
|
|
131
|
+
parent.children.delete(WILDCARD);
|
|
132
|
+
parent.children.delete(PLACEHOLDER);
|
|
133
|
+
}
|
|
134
|
+
}
|
|
135
|
+
|
|
136
|
+
return node;
|
|
137
|
+
}
|
|
138
|
+
}
|
|
139
|
+
|
|
140
|
+
|
|
141
|
+
export { Node };
|
|
@@ -0,0 +1,29 @@
|
|
|
1
|
+
const normalize = (path: string) => {
|
|
2
|
+
if (path[0] !== '/') {
|
|
3
|
+
path = `/${path}`;
|
|
4
|
+
}
|
|
5
|
+
|
|
6
|
+
if (path.endsWith('/')) {
|
|
7
|
+
path = path.slice(0, -1);
|
|
8
|
+
}
|
|
9
|
+
|
|
10
|
+
return path || '/';
|
|
11
|
+
};
|
|
12
|
+
|
|
13
|
+
const radixkey = (path: string, { method, subdomain }: { method?: string | null; subdomain?: string | null; } = {}) => {
|
|
14
|
+
let prefix = '';
|
|
15
|
+
|
|
16
|
+
if (subdomain) {
|
|
17
|
+
prefix = subdomain + ' ';
|
|
18
|
+
}
|
|
19
|
+
|
|
20
|
+
if (method) {
|
|
21
|
+
prefix += method + ' ';
|
|
22
|
+
}
|
|
23
|
+
|
|
24
|
+
return prefix.toUpperCase() + normalize(path);
|
|
25
|
+
};
|
|
26
|
+
|
|
27
|
+
|
|
28
|
+
export default { normalize, radixkey };
|
|
29
|
+
export { normalize, radixkey };
|
package/src/slugify.ts
ADDED
package/src/symbols.ts
ADDED
package/src/types.ts
CHANGED
|
@@ -1,36 +1,19 @@
|
|
|
1
|
-
import {
|
|
2
|
-
import routes from './routes';
|
|
1
|
+
import { Route, Router } from './router';
|
|
3
2
|
|
|
4
3
|
|
|
5
|
-
type
|
|
6
|
-
middleware: Middleware[];
|
|
7
|
-
name: string;
|
|
8
|
-
path: string;
|
|
9
|
-
subdomain: string;
|
|
10
|
-
};
|
|
11
|
-
|
|
12
|
-
type Middleware = (request: Request, next: Next) => unknown;
|
|
13
|
-
|
|
14
|
-
type Next = (request: Request) => unknown;
|
|
15
|
-
|
|
16
|
-
type Request = ReturnType<typeof parse>;
|
|
4
|
+
type Middleware = <T>(request: T, next: Next) => unknown;
|
|
17
5
|
|
|
18
|
-
type
|
|
6
|
+
type Next = <T>(request: T) => unknown;
|
|
19
7
|
|
|
20
|
-
type
|
|
21
|
-
|
|
22
|
-
|
|
23
|
-
routes: typeof routes.routes;
|
|
24
|
-
subdomains: typeof routes.subdomains;
|
|
25
|
-
};
|
|
26
|
-
|
|
27
|
-
type Route = {
|
|
28
|
-
middleware: Middleware[];
|
|
29
|
-
name: string;
|
|
8
|
+
type Options = {
|
|
9
|
+
middleware?: Middleware[];
|
|
10
|
+
name?: string;
|
|
30
11
|
path?: string;
|
|
31
12
|
responder: Responder;
|
|
32
13
|
subdomain?: string;
|
|
33
14
|
};
|
|
34
15
|
|
|
16
|
+
type Responder = <T>(request: T) => Promise<unknown> | unknown;
|
|
17
|
+
|
|
35
18
|
|
|
36
|
-
export {
|
|
19
|
+
export { Middleware, Next, Options, Responder, Route, Router };
|
package/tsconfig.json
CHANGED
|
@@ -1,24 +1,10 @@
|
|
|
1
1
|
{
|
|
2
2
|
"compilerOptions": {
|
|
3
|
-
"
|
|
4
|
-
"
|
|
5
|
-
"
|
|
6
|
-
"declaration": true,
|
|
7
|
-
"declarationDir": "./build",
|
|
8
|
-
"lib": ["dom", "dom.iterable", "esnext"],
|
|
9
|
-
"module": "esnext",
|
|
10
|
-
"moduleResolution": "nodenext",
|
|
11
|
-
"noUnusedLocals": true,
|
|
12
|
-
"noUnusedParameters": true,
|
|
13
|
-
"outDir": "./build",
|
|
14
|
-
"paths": {
|
|
15
|
-
"~/*": ["*"]
|
|
16
|
-
},
|
|
17
|
-
"removeComments": true,
|
|
18
|
-
"resolveJsonModule": true,
|
|
19
|
-
"strict": true,
|
|
20
|
-
"target": "esnext"
|
|
3
|
+
"baseUrl": ".",
|
|
4
|
+
"declarationDir": "build",
|
|
5
|
+
"outDir": "build",
|
|
21
6
|
},
|
|
22
7
|
"exclude": ["node_modules"],
|
|
8
|
+
"extends": "@esportsplus/rspack/tsconfig.base.json",
|
|
23
9
|
"include": ["src"]
|
|
24
|
-
}
|
|
10
|
+
}
|
package/build/group.d.ts
DELETED
package/build/group.js
DELETED
package/build/listener.d.ts
DELETED
package/build/listener.js
DELETED
|
@@ -1,13 +0,0 @@
|
|
|
1
|
-
let data, factory, registered = false;
|
|
2
|
-
function update() {
|
|
3
|
-
data.request = factory();
|
|
4
|
-
}
|
|
5
|
-
export default (d, f) => {
|
|
6
|
-
data = d;
|
|
7
|
-
factory = f;
|
|
8
|
-
if (!registered) {
|
|
9
|
-
registered = true;
|
|
10
|
-
update();
|
|
11
|
-
window.addEventListener('popstate', update);
|
|
12
|
-
}
|
|
13
|
-
};
|
|
@@ -1,11 +0,0 @@
|
|
|
1
|
-
import { factory } from '../../middleware';
|
|
2
|
-
export default (request) => {
|
|
3
|
-
let route = request.data.route;
|
|
4
|
-
if (!route) {
|
|
5
|
-
throw new Error(`Route dispatching failed, route was not defined!`);
|
|
6
|
-
}
|
|
7
|
-
if (!route.middleware.length) {
|
|
8
|
-
return route.responder(request);
|
|
9
|
-
}
|
|
10
|
-
return factory(...route.middleware, (request => route.responder(request)))(request);
|
|
11
|
-
};
|
|
@@ -1,29 +0,0 @@
|
|
|
1
|
-
declare const _default: {
|
|
2
|
-
dispatch: (request: {
|
|
3
|
-
data: Record<string, any>;
|
|
4
|
-
href: string;
|
|
5
|
-
hostname: string;
|
|
6
|
-
origin: string;
|
|
7
|
-
path: string;
|
|
8
|
-
port: string;
|
|
9
|
-
protocol: string;
|
|
10
|
-
query: {
|
|
11
|
-
[k: string]: string;
|
|
12
|
-
};
|
|
13
|
-
subdomain: string;
|
|
14
|
-
}) => any;
|
|
15
|
-
match: ({ routes, subdomains }: import("../../types").Routes) => (request: {
|
|
16
|
-
data: Record<string, any>;
|
|
17
|
-
href: string;
|
|
18
|
-
hostname: string;
|
|
19
|
-
origin: string;
|
|
20
|
-
path: string;
|
|
21
|
-
port: string;
|
|
22
|
-
protocol: string;
|
|
23
|
-
query: {
|
|
24
|
-
[k: string]: string;
|
|
25
|
-
};
|
|
26
|
-
subdomain: string;
|
|
27
|
-
}, next: import("../../types").Next) => unknown;
|
|
28
|
-
};
|
|
29
|
-
export default _default;
|
|
@@ -1,12 +0,0 @@
|
|
|
1
|
-
export default ({ routes, subdomains }) => {
|
|
2
|
-
return (request, next) => {
|
|
3
|
-
let name = (subdomains[request.subdomain] || {})[request.path], route = routes[name];
|
|
4
|
-
if (!route) {
|
|
5
|
-
}
|
|
6
|
-
if (!route && routes.fallback) {
|
|
7
|
-
route = routes.fallback;
|
|
8
|
-
}
|
|
9
|
-
request.data.route = route;
|
|
10
|
-
return next(request);
|
|
11
|
-
};
|
|
12
|
-
};
|
package/build/redirect.d.ts
DELETED
package/build/redirect.js
DELETED
|
@@ -1,10 +0,0 @@
|
|
|
1
|
-
import { routes } from './routes';
|
|
2
|
-
export default (key, _ = {}) => {
|
|
3
|
-
if (key.startsWith('http://') || key.startsWith('https://')) {
|
|
4
|
-
window.location.replace(key);
|
|
5
|
-
}
|
|
6
|
-
if (!routes[key]) {
|
|
7
|
-
throw new Error(`Route '${key}' does not exist`);
|
|
8
|
-
}
|
|
9
|
-
window.location.hash = `#${routes[key].path || ''}`;
|
|
10
|
-
};
|
package/build/routes.d.ts
DELETED
|
@@ -1,20 +0,0 @@
|
|
|
1
|
-
import { Responder, Routes, Route } from './types';
|
|
2
|
-
declare let routes: Record<Route['name'], Route>, subdomains: Record<NonNullable<Route['subdomain']>, Record<NonNullable<Route['path']>, Route['name']>>;
|
|
3
|
-
declare const add: ({ name, path, responder }: {
|
|
4
|
-
name: string;
|
|
5
|
-
path?: string | undefined;
|
|
6
|
-
responder: Responder;
|
|
7
|
-
}) => Route;
|
|
8
|
-
declare const group: (group: any, fn: (routes: Routes) => void) => void;
|
|
9
|
-
declare const _default: {
|
|
10
|
-
add: ({ name, path, responder }: {
|
|
11
|
-
name: string;
|
|
12
|
-
path?: string | undefined;
|
|
13
|
-
responder: Responder;
|
|
14
|
-
}) => Route;
|
|
15
|
-
group: (group: any, fn: (routes: Routes) => void) => void;
|
|
16
|
-
routes: Record<string, Route>;
|
|
17
|
-
subdomains: Record<string, Record<string, string>>;
|
|
18
|
-
};
|
|
19
|
-
export default _default;
|
|
20
|
-
export { add, group, routes, subdomains };
|
package/build/routes.js
DELETED
|
@@ -1,45 +0,0 @@
|
|
|
1
|
-
let groups = [], routes = {}, subdomains = {};
|
|
2
|
-
const add = ({ name, path, responder }) => {
|
|
3
|
-
let http = path !== undefined, route = {
|
|
4
|
-
middleware: [],
|
|
5
|
-
name: '',
|
|
6
|
-
responder
|
|
7
|
-
};
|
|
8
|
-
if (http) {
|
|
9
|
-
route.path = '';
|
|
10
|
-
route.subdomain = '';
|
|
11
|
-
}
|
|
12
|
-
for (let i = 0, n = groups.length; i < n; i++) {
|
|
13
|
-
let group = groups[i];
|
|
14
|
-
if (group.middleware.length) {
|
|
15
|
-
route.middleware.push(...group.middleware);
|
|
16
|
-
}
|
|
17
|
-
route.name += group.name;
|
|
18
|
-
if (http) {
|
|
19
|
-
route.path += group.path;
|
|
20
|
-
route.subdomain = group.subdomain + route.subdomain;
|
|
21
|
-
}
|
|
22
|
-
}
|
|
23
|
-
routes[route.name += name] = route;
|
|
24
|
-
if (http) {
|
|
25
|
-
route.path = `${route.path}${path}`;
|
|
26
|
-
if (route.path[0] !== '/') {
|
|
27
|
-
route.path = `/${route.path}`;
|
|
28
|
-
}
|
|
29
|
-
if (!route.subdomain || route.subdomain === 'www') {
|
|
30
|
-
route.subdomain = '';
|
|
31
|
-
}
|
|
32
|
-
if (!subdomains[route.subdomain]) {
|
|
33
|
-
subdomains[route.subdomain] = {};
|
|
34
|
-
}
|
|
35
|
-
subdomains[route.subdomain][route.path] = route.name;
|
|
36
|
-
}
|
|
37
|
-
return route;
|
|
38
|
-
};
|
|
39
|
-
const group = (group, fn) => {
|
|
40
|
-
groups.push(group);
|
|
41
|
-
fn({ add, group, routes, subdomains });
|
|
42
|
-
groups.pop();
|
|
43
|
-
};
|
|
44
|
-
export default { add, group, routes, subdomains };
|
|
45
|
-
export { add, group, routes, subdomains };
|
package/build/url.d.ts
DELETED
|
@@ -1,30 +0,0 @@
|
|
|
1
|
-
declare const parse: (url?: string) => {
|
|
2
|
-
data: Record<string, any>;
|
|
3
|
-
href: string;
|
|
4
|
-
hostname: string;
|
|
5
|
-
origin: string;
|
|
6
|
-
path: string;
|
|
7
|
-
port: string;
|
|
8
|
-
protocol: string;
|
|
9
|
-
query: {
|
|
10
|
-
[k: string]: string;
|
|
11
|
-
};
|
|
12
|
-
subdomain: string;
|
|
13
|
-
};
|
|
14
|
-
declare const _default: {
|
|
15
|
-
parse: (url?: string) => {
|
|
16
|
-
data: Record<string, any>;
|
|
17
|
-
href: string;
|
|
18
|
-
hostname: string;
|
|
19
|
-
origin: string;
|
|
20
|
-
path: string;
|
|
21
|
-
port: string;
|
|
22
|
-
protocol: string;
|
|
23
|
-
query: {
|
|
24
|
-
[k: string]: string;
|
|
25
|
-
};
|
|
26
|
-
subdomain: string;
|
|
27
|
-
};
|
|
28
|
-
};
|
|
29
|
-
export default _default;
|
|
30
|
-
export { parse };
|
package/build/url.js
DELETED
|
@@ -1,22 +0,0 @@
|
|
|
1
|
-
const parse = (url = window?.location?.href || '') => {
|
|
2
|
-
let { hash, host, hostname, href, origin, port, protocol } = new URL(url), parts = host.split('.'), path = hash?.replace('#/', '/')?.split('?') || ['/', ''], subdomain = '';
|
|
3
|
-
if (parts.length > 2) {
|
|
4
|
-
subdomain = parts[0];
|
|
5
|
-
if (['127', 'www'].includes(subdomain)) {
|
|
6
|
-
subdomain = '';
|
|
7
|
-
}
|
|
8
|
-
}
|
|
9
|
-
return {
|
|
10
|
-
data: {},
|
|
11
|
-
href: href,
|
|
12
|
-
hostname: hostname,
|
|
13
|
-
origin: origin,
|
|
14
|
-
path: path[0],
|
|
15
|
-
port: port,
|
|
16
|
-
protocol: protocol,
|
|
17
|
-
query: Object.fromEntries((new URLSearchParams(path[1])).entries()),
|
|
18
|
-
subdomain
|
|
19
|
-
};
|
|
20
|
-
};
|
|
21
|
-
export default { parse };
|
|
22
|
-
export { parse };
|
package/src/group.ts
DELETED
package/src/listener.ts
DELETED
|
@@ -1,24 +0,0 @@
|
|
|
1
|
-
import { parse } from './url';
|
|
2
|
-
|
|
3
|
-
|
|
4
|
-
let data: Record<string, any>,
|
|
5
|
-
factory: typeof parse,
|
|
6
|
-
registered: boolean = false;
|
|
7
|
-
|
|
8
|
-
|
|
9
|
-
function update() {
|
|
10
|
-
data.request = factory();
|
|
11
|
-
}
|
|
12
|
-
|
|
13
|
-
|
|
14
|
-
export default (d: typeof data, f: typeof factory) => {
|
|
15
|
-
data = d;
|
|
16
|
-
factory = f;
|
|
17
|
-
|
|
18
|
-
if (!registered) {
|
|
19
|
-
registered = true;
|
|
20
|
-
update();
|
|
21
|
-
|
|
22
|
-
window.addEventListener('popstate', update);
|
|
23
|
-
}
|
|
24
|
-
};
|
|
@@ -1,17 +0,0 @@
|
|
|
1
|
-
import { factory } from '~/middleware';
|
|
2
|
-
import { Request } from '~/types';
|
|
3
|
-
|
|
4
|
-
|
|
5
|
-
export default (request: Request) => {
|
|
6
|
-
let route = request.data.route;
|
|
7
|
-
|
|
8
|
-
if (!route) {
|
|
9
|
-
throw new Error(`Route dispatching failed, route was not defined!`);
|
|
10
|
-
}
|
|
11
|
-
|
|
12
|
-
if (!route.middleware.length) {
|
|
13
|
-
return route.responder(request);
|
|
14
|
-
}
|
|
15
|
-
|
|
16
|
-
return factory(...route.middleware, (request => route.responder(request)))(request);
|
|
17
|
-
};
|
|
@@ -1,24 +0,0 @@
|
|
|
1
|
-
import { Next, Request, Routes } from '~/types';
|
|
2
|
-
|
|
3
|
-
|
|
4
|
-
export default ({ routes, subdomains }: Routes) => {
|
|
5
|
-
return (request: Request, next: Next) => {
|
|
6
|
-
let name = (subdomains[request.subdomain] || {})[request.path],
|
|
7
|
-
route = routes[name];
|
|
8
|
-
|
|
9
|
-
// Dynamic routing
|
|
10
|
-
if (!route) {
|
|
11
|
-
// TODO:
|
|
12
|
-
// - Trie based routing
|
|
13
|
-
// - Bind variables to request
|
|
14
|
-
}
|
|
15
|
-
|
|
16
|
-
if (!route && routes.fallback) {
|
|
17
|
-
route = routes.fallback;
|
|
18
|
-
}
|
|
19
|
-
|
|
20
|
-
request.data.route = route;
|
|
21
|
-
|
|
22
|
-
return next(request);
|
|
23
|
-
};
|
|
24
|
-
};
|
package/src/redirect.ts
DELETED
|
@@ -1,16 +0,0 @@
|
|
|
1
|
-
import { routes } from './routes';
|
|
2
|
-
|
|
3
|
-
|
|
4
|
-
export default (key: string, _: Record<string, any> = {}) => {
|
|
5
|
-
// External redirect
|
|
6
|
-
if (key.startsWith('http://') || key.startsWith('https://')) {
|
|
7
|
-
window.location.replace(key);
|
|
8
|
-
}
|
|
9
|
-
|
|
10
|
-
// Internal route based redirect
|
|
11
|
-
if (!routes[key]) {
|
|
12
|
-
throw new Error(`Route '${key}' does not exist`);
|
|
13
|
-
}
|
|
14
|
-
|
|
15
|
-
window.location.hash = `#${routes[key].path || ''}`;
|
|
16
|
-
};
|
package/src/routes.ts
DELETED
|
@@ -1,68 +0,0 @@
|
|
|
1
|
-
import { Group, Responder, Routes, Route } from './types';
|
|
2
|
-
|
|
3
|
-
|
|
4
|
-
let groups: Group[] = [],
|
|
5
|
-
routes: Record<Route['name'], Route> = {},
|
|
6
|
-
subdomains: Record<NonNullable<Route['subdomain']>, Record<NonNullable<Route['path']>, Route['name']>> = {};
|
|
7
|
-
|
|
8
|
-
|
|
9
|
-
const add = ({ name, path, responder }: { name: string, path?: string, responder: Responder }) => {
|
|
10
|
-
let http = path !== undefined,
|
|
11
|
-
route: Route = {
|
|
12
|
-
middleware: [],
|
|
13
|
-
name: '',
|
|
14
|
-
responder
|
|
15
|
-
};
|
|
16
|
-
|
|
17
|
-
if (http) {
|
|
18
|
-
route.path = '';
|
|
19
|
-
route.subdomain = '';
|
|
20
|
-
}
|
|
21
|
-
|
|
22
|
-
for (let i = 0, n = groups.length; i < n; i++) {
|
|
23
|
-
let group = groups[i];
|
|
24
|
-
|
|
25
|
-
if (group.middleware.length) {
|
|
26
|
-
route.middleware.push(...group.middleware);
|
|
27
|
-
}
|
|
28
|
-
|
|
29
|
-
route.name += group.name;
|
|
30
|
-
|
|
31
|
-
if (http) {
|
|
32
|
-
route.path += group.path;
|
|
33
|
-
route.subdomain = group.subdomain + route.subdomain;
|
|
34
|
-
}
|
|
35
|
-
}
|
|
36
|
-
|
|
37
|
-
routes[ route.name += name ] = route;
|
|
38
|
-
|
|
39
|
-
if (http) {
|
|
40
|
-
route.path = `${route.path}${path}`;
|
|
41
|
-
|
|
42
|
-
if (route.path[0] !== '/') {
|
|
43
|
-
route.path = `/${route.path}`;
|
|
44
|
-
}
|
|
45
|
-
|
|
46
|
-
if (!route.subdomain || route.subdomain === 'www') {
|
|
47
|
-
route.subdomain = '';
|
|
48
|
-
}
|
|
49
|
-
|
|
50
|
-
if (!subdomains[route.subdomain]) {
|
|
51
|
-
subdomains[route.subdomain] = {};
|
|
52
|
-
}
|
|
53
|
-
|
|
54
|
-
subdomains[route.subdomain][route.path] = route.name;
|
|
55
|
-
}
|
|
56
|
-
|
|
57
|
-
return route;
|
|
58
|
-
};
|
|
59
|
-
|
|
60
|
-
const group = (group: any, fn: (routes: Routes) => void) => {
|
|
61
|
-
groups.push(group);
|
|
62
|
-
fn({ add, group, routes, subdomains });
|
|
63
|
-
groups.pop();
|
|
64
|
-
};
|
|
65
|
-
|
|
66
|
-
|
|
67
|
-
export default { add, group, routes, subdomains };
|
|
68
|
-
export { add, group, routes, subdomains };
|