@expo/router-server 56.0.8 → 56.0.9
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/getNamedParametrizedRoute.d.ts +12 -0
- package/build/getNamedParametrizedRoute.d.ts.map +1 -0
- package/build/getNamedParametrizedRoute.js +127 -0
- package/build/getNamedParametrizedRoute.js.map +1 -0
- package/build/getServerManifest.d.ts +0 -14
- package/build/getServerManifest.d.ts.map +1 -1
- package/build/getServerManifest.js +2 -131
- package/build/getServerManifest.js.map +1 -1
- package/build/rsc/middleware.d.ts +1 -1
- package/build/rsc/middleware.d.ts.map +1 -1
- package/build/rsc/middleware.js +4 -14
- package/build/rsc/middleware.js.map +1 -1
- package/build/rsc/path.d.ts +0 -17
- package/build/rsc/path.d.ts.map +1 -1
- package/build/rsc/path.js +1 -91
- package/build/rsc/path.js.map +1 -1
- package/build/rsc/router/createPages.d.ts +35 -0
- package/build/rsc/router/createPages.d.ts.map +1 -0
- package/build/rsc/router/createPages.js +258 -0
- package/build/rsc/router/createPages.js.map +1 -0
- package/build/rsc/router/defineRouter.d.ts +10 -6
- package/build/rsc/router/defineRouter.d.ts.map +1 -1
- package/build/rsc/router/defineRouter.js +38 -29
- package/build/rsc/router/defineRouter.js.map +1 -1
- package/build/rsc/router/expo-definedRouter.d.ts +3 -1
- package/build/rsc/router/expo-definedRouter.d.ts.map +1 -1
- package/build/rsc/router/expo-definedRouter.js +90 -94
- package/build/rsc/router/expo-definedRouter.js.map +1 -1
- package/build/rsc/router/index.d.ts +13 -0
- package/build/rsc/router/index.d.ts.map +1 -0
- package/build/rsc/router/index.js +13 -0
- package/build/rsc/router/index.js.map +1 -0
- package/build/rsc/router/noopRouter.d.ts +2 -1
- package/build/rsc/router/noopRouter.d.ts.map +1 -1
- package/build/rsc/router/noopRouter.js +4 -3
- package/build/rsc/router/noopRouter.js.map +1 -1
- package/build/rsc/rsc-renderer.d.ts +2 -0
- package/build/rsc/rsc-renderer.d.ts.map +1 -1
- package/build/rsc/rsc-renderer.js +34 -7
- package/build/rsc/rsc-renderer.js.map +1 -1
- package/build/rsc/server.d.ts +2 -3
- package/build/rsc/server.d.ts.map +1 -1
- package/build/rsc/server.js +7 -34
- package/build/rsc/server.js.map +1 -1
- package/package.json +8 -8
- package/build/rsc/router/create-expo-pages.d.ts +0 -20
- package/build/rsc/router/create-expo-pages.d.ts.map +0 -1
- package/build/rsc/router/create-expo-pages.js +0 -21
- package/build/rsc/router/create-expo-pages.js.map +0 -1
- package/build/rsc/router/create-pages.d.ts +0 -80
- package/build/rsc/router/create-pages.d.ts.map +0 -1
- package/build/rsc/router/create-pages.js +0 -232
- package/build/rsc/router/create-pages.js.map +0 -1
package/build/rsc/path.js
CHANGED
|
@@ -9,7 +9,7 @@
|
|
|
9
9
|
* https://github.com/dai-shi/waku/blob/32d52242c1450b5f5965860e671ff73c42da8bd0/packages/waku/src/lib/utils/path.ts#L1
|
|
10
10
|
*/
|
|
11
11
|
Object.defineProperty(exports, "__esModule", { value: true });
|
|
12
|
-
exports.
|
|
12
|
+
exports.extname = exports.joinPath = exports.fileURLToFilePath = exports.filePathToFileURL = exports.decodeFilePathFromAbsolute = exports.encodeFilePathToAbsolute = void 0;
|
|
13
13
|
// Terminology:
|
|
14
14
|
// - filePath: posix-like file path, e.g. `/foo/bar.js` or `c:/foo/bar.js`
|
|
15
15
|
// This is used by Vite.
|
|
@@ -81,94 +81,4 @@ const extname = (filePath) => {
|
|
|
81
81
|
return index > 0 ? filePath.slice(index) : '';
|
|
82
82
|
};
|
|
83
83
|
exports.extname = extname;
|
|
84
|
-
const parsePathWithSlug = (path) => path
|
|
85
|
-
.split('/')
|
|
86
|
-
.filter(Boolean)
|
|
87
|
-
.map((name) => {
|
|
88
|
-
let type = 'literal';
|
|
89
|
-
const isSlug = name.startsWith('[') && name.endsWith(']');
|
|
90
|
-
if (isSlug) {
|
|
91
|
-
type = 'group';
|
|
92
|
-
name = name.slice(1, -1);
|
|
93
|
-
}
|
|
94
|
-
const isWildcard = name.startsWith('...');
|
|
95
|
-
if (isWildcard) {
|
|
96
|
-
type = 'wildcard';
|
|
97
|
-
name = name.slice(3);
|
|
98
|
-
}
|
|
99
|
-
return { type, name };
|
|
100
|
-
});
|
|
101
|
-
exports.parsePathWithSlug = parsePathWithSlug;
|
|
102
|
-
const getPathMapping = (pathSpec, pathname) => {
|
|
103
|
-
const actual = pathname.split('/').filter(Boolean);
|
|
104
|
-
if (pathSpec.length > actual.length) {
|
|
105
|
-
return null;
|
|
106
|
-
}
|
|
107
|
-
const mapping = {};
|
|
108
|
-
let wildcardStartIndex = -1;
|
|
109
|
-
for (let i = 0; i < pathSpec.length; i++) {
|
|
110
|
-
const { type, name } = pathSpec[i];
|
|
111
|
-
if (type === 'literal') {
|
|
112
|
-
if (name !== actual[i]) {
|
|
113
|
-
return null;
|
|
114
|
-
}
|
|
115
|
-
}
|
|
116
|
-
else if (type === 'wildcard') {
|
|
117
|
-
wildcardStartIndex = i;
|
|
118
|
-
break;
|
|
119
|
-
}
|
|
120
|
-
else if (name) {
|
|
121
|
-
mapping[name] = actual[i];
|
|
122
|
-
}
|
|
123
|
-
}
|
|
124
|
-
if (wildcardStartIndex === -1) {
|
|
125
|
-
if (pathSpec.length !== actual.length) {
|
|
126
|
-
return null;
|
|
127
|
-
}
|
|
128
|
-
return mapping;
|
|
129
|
-
}
|
|
130
|
-
let wildcardEndIndex = -1;
|
|
131
|
-
for (let i = 0; i < pathSpec.length; i++) {
|
|
132
|
-
const { type, name } = pathSpec[pathSpec.length - i - 1];
|
|
133
|
-
if (type === 'literal') {
|
|
134
|
-
if (name !== actual[actual.length - i - 1]) {
|
|
135
|
-
return null;
|
|
136
|
-
}
|
|
137
|
-
}
|
|
138
|
-
else if (type === 'wildcard') {
|
|
139
|
-
wildcardEndIndex = actual.length - i - 1;
|
|
140
|
-
break;
|
|
141
|
-
}
|
|
142
|
-
else if (name) {
|
|
143
|
-
mapping[name] = actual[actual.length - i - 1];
|
|
144
|
-
}
|
|
145
|
-
}
|
|
146
|
-
if (wildcardStartIndex === -1 || wildcardEndIndex === -1) {
|
|
147
|
-
throw new Error('Invalid wildcard path');
|
|
148
|
-
}
|
|
149
|
-
const wildcardName = pathSpec[wildcardStartIndex].name;
|
|
150
|
-
if (wildcardName) {
|
|
151
|
-
mapping[wildcardName] = actual.slice(wildcardStartIndex, wildcardEndIndex + 1);
|
|
152
|
-
}
|
|
153
|
-
return mapping;
|
|
154
|
-
};
|
|
155
|
-
exports.getPathMapping = getPathMapping;
|
|
156
|
-
/**
|
|
157
|
-
* Transform a path spec to a regular expression.
|
|
158
|
-
*/
|
|
159
|
-
const path2regexp = (path) => {
|
|
160
|
-
const parts = path.map(({ type, name }) => {
|
|
161
|
-
if (type === 'literal') {
|
|
162
|
-
return name;
|
|
163
|
-
}
|
|
164
|
-
else if (type === 'group') {
|
|
165
|
-
return `([^/]+)`;
|
|
166
|
-
}
|
|
167
|
-
else {
|
|
168
|
-
return `(.*)`;
|
|
169
|
-
}
|
|
170
|
-
});
|
|
171
|
-
return `^/${parts.join('/')}$`;
|
|
172
|
-
};
|
|
173
|
-
exports.path2regexp = path2regexp;
|
|
174
84
|
//# sourceMappingURL=path.js.map
|
package/build/rsc/path.js.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"path.js","sourceRoot":"","sources":["../../src/rsc/path.ts"],"names":[],"mappings":"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","sourcesContent":["/**\n * Copyright © 2024 650 Industries.\n * Copyright © 2024 2023 Daishi Kato\n *\n * This source code is licensed under the MIT license found in the\n * LICENSE file in the root directory of this source tree.\n *\n * https://github.com/dai-shi/waku/blob/32d52242c1450b5f5965860e671ff73c42da8bd0/packages/waku/src/lib/utils/path.ts#L1\n */\n\n// Terminology:\n// - filePath: posix-like file path, e.g. `/foo/bar.js` or `c:/foo/bar.js`\n// This is used by Vite.\n// - fileURL: file URL, e.g. `file:///foo/bar.js` or `file:///c:/foo/bar.js`\n// This is used by import().\n// - osPath: os dependent path, e.g. `/foo/bar.js` or `c:\\foo\\bar.js`\n// This is used by node:fs.\n\nconst ABSOLUTE_WIN32_PATH_REGEXP = /^\\/[a-zA-Z]:\\//;\n\nexport const encodeFilePathToAbsolute = (filePath: string) => {\n if (ABSOLUTE_WIN32_PATH_REGEXP.test(filePath)) {\n throw new Error('Unsupported absolute file path');\n }\n if (filePath.startsWith('/')) {\n return filePath;\n }\n return '/' + filePath;\n};\n\nexport const decodeFilePathFromAbsolute = (filePath: string) => {\n if (ABSOLUTE_WIN32_PATH_REGEXP.test(filePath)) {\n return filePath.slice(1);\n }\n return filePath;\n};\n\nexport const filePathToFileURL = (filePath: string) => 'file://' + encodeURI(filePath);\n\n/** Return the original \"osPath\" based on the file URL */\nexport const fileURLToFilePath = (fileURL: string) => {\n if (!fileURL.startsWith('file://')) {\n throw new Error('Not a file URL');\n }\n\n const filePath = decodeURI(fileURL.slice('file://'.length));\n\n // File URLs are always formatted in POSIX, using a leading `/` (URL pathname) separator.\n // On POSIX systems, this leading `/` is the root directory, which is valid for absolute file paths.\n // On UNIX systems, this leading `/` needs to be stripped, and the actual UNIX formatted path is returned - to match Metro's behavior\n return ABSOLUTE_WIN32_PATH_REGEXP.test(filePath)\n ? filePath.slice(1).replace(/\\//g, '\\\\')\n : filePath;\n};\n\n// for filePath\nexport const joinPath = (...paths: string[]) => {\n const isAbsolute = paths[0]?.startsWith('/');\n const items = ([] as string[]).concat(...paths.map((path) => path.split('/')));\n let i = 0;\n while (i < items.length) {\n if (items[i] === '.' || items[i] === '') {\n items.splice(i, 1);\n } else if (items[i] === '..') {\n if (i > 0) {\n items.splice(i - 1, 2);\n --i;\n } else {\n items.splice(i, 1);\n }\n } else {\n ++i;\n }\n }\n return (isAbsolute ? '/' : '') + items.join('/') || '.';\n};\n\nexport const extname = (filePath: string) => {\n const index = filePath.lastIndexOf('.');\n return index > 0 ? filePath.slice(index) : '';\n};\n\nexport type PathSpecItem =\n | { type: 'literal'; name: string }\n | { type: 'group'; name?: string }\n | { type: 'wildcard'; name?: string };\nexport type PathSpec = readonly PathSpecItem[];\n\nexport const parsePathWithSlug = (path: string): PathSpec =>\n path\n .split('/')\n .filter(Boolean)\n .map((name) => {\n let type: 'literal' | 'group' | 'wildcard' = 'literal';\n const isSlug = name.startsWith('[') && name.endsWith(']');\n if (isSlug) {\n type = 'group';\n name = name.slice(1, -1);\n }\n const isWildcard = name.startsWith('...');\n if (isWildcard) {\n type = 'wildcard';\n name = name.slice(3);\n }\n return { type, name };\n });\n\nexport const getPathMapping = (\n pathSpec: PathSpec,\n pathname: string\n): Record<string, string | string[]> | null => {\n const actual = pathname.split('/').filter(Boolean);\n if (pathSpec.length > actual.length) {\n return null;\n }\n const mapping: Record<string, string | string[]> = {};\n let wildcardStartIndex = -1;\n for (let i = 0; i < pathSpec.length; i++) {\n const { type, name } = pathSpec[i]!;\n if (type === 'literal') {\n if (name !== actual[i]) {\n return null;\n }\n } else if (type === 'wildcard') {\n wildcardStartIndex = i;\n break;\n } else if (name) {\n mapping[name] = actual[i]!;\n }\n }\n if (wildcardStartIndex === -1) {\n if (pathSpec.length !== actual.length) {\n return null;\n }\n return mapping;\n }\n let wildcardEndIndex = -1;\n for (let i = 0; i < pathSpec.length; i++) {\n const { type, name } = pathSpec[pathSpec.length - i - 1]!;\n if (type === 'literal') {\n if (name !== actual[actual.length - i - 1]) {\n return null;\n }\n } else if (type === 'wildcard') {\n wildcardEndIndex = actual.length - i - 1;\n break;\n } else if (name) {\n mapping[name] = actual[actual.length - i - 1]!;\n }\n }\n if (wildcardStartIndex === -1 || wildcardEndIndex === -1) {\n throw new Error('Invalid wildcard path');\n }\n const wildcardName = pathSpec[wildcardStartIndex]!.name;\n if (wildcardName) {\n mapping[wildcardName] = actual.slice(wildcardStartIndex, wildcardEndIndex + 1);\n }\n return mapping;\n};\n\n/**\n * Transform a path spec to a regular expression.\n */\nexport const path2regexp = (path: PathSpec) => {\n const parts = path.map(({ type, name }) => {\n if (type === 'literal') {\n return name;\n } else if (type === 'group') {\n return `([^/]+)`;\n } else {\n return `(.*)`;\n }\n });\n return `^/${parts.join('/')}$`;\n};\n"]}
|
|
1
|
+
{"version":3,"file":"path.js","sourceRoot":"","sources":["../../src/rsc/path.ts"],"names":[],"mappings":"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","sourcesContent":["/**\n * Copyright © 2024 650 Industries.\n * Copyright © 2024 2023 Daishi Kato\n *\n * This source code is licensed under the MIT license found in the\n * LICENSE file in the root directory of this source tree.\n *\n * https://github.com/dai-shi/waku/blob/32d52242c1450b5f5965860e671ff73c42da8bd0/packages/waku/src/lib/utils/path.ts#L1\n */\n\n// Terminology:\n// - filePath: posix-like file path, e.g. `/foo/bar.js` or `c:/foo/bar.js`\n// This is used by Vite.\n// - fileURL: file URL, e.g. `file:///foo/bar.js` or `file:///c:/foo/bar.js`\n// This is used by import().\n// - osPath: os dependent path, e.g. `/foo/bar.js` or `c:\\foo\\bar.js`\n// This is used by node:fs.\n\nconst ABSOLUTE_WIN32_PATH_REGEXP = /^\\/[a-zA-Z]:\\//;\n\nexport const encodeFilePathToAbsolute = (filePath: string) => {\n if (ABSOLUTE_WIN32_PATH_REGEXP.test(filePath)) {\n throw new Error('Unsupported absolute file path');\n }\n if (filePath.startsWith('/')) {\n return filePath;\n }\n return '/' + filePath;\n};\n\nexport const decodeFilePathFromAbsolute = (filePath: string) => {\n if (ABSOLUTE_WIN32_PATH_REGEXP.test(filePath)) {\n return filePath.slice(1);\n }\n return filePath;\n};\n\nexport const filePathToFileURL = (filePath: string) => 'file://' + encodeURI(filePath);\n\n/** Return the original \"osPath\" based on the file URL */\nexport const fileURLToFilePath = (fileURL: string) => {\n if (!fileURL.startsWith('file://')) {\n throw new Error('Not a file URL');\n }\n\n const filePath = decodeURI(fileURL.slice('file://'.length));\n\n // File URLs are always formatted in POSIX, using a leading `/` (URL pathname) separator.\n // On POSIX systems, this leading `/` is the root directory, which is valid for absolute file paths.\n // On UNIX systems, this leading `/` needs to be stripped, and the actual UNIX formatted path is returned - to match Metro's behavior\n return ABSOLUTE_WIN32_PATH_REGEXP.test(filePath)\n ? filePath.slice(1).replace(/\\//g, '\\\\')\n : filePath;\n};\n\n// for filePath\nexport const joinPath = (...paths: string[]) => {\n const isAbsolute = paths[0]?.startsWith('/');\n const items = ([] as string[]).concat(...paths.map((path) => path.split('/')));\n let i = 0;\n while (i < items.length) {\n if (items[i] === '.' || items[i] === '') {\n items.splice(i, 1);\n } else if (items[i] === '..') {\n if (i > 0) {\n items.splice(i - 1, 2);\n --i;\n } else {\n items.splice(i, 1);\n }\n } else {\n ++i;\n }\n }\n return (isAbsolute ? '/' : '') + items.join('/') || '.';\n};\n\nexport const extname = (filePath: string) => {\n const index = filePath.lastIndexOf('.');\n return index > 0 ? filePath.slice(index) : '';\n};\n"]}
|
|
@@ -0,0 +1,35 @@
|
|
|
1
|
+
import type { RouteProps } from 'expo-router/internal/rsc';
|
|
2
|
+
import type { FunctionComponent, ReactNode } from 'react';
|
|
3
|
+
import { unstable_defineRouter } from './defineRouter';
|
|
4
|
+
import type { BuildConfig } from '../server';
|
|
5
|
+
export type CreatePageInput = {
|
|
6
|
+
path: string;
|
|
7
|
+
component: FunctionComponent<any>;
|
|
8
|
+
render: 'static' | 'dynamic';
|
|
9
|
+
staticPaths?: (string | string[])[];
|
|
10
|
+
unstable_disableSSR?: boolean;
|
|
11
|
+
};
|
|
12
|
+
export type CreateLayoutInput = {
|
|
13
|
+
path: string;
|
|
14
|
+
component: FunctionComponent<Omit<RouteProps, 'searchParams'> & {
|
|
15
|
+
children: ReactNode;
|
|
16
|
+
}>;
|
|
17
|
+
render: 'static' | 'dynamic';
|
|
18
|
+
};
|
|
19
|
+
export type CreatePagesApi = {
|
|
20
|
+
createPage: (page: CreatePageInput) => void;
|
|
21
|
+
createLayout: (layout: CreateLayoutInput) => void;
|
|
22
|
+
unstable_setBuildData: (path: string, data: unknown) => void;
|
|
23
|
+
};
|
|
24
|
+
export type CreatePagesFn = (api: CreatePagesApi, opts: {
|
|
25
|
+
unstable_buildConfig: BuildConfig | undefined;
|
|
26
|
+
}) => Promise<void>;
|
|
27
|
+
/**
|
|
28
|
+
* Build an RSC router from a registration callback. Imitates `expo-server`'s
|
|
29
|
+
* URL routing: each registered component carries a regex matcher, and the
|
|
30
|
+
* resolver iterates the registry in specificity order, first match wins.
|
|
31
|
+
* No exact-key lookup: this lets paths with `(group)` segments match runtime
|
|
32
|
+
* IDs that don't include them.
|
|
33
|
+
*/
|
|
34
|
+
export declare function createPages(fn: CreatePagesFn): ReturnType<typeof unstable_defineRouter>;
|
|
35
|
+
//# sourceMappingURL=createPages.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"createPages.d.ts","sourceRoot":"","sources":["../../../src/rsc/router/createPages.ts"],"names":[],"mappings":"AACA,OAAO,KAAK,EAAE,UAAU,EAAE,MAAM,0BAA0B,CAAC;AAE3D,OAAO,KAAK,EAAE,iBAAiB,EAAE,SAAS,EAAE,MAAM,OAAO,CAAC;AAE1D,OAAO,EAAE,qBAAqB,EAAE,MAAM,gBAAgB,CAAC;AAEvD,OAAO,KAAK,EAAE,WAAW,EAAE,MAAM,WAAW,CAAC;AAoB7C,MAAM,MAAM,eAAe,GAAG;IAC5B,IAAI,EAAE,MAAM,CAAC;IACb,SAAS,EAAE,iBAAiB,CAAC,GAAG,CAAC,CAAC;IAClC,MAAM,EAAE,QAAQ,GAAG,SAAS,CAAC;IAC7B,WAAW,CAAC,EAAE,CAAC,MAAM,GAAG,MAAM,EAAE,CAAC,EAAE,CAAC;IACpC,mBAAmB,CAAC,EAAE,OAAO,CAAC;CAC/B,CAAC;AAEF,MAAM,MAAM,iBAAiB,GAAG;IAC9B,IAAI,EAAE,MAAM,CAAC;IACb,SAAS,EAAE,iBAAiB,CAAC,IAAI,CAAC,UAAU,EAAE,cAAc,CAAC,GAAG;QAAE,QAAQ,EAAE,SAAS,CAAA;KAAE,CAAC,CAAC;IACzF,MAAM,EAAE,QAAQ,GAAG,SAAS,CAAC;CAC9B,CAAC;AAEF,MAAM,MAAM,cAAc,GAAG;IAC3B,UAAU,EAAE,CAAC,IAAI,EAAE,eAAe,KAAK,IAAI,CAAC;IAC5C,YAAY,EAAE,CAAC,MAAM,EAAE,iBAAiB,KAAK,IAAI,CAAC;IAClD,qBAAqB,EAAE,CAAC,IAAI,EAAE,MAAM,EAAE,IAAI,EAAE,OAAO,KAAK,IAAI,CAAC;CAC9D,CAAC;AAEF,MAAM,MAAM,aAAa,GAAG,CAC1B,GAAG,EAAE,cAAc,EACnB,IAAI,EAAE;IAAE,oBAAoB,EAAE,WAAW,GAAG,SAAS,CAAA;CAAE,KACpD,OAAO,CAAC,IAAI,CAAC,CAAC;AAgDnB;;;;;;GAMG;AACH,wBAAgB,WAAW,CAAC,EAAE,EAAE,aAAa,GAAG,UAAU,CAAC,OAAO,qBAAqB,CAAC,CAgOvF"}
|
|
@@ -0,0 +1,258 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
3
|
+
exports.createPages = createPages;
|
|
4
|
+
const routing_1 = require("expo-router/internal/routing");
|
|
5
|
+
const react_1 = require("react");
|
|
6
|
+
const defineRouter_1 = require("./defineRouter");
|
|
7
|
+
const getNamedParametrizedRoute_1 = require("../../getNamedParametrizedRoute");
|
|
8
|
+
function compilePathMatcher(path, suffix) {
|
|
9
|
+
// Reuse expo-router-server's canonical regex builder so RSC matching agrees with
|
|
10
|
+
// the URL manifest about brackets, group routes (optional), wildcards, and +not-found.
|
|
11
|
+
const { namedParameterizedRoute, routeKeys, wildcardKeys } = (0, getNamedParametrizedRoute_1.getNamedParametrizedRoute)(path);
|
|
12
|
+
// Strip a trailing slash before appending the suffix so the root path doesn't
|
|
13
|
+
// produce `//page` when concatenated.
|
|
14
|
+
const base = namedParameterizedRoute.replace(/\/$/, '');
|
|
15
|
+
const regex = new RegExp(`^${suffix ? `${base}/${suffix}` : base}/?$`);
|
|
16
|
+
return (target) => {
|
|
17
|
+
// Targets are either IDs (`posts/123/page`) or pathnames (`/posts/123`).
|
|
18
|
+
// The canonical regex expects a leading slash, so add one for IDs.
|
|
19
|
+
const match = regex.exec(target.startsWith('/') ? target : '/' + target);
|
|
20
|
+
if (!match)
|
|
21
|
+
return null;
|
|
22
|
+
const params = {};
|
|
23
|
+
for (const [cleanedKey, originalName] of Object.entries(routeKeys)) {
|
|
24
|
+
const value = match.groups?.[cleanedKey];
|
|
25
|
+
if (value === undefined)
|
|
26
|
+
continue;
|
|
27
|
+
params[originalName] = wildcardKeys.has(cleanedKey) ? value.split('/') : value;
|
|
28
|
+
}
|
|
29
|
+
return params;
|
|
30
|
+
};
|
|
31
|
+
}
|
|
32
|
+
function buildMatchesPathname(path) {
|
|
33
|
+
const matcher = compilePathMatcher(path);
|
|
34
|
+
return (pathname) => matcher(pathname) != null;
|
|
35
|
+
}
|
|
36
|
+
function isDynamicPath(path) {
|
|
37
|
+
return path.split('/').some((segment) => (0, routing_1.matchDynamicName)(segment) != null);
|
|
38
|
+
}
|
|
39
|
+
function hasPathPrefix(prefix, path) {
|
|
40
|
+
return path === prefix || path.startsWith(prefix + '/');
|
|
41
|
+
}
|
|
42
|
+
/** Normalize a registration path to a URL-shaped pathname (always starts with `/`). */
|
|
43
|
+
function normalizePath(path) {
|
|
44
|
+
if (path === '' || path === '/')
|
|
45
|
+
return '/';
|
|
46
|
+
return path.startsWith('/') ? path : '/' + path;
|
|
47
|
+
}
|
|
48
|
+
function sanitizeSlug(slug) {
|
|
49
|
+
return slug.replace(/\./g, '').replace(/ /g, '-');
|
|
50
|
+
}
|
|
51
|
+
/**
|
|
52
|
+
* Build an RSC router from a registration callback. Imitates `expo-server`'s
|
|
53
|
+
* URL routing: each registered component carries a regex matcher, and the
|
|
54
|
+
* resolver iterates the registry in specificity order, first match wins.
|
|
55
|
+
* No exact-key lookup: this lets paths with `(group)` segments match runtime
|
|
56
|
+
* IDs that don't include them.
|
|
57
|
+
*/
|
|
58
|
+
function createPages(fn) {
|
|
59
|
+
let configured = false;
|
|
60
|
+
const entriesByKey = new Map();
|
|
61
|
+
const buildDataMap = new Map();
|
|
62
|
+
let sortedEntries = [];
|
|
63
|
+
const register = (entry) => {
|
|
64
|
+
const key = `${entry.kind}:${entry.path}`;
|
|
65
|
+
const existing = entriesByKey.get(key);
|
|
66
|
+
if (existing && existing.component !== entry.component) {
|
|
67
|
+
throw new Error(`Duplicated component for ${entry.kind}: ${entry.path}`);
|
|
68
|
+
}
|
|
69
|
+
entriesByKey.set(key, entry);
|
|
70
|
+
};
|
|
71
|
+
const createPage = (page) => {
|
|
72
|
+
if (configured) {
|
|
73
|
+
throw new Error('no longer available');
|
|
74
|
+
}
|
|
75
|
+
// Normalize once up-front: top-level `./index.tsx` arrives as `''`, and
|
|
76
|
+
// everything downstream (the matcher, the registry key, the resolver) wants
|
|
77
|
+
// a URL-shaped pathname.
|
|
78
|
+
const path = normalizePath(page.path);
|
|
79
|
+
const noSsr = !!page.unstable_disableSSR;
|
|
80
|
+
const segments = path.split('/').filter(Boolean);
|
|
81
|
+
let numSlugs = 0;
|
|
82
|
+
let numWildcards = 0;
|
|
83
|
+
for (const segment of segments) {
|
|
84
|
+
const dynamic = (0, routing_1.matchDynamicName)(segment);
|
|
85
|
+
if (!dynamic)
|
|
86
|
+
continue;
|
|
87
|
+
numSlugs++;
|
|
88
|
+
if (dynamic.deep)
|
|
89
|
+
numWildcards++;
|
|
90
|
+
}
|
|
91
|
+
if (page.render === 'static' && numSlugs === 0) {
|
|
92
|
+
register({
|
|
93
|
+
path,
|
|
94
|
+
component: page.component,
|
|
95
|
+
kind: 'page',
|
|
96
|
+
isDynamic: false,
|
|
97
|
+
isWildcard: false,
|
|
98
|
+
noSsr,
|
|
99
|
+
matchId: compilePathMatcher(path, 'page'),
|
|
100
|
+
matchesPathname: buildMatchesPathname(path),
|
|
101
|
+
});
|
|
102
|
+
return;
|
|
103
|
+
}
|
|
104
|
+
if (page.render === 'static' && numSlugs > 0) {
|
|
105
|
+
if (!page.staticPaths) {
|
|
106
|
+
throw new Error('staticPaths is required for static pages with slugs');
|
|
107
|
+
}
|
|
108
|
+
const staticPaths = page.staticPaths.map((item) => (Array.isArray(item) ? item : [item]).map(sanitizeSlug));
|
|
109
|
+
for (const staticPath of staticPaths) {
|
|
110
|
+
if (staticPath.length !== numSlugs && numWildcards === 0) {
|
|
111
|
+
throw new Error('staticPaths does not match with slug pattern');
|
|
112
|
+
}
|
|
113
|
+
const mapping = {};
|
|
114
|
+
let slugIndex = 0;
|
|
115
|
+
const pathItems = [];
|
|
116
|
+
for (const segment of segments) {
|
|
117
|
+
const dynamic = (0, routing_1.matchDynamicName)(segment);
|
|
118
|
+
if (!dynamic) {
|
|
119
|
+
pathItems.push(segment);
|
|
120
|
+
continue;
|
|
121
|
+
}
|
|
122
|
+
if (dynamic.deep) {
|
|
123
|
+
mapping[dynamic.name] = staticPath.slice(slugIndex);
|
|
124
|
+
staticPath.slice(slugIndex++).forEach((slug) => pathItems.push(slug));
|
|
125
|
+
}
|
|
126
|
+
else {
|
|
127
|
+
pathItems.push(staticPath[slugIndex++]);
|
|
128
|
+
mapping[dynamic.name] = pathItems[pathItems.length - 1];
|
|
129
|
+
}
|
|
130
|
+
}
|
|
131
|
+
const concretePath = '/' + pathItems.join('/');
|
|
132
|
+
const WrappedComponent = (props) => (0, react_1.createElement)(page.component, { ...props, ...mapping });
|
|
133
|
+
register({
|
|
134
|
+
path: concretePath,
|
|
135
|
+
component: WrappedComponent,
|
|
136
|
+
kind: 'page',
|
|
137
|
+
isDynamic: false,
|
|
138
|
+
isWildcard: false,
|
|
139
|
+
noSsr,
|
|
140
|
+
matchId: compilePathMatcher(concretePath, 'page'),
|
|
141
|
+
matchesPathname: buildMatchesPathname(concretePath),
|
|
142
|
+
});
|
|
143
|
+
}
|
|
144
|
+
return;
|
|
145
|
+
}
|
|
146
|
+
if (page.render === 'dynamic') {
|
|
147
|
+
if (numWildcards > 1) {
|
|
148
|
+
throw new Error('Invalid page configuration: ' + path);
|
|
149
|
+
}
|
|
150
|
+
register({
|
|
151
|
+
path,
|
|
152
|
+
component: page.component,
|
|
153
|
+
kind: 'page',
|
|
154
|
+
isDynamic: true,
|
|
155
|
+
isWildcard: numWildcards === 1,
|
|
156
|
+
noSsr,
|
|
157
|
+
matchId: compilePathMatcher(path, 'page'),
|
|
158
|
+
matchesPathname: buildMatchesPathname(path),
|
|
159
|
+
});
|
|
160
|
+
return;
|
|
161
|
+
}
|
|
162
|
+
throw new Error('Invalid page configuration: ' + path);
|
|
163
|
+
};
|
|
164
|
+
const createLayout = (layout) => {
|
|
165
|
+
if (configured) {
|
|
166
|
+
throw new Error('no longer available');
|
|
167
|
+
}
|
|
168
|
+
if (layout.render !== 'static' && layout.render !== 'dynamic') {
|
|
169
|
+
throw new Error('Invalid layout configuration');
|
|
170
|
+
}
|
|
171
|
+
const path = normalizePath(layout.path);
|
|
172
|
+
register({
|
|
173
|
+
path,
|
|
174
|
+
component: layout.component,
|
|
175
|
+
kind: 'layout',
|
|
176
|
+
isDynamic: layout.render === 'dynamic' || isDynamicPath(path),
|
|
177
|
+
isWildcard: false,
|
|
178
|
+
noSsr: false,
|
|
179
|
+
matchId: compilePathMatcher(path, 'layout'),
|
|
180
|
+
matchesPathname: buildMatchesPathname(path),
|
|
181
|
+
});
|
|
182
|
+
};
|
|
183
|
+
const unstable_setBuildData = (path, data) => {
|
|
184
|
+
// Key by the same normalized pathname `register` uses, so the lookup at
|
|
185
|
+
// `buildDataMap.get(entry.path)` finds it regardless of caller convention.
|
|
186
|
+
buildDataMap.set(normalizePath(path), data);
|
|
187
|
+
};
|
|
188
|
+
let ready;
|
|
189
|
+
const configure = async (buildConfig) => {
|
|
190
|
+
if (!configured && !ready) {
|
|
191
|
+
ready = fn({ createPage, createLayout, unstable_setBuildData }, { unstable_buildConfig: buildConfig });
|
|
192
|
+
await ready;
|
|
193
|
+
configured = true;
|
|
194
|
+
// Resolver iterates this once per request and takes the first matchId hit.
|
|
195
|
+
// Non-wildcard pages must out-rank wildcards so a more specific path wins; the
|
|
196
|
+
// matcher's `/page` vs `/layout` suffix prevents cross-kind false matches, so
|
|
197
|
+
// page-vs-layout order is irrelevant.
|
|
198
|
+
sortedEntries = Array.from(entriesByKey.values()).sort((a, b) => Number(a.isWildcard) - Number(b.isWildcard));
|
|
199
|
+
}
|
|
200
|
+
await ready;
|
|
201
|
+
};
|
|
202
|
+
return (0, defineRouter_1.unstable_defineRouter)(async () => {
|
|
203
|
+
await configure();
|
|
204
|
+
const dynamicLayoutPaths = [];
|
|
205
|
+
for (const entry of sortedEntries) {
|
|
206
|
+
if (entry.kind === 'layout' && entry.isDynamic)
|
|
207
|
+
dynamicLayoutPaths.push(entry.path);
|
|
208
|
+
}
|
|
209
|
+
const isUnderDynamicLayout = (pagePath) => dynamicLayoutPaths.some((lp) => hasPathPrefix(lp, pagePath));
|
|
210
|
+
const paths = [];
|
|
211
|
+
for (const entry of sortedEntries) {
|
|
212
|
+
if (entry.kind !== 'page')
|
|
213
|
+
continue;
|
|
214
|
+
paths.push({
|
|
215
|
+
path: entry.path,
|
|
216
|
+
matchesPathname: entry.matchesPathname,
|
|
217
|
+
isStatic: !entry.isDynamic && !isUnderDynamicLayout(entry.path),
|
|
218
|
+
noSsr: entry.noSsr,
|
|
219
|
+
data: buildDataMap.get(entry.path),
|
|
220
|
+
});
|
|
221
|
+
}
|
|
222
|
+
return paths;
|
|
223
|
+
}, async (id, { unstable_setShouldSkip, unstable_buildConfig }) => {
|
|
224
|
+
await configure(unstable_buildConfig);
|
|
225
|
+
for (const entry of sortedEntries) {
|
|
226
|
+
const mapping = entry.matchId(id);
|
|
227
|
+
if (!mapping)
|
|
228
|
+
continue;
|
|
229
|
+
if (entry.kind === 'layout') {
|
|
230
|
+
if (Object.keys(mapping).length) {
|
|
231
|
+
throw new Error('[Bug] layout should not have slugs');
|
|
232
|
+
}
|
|
233
|
+
// Layouts never opt into shouldSkipObj — they must render on every request to
|
|
234
|
+
// enforce their auth/loader effects.
|
|
235
|
+
return {
|
|
236
|
+
component: entry.component,
|
|
237
|
+
kind: 'layout',
|
|
238
|
+
};
|
|
239
|
+
}
|
|
240
|
+
// Static pages opt into shouldSkipObj so the client can cache them across
|
|
241
|
+
// navigations. Dynamic pages don't (their content depends on slugs).
|
|
242
|
+
if (entry.isDynamic) {
|
|
243
|
+
unstable_setShouldSkip();
|
|
244
|
+
}
|
|
245
|
+
else {
|
|
246
|
+
unstable_setShouldSkip([]);
|
|
247
|
+
}
|
|
248
|
+
if (Object.keys(mapping).length === 0) {
|
|
249
|
+
return { component: entry.component, kind: 'page' };
|
|
250
|
+
}
|
|
251
|
+
const WrappedComponent = (props) => (0, react_1.createElement)(entry.component, { ...props, ...mapping });
|
|
252
|
+
return { component: WrappedComponent, kind: 'page' };
|
|
253
|
+
}
|
|
254
|
+
unstable_setShouldSkip([]);
|
|
255
|
+
return null;
|
|
256
|
+
});
|
|
257
|
+
}
|
|
258
|
+
//# sourceMappingURL=createPages.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"createPages.js","sourceRoot":"","sources":["../../../src/rsc/router/createPages.ts"],"names":[],"mappings":"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","sourcesContent":["import { matchDynamicName } from 'expo-router/internal/routing';\nimport type { RouteProps } from 'expo-router/internal/rsc';\nimport { createElement } from 'react';\nimport type { FunctionComponent, ReactNode } from 'react';\n\nimport { unstable_defineRouter } from './defineRouter';\nimport { getNamedParametrizedRoute } from '../../getNamedParametrizedRoute';\nimport type { BuildConfig } from '../server';\n\ntype ComponentKind = 'page' | 'layout';\ntype SlugMapping = Record<string, string | string[]>;\ntype IdMatcher = (id: string) => SlugMapping | null;\n\ntype Entry = {\n /** Registered path, may contain `[slug]`, `[...wildcard]`, or `(group)` segments. */\n path: string;\n component: FunctionComponent<any>;\n kind: ComponentKind;\n /** True if the path contains any slug or wildcard segments. */\n isDynamic: boolean;\n /** True if the path contains a wildcard `[...rest]` segment. */\n isWildcard: boolean;\n noSsr: boolean;\n matchId: IdMatcher;\n matchesPathname: (pathname: string) => boolean;\n};\n\nexport type CreatePageInput = {\n path: string;\n component: FunctionComponent<any>;\n render: 'static' | 'dynamic';\n staticPaths?: (string | string[])[];\n unstable_disableSSR?: boolean;\n};\n\nexport type CreateLayoutInput = {\n path: string;\n component: FunctionComponent<Omit<RouteProps, 'searchParams'> & { children: ReactNode }>;\n render: 'static' | 'dynamic';\n};\n\nexport type CreatePagesApi = {\n createPage: (page: CreatePageInput) => void;\n createLayout: (layout: CreateLayoutInput) => void;\n unstable_setBuildData: (path: string, data: unknown) => void;\n};\n\nexport type CreatePagesFn = (\n api: CreatePagesApi,\n opts: { unstable_buildConfig: BuildConfig | undefined }\n) => Promise<void>;\n\nfunction compilePathMatcher(path: string, suffix?: 'page' | 'layout'): IdMatcher {\n // Reuse expo-router-server's canonical regex builder so RSC matching agrees with\n // the URL manifest about brackets, group routes (optional), wildcards, and +not-found.\n const { namedParameterizedRoute, routeKeys, wildcardKeys } = getNamedParametrizedRoute(path);\n // Strip a trailing slash before appending the suffix so the root path doesn't\n // produce `//page` when concatenated.\n const base = namedParameterizedRoute.replace(/\\/$/, '');\n const regex = new RegExp(`^${suffix ? `${base}/${suffix}` : base}/?$`);\n return (target) => {\n // Targets are either IDs (`posts/123/page`) or pathnames (`/posts/123`).\n // The canonical regex expects a leading slash, so add one for IDs.\n const match = regex.exec(target.startsWith('/') ? target : '/' + target);\n if (!match) return null;\n const params: SlugMapping = {};\n for (const [cleanedKey, originalName] of Object.entries(routeKeys)) {\n const value = match.groups?.[cleanedKey];\n if (value === undefined) continue;\n params[originalName] = wildcardKeys.has(cleanedKey) ? value.split('/') : value;\n }\n return params;\n };\n}\n\nfunction buildMatchesPathname(path: string): (pathname: string) => boolean {\n const matcher = compilePathMatcher(path);\n return (pathname) => matcher(pathname) != null;\n}\n\nfunction isDynamicPath(path: string): boolean {\n return path.split('/').some((segment) => matchDynamicName(segment) != null);\n}\n\nfunction hasPathPrefix(prefix: string, path: string): boolean {\n return path === prefix || path.startsWith(prefix + '/');\n}\n\n/** Normalize a registration path to a URL-shaped pathname (always starts with `/`). */\nfunction normalizePath(path: string): string {\n if (path === '' || path === '/') return '/';\n return path.startsWith('/') ? path : '/' + path;\n}\n\nfunction sanitizeSlug(slug: string): string {\n return slug.replace(/\\./g, '').replace(/ /g, '-');\n}\n\n/**\n * Build an RSC router from a registration callback. Imitates `expo-server`'s\n * URL routing: each registered component carries a regex matcher, and the\n * resolver iterates the registry in specificity order, first match wins.\n * No exact-key lookup: this lets paths with `(group)` segments match runtime\n * IDs that don't include them.\n */\nexport function createPages(fn: CreatePagesFn): ReturnType<typeof unstable_defineRouter> {\n let configured = false;\n const entriesByKey = new Map<string, Entry>();\n const buildDataMap = new Map<string, unknown>();\n let sortedEntries: Entry[] = [];\n\n const register = (entry: Entry) => {\n const key = `${entry.kind}:${entry.path}`;\n const existing = entriesByKey.get(key);\n if (existing && existing.component !== entry.component) {\n throw new Error(`Duplicated component for ${entry.kind}: ${entry.path}`);\n }\n entriesByKey.set(key, entry);\n };\n\n const createPage = (page: CreatePageInput): void => {\n if (configured) {\n throw new Error('no longer available');\n }\n // Normalize once up-front: top-level `./index.tsx` arrives as `''`, and\n // everything downstream (the matcher, the registry key, the resolver) wants\n // a URL-shaped pathname.\n const path = normalizePath(page.path);\n const noSsr = !!page.unstable_disableSSR;\n const segments = path.split('/').filter(Boolean);\n let numSlugs = 0;\n let numWildcards = 0;\n for (const segment of segments) {\n const dynamic = matchDynamicName(segment);\n if (!dynamic) continue;\n numSlugs++;\n if (dynamic.deep) numWildcards++;\n }\n\n if (page.render === 'static' && numSlugs === 0) {\n register({\n path,\n component: page.component,\n kind: 'page',\n isDynamic: false,\n isWildcard: false,\n noSsr,\n matchId: compilePathMatcher(path, 'page'),\n matchesPathname: buildMatchesPathname(path),\n });\n return;\n }\n\n if (page.render === 'static' && numSlugs > 0) {\n if (!page.staticPaths) {\n throw new Error('staticPaths is required for static pages with slugs');\n }\n const staticPaths = page.staticPaths.map((item) =>\n (Array.isArray(item) ? item : [item]).map(sanitizeSlug)\n );\n for (const staticPath of staticPaths) {\n if (staticPath.length !== numSlugs && numWildcards === 0) {\n throw new Error('staticPaths does not match with slug pattern');\n }\n const mapping: SlugMapping = {};\n let slugIndex = 0;\n const pathItems: string[] = [];\n for (const segment of segments) {\n const dynamic = matchDynamicName(segment);\n if (!dynamic) {\n pathItems.push(segment);\n continue;\n }\n if (dynamic.deep) {\n mapping[dynamic.name] = staticPath.slice(slugIndex);\n staticPath.slice(slugIndex++).forEach((slug) => pathItems.push(slug));\n } else {\n pathItems.push(staticPath[slugIndex++]!);\n mapping[dynamic.name] = pathItems[pathItems.length - 1]!;\n }\n }\n const concretePath = '/' + pathItems.join('/');\n const WrappedComponent = (props: Record<string, unknown>) =>\n createElement(page.component as any, { ...props, ...mapping });\n register({\n path: concretePath,\n component: WrappedComponent,\n kind: 'page',\n isDynamic: false,\n isWildcard: false,\n noSsr,\n matchId: compilePathMatcher(concretePath, 'page'),\n matchesPathname: buildMatchesPathname(concretePath),\n });\n }\n return;\n }\n\n if (page.render === 'dynamic') {\n if (numWildcards > 1) {\n throw new Error('Invalid page configuration: ' + path);\n }\n register({\n path,\n component: page.component,\n kind: 'page',\n isDynamic: true,\n isWildcard: numWildcards === 1,\n noSsr,\n matchId: compilePathMatcher(path, 'page'),\n matchesPathname: buildMatchesPathname(path),\n });\n return;\n }\n\n throw new Error('Invalid page configuration: ' + path);\n };\n\n const createLayout = (layout: CreateLayoutInput): void => {\n if (configured) {\n throw new Error('no longer available');\n }\n if (layout.render !== 'static' && layout.render !== 'dynamic') {\n throw new Error('Invalid layout configuration');\n }\n const path = normalizePath(layout.path);\n register({\n path,\n component: layout.component as FunctionComponent<any>,\n kind: 'layout',\n isDynamic: layout.render === 'dynamic' || isDynamicPath(path),\n isWildcard: false,\n noSsr: false,\n matchId: compilePathMatcher(path, 'layout'),\n matchesPathname: buildMatchesPathname(path),\n });\n };\n\n const unstable_setBuildData = (path: string, data: unknown) => {\n // Key by the same normalized pathname `register` uses, so the lookup at\n // `buildDataMap.get(entry.path)` finds it regardless of caller convention.\n buildDataMap.set(normalizePath(path), data);\n };\n\n let ready: Promise<void> | undefined;\n const configure = async (buildConfig?: BuildConfig) => {\n if (!configured && !ready) {\n ready = fn(\n { createPage, createLayout, unstable_setBuildData },\n { unstable_buildConfig: buildConfig }\n );\n await ready;\n configured = true;\n // Resolver iterates this once per request and takes the first matchId hit.\n // Non-wildcard pages must out-rank wildcards so a more specific path wins; the\n // matcher's `/page` vs `/layout` suffix prevents cross-kind false matches, so\n // page-vs-layout order is irrelevant.\n sortedEntries = Array.from(entriesByKey.values()).sort(\n (a, b) => Number(a.isWildcard) - Number(b.isWildcard)\n );\n }\n await ready;\n };\n\n return unstable_defineRouter(\n async () => {\n await configure();\n const dynamicLayoutPaths: string[] = [];\n for (const entry of sortedEntries) {\n if (entry.kind === 'layout' && entry.isDynamic) dynamicLayoutPaths.push(entry.path);\n }\n const isUnderDynamicLayout = (pagePath: string) =>\n dynamicLayoutPaths.some((lp) => hasPathPrefix(lp, pagePath));\n\n const paths: {\n path: string;\n matchesPathname: (pathname: string) => boolean;\n isStatic: boolean;\n noSsr: boolean;\n data: unknown;\n }[] = [];\n for (const entry of sortedEntries) {\n if (entry.kind !== 'page') continue;\n paths.push({\n path: entry.path,\n matchesPathname: entry.matchesPathname,\n isStatic: !entry.isDynamic && !isUnderDynamicLayout(entry.path),\n noSsr: entry.noSsr,\n data: buildDataMap.get(entry.path),\n });\n }\n return paths;\n },\n async (id, { unstable_setShouldSkip, unstable_buildConfig }) => {\n await configure(unstable_buildConfig);\n for (const entry of sortedEntries) {\n const mapping = entry.matchId(id);\n if (!mapping) continue;\n if (entry.kind === 'layout') {\n if (Object.keys(mapping).length) {\n throw new Error('[Bug] layout should not have slugs');\n }\n // Layouts never opt into shouldSkipObj — they must render on every request to\n // enforce their auth/loader effects.\n return {\n component: entry.component as FunctionComponent<\n Omit<RouteProps, 'searchParams'> & { children: ReactNode }\n >,\n kind: 'layout',\n };\n }\n // Static pages opt into shouldSkipObj so the client can cache them across\n // navigations. Dynamic pages don't (their content depends on slugs).\n if (entry.isDynamic) {\n unstable_setShouldSkip();\n } else {\n unstable_setShouldSkip([]);\n }\n if (Object.keys(mapping).length === 0) {\n return { component: entry.component as FunctionComponent<RouteProps>, kind: 'page' };\n }\n const WrappedComponent = (props: Record<string, unknown>) =>\n createElement(entry.component, { ...props, ...mapping });\n return { component: WrappedComponent as FunctionComponent<RouteProps>, kind: 'page' };\n }\n unstable_setShouldSkip([]);\n return null;\n }\n );\n}\n"]}
|
|
@@ -7,23 +7,27 @@
|
|
|
7
7
|
*/
|
|
8
8
|
import { type RouteProps, type ShouldSkip } from 'expo-router/internal/rsc';
|
|
9
9
|
import type { FunctionComponent, ReactNode } from 'react';
|
|
10
|
-
import type { PathSpec } from '../path';
|
|
11
10
|
import type { BuildConfig, defineEntries } from '../server';
|
|
12
11
|
type RoutePropsForLayout = Omit<RouteProps, 'searchParams'> & {
|
|
13
12
|
children: ReactNode;
|
|
14
13
|
};
|
|
15
14
|
type ShouldSkipValue = ShouldSkip[number][1];
|
|
16
15
|
export declare function unstable_defineRouter(getPathConfig: () => Promise<Iterable<{
|
|
17
|
-
|
|
18
|
-
|
|
16
|
+
path: string;
|
|
17
|
+
matchesPathname: (pathname: string) => boolean;
|
|
19
18
|
isStatic?: boolean;
|
|
20
19
|
noSsr?: boolean;
|
|
21
20
|
data?: unknown;
|
|
22
|
-
}>>, getComponent: (componentId: string,
|
|
23
|
-
options: {
|
|
21
|
+
}>>, getComponent: (componentId: string, options: {
|
|
24
22
|
unstable_setShouldSkip: (val?: ShouldSkipValue) => void;
|
|
25
23
|
unstable_buildConfig: BuildConfig | undefined;
|
|
26
|
-
}) => Promise<
|
|
24
|
+
}) => Promise<{
|
|
25
|
+
component: FunctionComponent<RouteProps>;
|
|
26
|
+
kind: 'page';
|
|
27
|
+
} | {
|
|
28
|
+
component: FunctionComponent<RoutePropsForLayout>;
|
|
29
|
+
kind: 'layout';
|
|
30
|
+
} | null>): ReturnType<typeof defineEntries>;
|
|
27
31
|
export declare function unstable_redirect(pathname: string, searchParams?: URLSearchParams, skip?: string[]): void;
|
|
28
32
|
export {};
|
|
29
33
|
//# sourceMappingURL=defineRouter.d.ts.map
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"defineRouter.d.ts","sourceRoot":"","sources":["../../../src/rsc/router/defineRouter.ts"],"names":[],"mappings":"AAAA;;;;;;GAMG;AACH,OAAO,EAUL,KAAK,UAAU,EACf,KAAK,UAAU,EAChB,MAAM,0BAA0B,CAAC;AAClC,OAAO,KAAK,EAAkB,iBAAiB,EAAE,SAAS,EAAE,MAAM,OAAO,CAAC;AAI1E,OAAO,KAAK,
|
|
1
|
+
{"version":3,"file":"defineRouter.d.ts","sourceRoot":"","sources":["../../../src/rsc/router/defineRouter.ts"],"names":[],"mappings":"AAAA;;;;;;GAMG;AACH,OAAO,EAUL,KAAK,UAAU,EACf,KAAK,UAAU,EAChB,MAAM,0BAA0B,CAAC;AAClC,OAAO,KAAK,EAAkB,iBAAiB,EAAE,SAAS,EAAE,MAAM,OAAO,CAAC;AAI1E,OAAO,KAAK,EACV,WAAW,EAIX,aAAa,EACd,MAAM,WAAW,CAAC;AAEnB,KAAK,mBAAmB,GAAG,IAAI,CAAC,UAAU,EAAE,cAAc,CAAC,GAAG;IAC5D,QAAQ,EAAE,SAAS,CAAC;CACrB,CAAC;AAEF,KAAK,eAAe,GAAG,UAAU,CAAC,MAAM,CAAC,CAAC,CAAC,CAAC,CAAC;AAqB7C,wBAAgB,qBAAqB,CACnC,aAAa,EAAE,MAAM,OAAO,CAC1B,QAAQ,CAAC;IACP,IAAI,EAAE,MAAM,CAAC;IACb,eAAe,EAAE,CAAC,QAAQ,EAAE,MAAM,KAAK,OAAO,CAAC;IAC/C,QAAQ,CAAC,EAAE,OAAO,CAAC;IACnB,KAAK,CAAC,EAAE,OAAO,CAAC;IAChB,IAAI,CAAC,EAAE,OAAO,CAAC;CAChB,CAAC,CACH,EACD,YAAY,EAAE,CACZ,WAAW,EAAE,MAAM,EACnB,OAAO,EAAE;IAEP,sBAAsB,EAAE,CAAC,GAAG,CAAC,EAAE,eAAe,KAAK,IAAI,CAAC;IACxD,oBAAoB,EAAE,WAAW,GAAG,SAAS,CAAC;CAC/C,KACE,OAAO,CACR;IAAE,SAAS,EAAE,iBAAiB,CAAC,UAAU,CAAC,CAAC;IAAC,IAAI,EAAE,MAAM,CAAA;CAAE,GAC1D;IAAE,SAAS,EAAE,iBAAiB,CAAC,mBAAmB,CAAC,CAAC;IAAC,IAAI,EAAE,QAAQ,CAAA;CAAE,GACrE,IAAI,CACP,GACA,UAAU,CAAC,OAAO,aAAa,CAAC,CAsKlC;AAED,wBAAgB,iBAAiB,CAC/B,QAAQ,EAAE,MAAM,EAChB,YAAY,CAAC,EAAE,eAAe,EAC9B,IAAI,CAAC,EAAE,MAAM,EAAE,QAUhB"}
|