@tanstack/react-router 0.0.1-beta.269 → 0.0.1-beta.270
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/cjs/Matches.js +18 -42
- package/build/cjs/Matches.js.map +1 -1
- package/build/cjs/fileRoute.js.map +1 -1
- package/build/cjs/index.js +1 -1
- package/build/cjs/lazyRouteComponent.js.map +1 -1
- package/build/cjs/link.js.map +1 -1
- package/build/cjs/route.js.map +1 -1
- package/build/cjs/router.js +2 -4
- package/build/cjs/router.js.map +1 -1
- package/build/cjs/useNavigate.js +15 -4
- package/build/cjs/useNavigate.js.map +1 -1
- package/build/esm/index.js +486 -500
- package/build/esm/index.js.map +1 -1
- package/build/stats-html.html +1 -1
- package/build/stats-react.json +428 -434
- package/build/types/Matches.d.ts +5 -4
- package/build/types/fileRoute.d.ts +4 -4
- package/build/types/lazyRouteComponent.d.ts +2 -2
- package/build/types/link.d.ts +5 -5
- package/build/types/location.d.ts +0 -2
- package/build/types/route.d.ts +10 -39
- package/build/types/router.d.ts +9 -10
- package/build/types/useNavigate.d.ts +3 -4
- package/build/umd/index.development.js +486 -500
- package/build/umd/index.development.js.map +1 -1
- package/build/umd/index.production.js +1 -1
- package/build/umd/index.production.js.map +1 -1
- package/package.json +2 -2
- package/src/Matches.tsx +31 -66
- package/src/fileRoute.ts +1 -6
- package/src/lazyRouteComponent.tsx +2 -4
- package/src/link.tsx +5 -5
- package/src/location.ts +0 -2
- package/src/route.ts +11 -129
- package/src/router.ts +9 -31
- package/src/useNavigate.tsx +19 -18
|
@@ -909,6 +909,346 @@
|
|
|
909
909
|
.replace(/"/g, '\\"'); // Escape double quotes
|
|
910
910
|
}
|
|
911
911
|
|
|
912
|
+
const matchContext = /*#__PURE__*/React__namespace.createContext(undefined);
|
|
913
|
+
function Matches() {
|
|
914
|
+
const router = useRouter();
|
|
915
|
+
const matchId = useRouterState({
|
|
916
|
+
select: s => {
|
|
917
|
+
return getRenderedMatches(s)[0]?.id;
|
|
918
|
+
}
|
|
919
|
+
});
|
|
920
|
+
return /*#__PURE__*/React__namespace.createElement(matchContext.Provider, {
|
|
921
|
+
value: matchId
|
|
922
|
+
}, /*#__PURE__*/React__namespace.createElement(CatchBoundary, {
|
|
923
|
+
getResetKey: () => router.state.resolvedLocation.state?.key,
|
|
924
|
+
errorComponent: ErrorComponent,
|
|
925
|
+
onCatch: () => {
|
|
926
|
+
warning(false, `Error in router! Consider setting an 'errorComponent' in your RootRoute! 👍`);
|
|
927
|
+
}
|
|
928
|
+
}, matchId ? /*#__PURE__*/React__namespace.createElement(Match, {
|
|
929
|
+
matchId: matchId
|
|
930
|
+
}) : null));
|
|
931
|
+
}
|
|
932
|
+
function SafeFragment(props) {
|
|
933
|
+
return /*#__PURE__*/React__namespace.createElement(React__namespace.Fragment, null, props.children);
|
|
934
|
+
}
|
|
935
|
+
function Match({
|
|
936
|
+
matchId
|
|
937
|
+
}) {
|
|
938
|
+
const router = useRouter();
|
|
939
|
+
const routeId = useRouterState({
|
|
940
|
+
select: s => getRenderedMatches(s).find(d => d.id === matchId)?.routeId
|
|
941
|
+
});
|
|
942
|
+
invariant(routeId, `Could not find routeId for matchId "${matchId}". Please file an issue!`);
|
|
943
|
+
const route = router.routesById[routeId];
|
|
944
|
+
const PendingComponent = route.options.pendingComponent ?? router.options.defaultPendingComponent;
|
|
945
|
+
const routeErrorComponent = route.options.errorComponent ?? router.options.defaultErrorComponent ?? ErrorComponent;
|
|
946
|
+
const ResolvedSuspenseBoundary = route.options.wrapInSuspense ?? PendingComponent ?? route.options.component?.preload ?? route.options.pendingComponent?.preload ?? route.options.errorComponent?.preload ? React__namespace.Suspense : SafeFragment;
|
|
947
|
+
const ResolvedCatchBoundary = routeErrorComponent ? CatchBoundary : SafeFragment;
|
|
948
|
+
return /*#__PURE__*/React__namespace.createElement(matchContext.Provider, {
|
|
949
|
+
value: matchId
|
|
950
|
+
}, /*#__PURE__*/React__namespace.createElement(ResolvedSuspenseBoundary, {
|
|
951
|
+
fallback: PendingComponent
|
|
952
|
+
}, /*#__PURE__*/React__namespace.createElement(ResolvedCatchBoundary, {
|
|
953
|
+
getResetKey: () => router.state.resolvedLocation.state?.key,
|
|
954
|
+
errorComponent: routeErrorComponent,
|
|
955
|
+
onCatch: () => {
|
|
956
|
+
warning(false, `Error in route match: ${matchId}`);
|
|
957
|
+
}
|
|
958
|
+
}, /*#__PURE__*/React__namespace.createElement(MatchInner, {
|
|
959
|
+
matchId: matchId,
|
|
960
|
+
pendingElement: PendingComponent
|
|
961
|
+
}))));
|
|
962
|
+
}
|
|
963
|
+
function MatchInner({
|
|
964
|
+
matchId,
|
|
965
|
+
pendingElement
|
|
966
|
+
}) {
|
|
967
|
+
const router = useRouter();
|
|
968
|
+
const routeId = useRouterState({
|
|
969
|
+
select: s => getRenderedMatches(s).find(d => d.id === matchId)?.routeId
|
|
970
|
+
});
|
|
971
|
+
const route = router.routesById[routeId];
|
|
972
|
+
const match = useRouterState({
|
|
973
|
+
select: s => pick(getRenderedMatches(s).find(d => d.id === matchId), ['status', 'error', 'showPending', 'loadPromise'])
|
|
974
|
+
});
|
|
975
|
+
if (match.status === 'error') {
|
|
976
|
+
throw match.error;
|
|
977
|
+
}
|
|
978
|
+
if (match.status === 'pending') {
|
|
979
|
+
if (match.showPending) {
|
|
980
|
+
return pendingElement || null;
|
|
981
|
+
}
|
|
982
|
+
throw match.loadPromise;
|
|
983
|
+
}
|
|
984
|
+
if (match.status === 'success') {
|
|
985
|
+
let Comp = route.options.component ?? router.options.defaultComponent;
|
|
986
|
+
if (Comp) {
|
|
987
|
+
return /*#__PURE__*/React__namespace.createElement(Comp, null);
|
|
988
|
+
}
|
|
989
|
+
return /*#__PURE__*/React__namespace.createElement(Outlet, null);
|
|
990
|
+
}
|
|
991
|
+
invariant(false, 'Idle routeMatch status encountered during rendering! You should never see this. File an issue!');
|
|
992
|
+
}
|
|
993
|
+
const Outlet = /*#__PURE__*/React__namespace.memo(function Outlet() {
|
|
994
|
+
const matchId = React__namespace.useContext(matchContext);
|
|
995
|
+
const childMatchId = useRouterState({
|
|
996
|
+
select: s => {
|
|
997
|
+
const matches = getRenderedMatches(s);
|
|
998
|
+
const index = matches.findIndex(d => d.id === matchId);
|
|
999
|
+
return matches[index + 1]?.id;
|
|
1000
|
+
}
|
|
1001
|
+
});
|
|
1002
|
+
if (!childMatchId) {
|
|
1003
|
+
return null;
|
|
1004
|
+
}
|
|
1005
|
+
return /*#__PURE__*/React__namespace.createElement(Match, {
|
|
1006
|
+
matchId: childMatchId
|
|
1007
|
+
});
|
|
1008
|
+
});
|
|
1009
|
+
function useMatchRoute() {
|
|
1010
|
+
const {
|
|
1011
|
+
matchRoute
|
|
1012
|
+
} = useRouter();
|
|
1013
|
+
return React__namespace.useCallback(opts => {
|
|
1014
|
+
const {
|
|
1015
|
+
pending,
|
|
1016
|
+
caseSensitive,
|
|
1017
|
+
...rest
|
|
1018
|
+
} = opts;
|
|
1019
|
+
return matchRoute(rest, {
|
|
1020
|
+
pending,
|
|
1021
|
+
caseSensitive
|
|
1022
|
+
});
|
|
1023
|
+
}, []);
|
|
1024
|
+
}
|
|
1025
|
+
function MatchRoute(props) {
|
|
1026
|
+
const matchRoute = useMatchRoute();
|
|
1027
|
+
const params = matchRoute(props);
|
|
1028
|
+
if (typeof props.children === 'function') {
|
|
1029
|
+
return props.children(params);
|
|
1030
|
+
}
|
|
1031
|
+
return !!params ? props.children : null;
|
|
1032
|
+
}
|
|
1033
|
+
function getRenderedMatches(state) {
|
|
1034
|
+
return state.pendingMatches?.some(d => d.showPending) ? state.pendingMatches : state.matches;
|
|
1035
|
+
}
|
|
1036
|
+
function useMatch(opts) {
|
|
1037
|
+
const router = useRouter();
|
|
1038
|
+
const nearestMatchId = React__namespace.useContext(matchContext);
|
|
1039
|
+
const nearestMatchRouteId = getRenderedMatches(router.state).find(d => d.id === nearestMatchId)?.routeId;
|
|
1040
|
+
const matchRouteId = (() => {
|
|
1041
|
+
const matches = getRenderedMatches(router.state);
|
|
1042
|
+
const match = opts?.from ? matches.find(d => d.routeId === opts?.from) : matches.find(d => d.id === nearestMatchId);
|
|
1043
|
+
return match.routeId;
|
|
1044
|
+
})();
|
|
1045
|
+
if (opts?.strict ?? true) {
|
|
1046
|
+
invariant(nearestMatchRouteId == matchRouteId, `useMatch("${matchRouteId}") is being called in a component that is meant to render the '${nearestMatchRouteId}' route. Did you mean to 'useMatch("${matchRouteId}", { strict: false })' or 'useRoute("${matchRouteId}")' instead?`);
|
|
1047
|
+
}
|
|
1048
|
+
const matchSelection = useRouterState({
|
|
1049
|
+
select: state => {
|
|
1050
|
+
const match = getRenderedMatches(state).find(d => d.id === nearestMatchId);
|
|
1051
|
+
invariant(match, `Could not find ${opts?.from ? `an active match from "${opts.from}"` : 'a nearest match!'}`);
|
|
1052
|
+
return opts?.select ? opts.select(match) : match;
|
|
1053
|
+
}
|
|
1054
|
+
});
|
|
1055
|
+
return matchSelection;
|
|
1056
|
+
}
|
|
1057
|
+
function useMatches(opts) {
|
|
1058
|
+
return useRouterState({
|
|
1059
|
+
select: state => {
|
|
1060
|
+
let matches = getRenderedMatches(state);
|
|
1061
|
+
return opts?.select ? opts.select(matches) : matches;
|
|
1062
|
+
}
|
|
1063
|
+
});
|
|
1064
|
+
}
|
|
1065
|
+
function useParentMatches(opts) {
|
|
1066
|
+
const contextMatchId = React__namespace.useContext(matchContext);
|
|
1067
|
+
return useMatches({
|
|
1068
|
+
select: matches => {
|
|
1069
|
+
matches = matches.slice(matches.findIndex(d => d.id === contextMatchId));
|
|
1070
|
+
return opts?.select ? opts.select(matches) : matches;
|
|
1071
|
+
}
|
|
1072
|
+
});
|
|
1073
|
+
}
|
|
1074
|
+
function useLoaderData(opts) {
|
|
1075
|
+
return useMatch({
|
|
1076
|
+
...opts,
|
|
1077
|
+
select: s => {
|
|
1078
|
+
return typeof opts.select === 'function' ? opts.select(s?.loaderData) : s?.loaderData;
|
|
1079
|
+
}
|
|
1080
|
+
});
|
|
1081
|
+
}
|
|
1082
|
+
|
|
1083
|
+
const routerContext = /*#__PURE__*/React__namespace.createContext(null);
|
|
1084
|
+
if (typeof document !== 'undefined') {
|
|
1085
|
+
window.__TSR_ROUTER_CONTEXT__ = routerContext;
|
|
1086
|
+
}
|
|
1087
|
+
function RouterProvider({
|
|
1088
|
+
router,
|
|
1089
|
+
...rest
|
|
1090
|
+
}) {
|
|
1091
|
+
// Allow the router to update options on the router instance
|
|
1092
|
+
router.update({
|
|
1093
|
+
...router.options,
|
|
1094
|
+
...rest,
|
|
1095
|
+
context: {
|
|
1096
|
+
...router.options.context,
|
|
1097
|
+
...rest?.context
|
|
1098
|
+
}
|
|
1099
|
+
});
|
|
1100
|
+
const inner = /*#__PURE__*/React__namespace.createElement(routerContext.Provider, {
|
|
1101
|
+
value: router
|
|
1102
|
+
}, /*#__PURE__*/React__namespace.createElement(Matches, null), /*#__PURE__*/React__namespace.createElement(Transitioner, null));
|
|
1103
|
+
if (router.options.Wrap) {
|
|
1104
|
+
return /*#__PURE__*/React__namespace.createElement(router.options.Wrap, null, inner);
|
|
1105
|
+
}
|
|
1106
|
+
return inner;
|
|
1107
|
+
}
|
|
1108
|
+
function Transitioner() {
|
|
1109
|
+
const router = useRouter();
|
|
1110
|
+
const routerState = useRouterState({
|
|
1111
|
+
select: s => pick(s, ['isLoading', 'location', 'resolvedLocation', 'isTransitioning'])
|
|
1112
|
+
});
|
|
1113
|
+
const [isTransitioning, startReactTransition] = React__namespace.useTransition();
|
|
1114
|
+
router.startReactTransition = startReactTransition;
|
|
1115
|
+
React__namespace.useEffect(() => {
|
|
1116
|
+
if (isTransitioning) {
|
|
1117
|
+
router.__store.setState(s => ({
|
|
1118
|
+
...s,
|
|
1119
|
+
isTransitioning
|
|
1120
|
+
}));
|
|
1121
|
+
}
|
|
1122
|
+
}, [isTransitioning]);
|
|
1123
|
+
const tryLoad = () => {
|
|
1124
|
+
const apply = cb => {
|
|
1125
|
+
if (!routerState.isTransitioning) {
|
|
1126
|
+
startReactTransition(() => cb());
|
|
1127
|
+
} else {
|
|
1128
|
+
cb();
|
|
1129
|
+
}
|
|
1130
|
+
};
|
|
1131
|
+
apply(() => {
|
|
1132
|
+
try {
|
|
1133
|
+
router.load();
|
|
1134
|
+
} catch (err) {
|
|
1135
|
+
console.error(err);
|
|
1136
|
+
}
|
|
1137
|
+
});
|
|
1138
|
+
};
|
|
1139
|
+
useLayoutEffect$1(() => {
|
|
1140
|
+
const unsub = router.history.subscribe(() => {
|
|
1141
|
+
router.latestLocation = router.parseLocation(router.latestLocation);
|
|
1142
|
+
if (routerState.location !== router.latestLocation) {
|
|
1143
|
+
tryLoad();
|
|
1144
|
+
}
|
|
1145
|
+
});
|
|
1146
|
+
const nextLocation = router.buildLocation({
|
|
1147
|
+
search: true,
|
|
1148
|
+
params: true,
|
|
1149
|
+
hash: true,
|
|
1150
|
+
state: true
|
|
1151
|
+
});
|
|
1152
|
+
if (routerState.location.href !== nextLocation.href) {
|
|
1153
|
+
router.commitLocation({
|
|
1154
|
+
...nextLocation,
|
|
1155
|
+
replace: true
|
|
1156
|
+
});
|
|
1157
|
+
}
|
|
1158
|
+
return () => {
|
|
1159
|
+
unsub();
|
|
1160
|
+
};
|
|
1161
|
+
}, [router.history]);
|
|
1162
|
+
useLayoutEffect$1(() => {
|
|
1163
|
+
if (routerState.isTransitioning && !isTransitioning && !routerState.isLoading && routerState.resolvedLocation !== routerState.location) {
|
|
1164
|
+
router.emit({
|
|
1165
|
+
type: 'onResolved',
|
|
1166
|
+
fromLocation: routerState.resolvedLocation,
|
|
1167
|
+
toLocation: routerState.location,
|
|
1168
|
+
pathChanged: routerState.location.href !== routerState.resolvedLocation?.href
|
|
1169
|
+
});
|
|
1170
|
+
if (document.querySelector) {
|
|
1171
|
+
const el = document.getElementById(routerState.location.hash);
|
|
1172
|
+
if (el) {
|
|
1173
|
+
el.scrollIntoView();
|
|
1174
|
+
}
|
|
1175
|
+
}
|
|
1176
|
+
router.pendingMatches = [];
|
|
1177
|
+
router.__store.setState(s => ({
|
|
1178
|
+
...s,
|
|
1179
|
+
isTransitioning: false,
|
|
1180
|
+
resolvedLocation: s.location
|
|
1181
|
+
}));
|
|
1182
|
+
}
|
|
1183
|
+
}, [routerState.isTransitioning, isTransitioning, routerState.isLoading, routerState.resolvedLocation, routerState.location]);
|
|
1184
|
+
useLayoutEffect$1(() => {
|
|
1185
|
+
if (!window.__TSR_DEHYDRATED__) {
|
|
1186
|
+
tryLoad();
|
|
1187
|
+
}
|
|
1188
|
+
}, []);
|
|
1189
|
+
return null;
|
|
1190
|
+
}
|
|
1191
|
+
function getRouteMatch(state, id) {
|
|
1192
|
+
return [...(state.pendingMatches ?? []), ...state.matches].find(d => d.id === id);
|
|
1193
|
+
}
|
|
1194
|
+
function useRouterState(opts) {
|
|
1195
|
+
const router = useRouter();
|
|
1196
|
+
return useStore(router.__store, opts?.select);
|
|
1197
|
+
}
|
|
1198
|
+
function useRouter() {
|
|
1199
|
+
const resolvedContext = typeof document !== 'undefined' ? window.__TSR_ROUTER_CONTEXT__ || routerContext : routerContext;
|
|
1200
|
+
const value = React__namespace.useContext(resolvedContext);
|
|
1201
|
+
warning(value, 'useRouter must be used inside a <RouterProvider> component!');
|
|
1202
|
+
return value;
|
|
1203
|
+
}
|
|
1204
|
+
|
|
1205
|
+
function defer(_promise) {
|
|
1206
|
+
const promise = _promise;
|
|
1207
|
+
if (!promise.__deferredState) {
|
|
1208
|
+
promise.__deferredState = {
|
|
1209
|
+
uid: Math.random().toString(36).slice(2),
|
|
1210
|
+
status: 'pending'
|
|
1211
|
+
};
|
|
1212
|
+
const state = promise.__deferredState;
|
|
1213
|
+
promise.then(data => {
|
|
1214
|
+
state.status = 'success';
|
|
1215
|
+
state.data = data;
|
|
1216
|
+
}).catch(error => {
|
|
1217
|
+
state.status = 'error';
|
|
1218
|
+
state.error = error;
|
|
1219
|
+
});
|
|
1220
|
+
}
|
|
1221
|
+
return promise;
|
|
1222
|
+
}
|
|
1223
|
+
function isDehydratedDeferred(obj) {
|
|
1224
|
+
return typeof obj === 'object' && obj !== null && !(obj instanceof Promise) && !obj.then && '__deferredState' in obj;
|
|
1225
|
+
}
|
|
1226
|
+
|
|
1227
|
+
function useAwaited({
|
|
1228
|
+
promise
|
|
1229
|
+
}) {
|
|
1230
|
+
const router = useRouter();
|
|
1231
|
+
let state = promise.__deferredState;
|
|
1232
|
+
const key = `__TSR__DEFERRED__${state.uid}`;
|
|
1233
|
+
if (isDehydratedDeferred(promise)) {
|
|
1234
|
+
state = router.hydrateData(key);
|
|
1235
|
+
promise = Promise.resolve(state.data);
|
|
1236
|
+
promise.__deferredState = state;
|
|
1237
|
+
}
|
|
1238
|
+
if (state.status === 'pending') {
|
|
1239
|
+
throw new Promise(r => setTimeout(r, 1)).then(() => promise);
|
|
1240
|
+
}
|
|
1241
|
+
if (state.status === 'error') {
|
|
1242
|
+
throw state.error;
|
|
1243
|
+
}
|
|
1244
|
+
router.dehydrateData(key, state);
|
|
1245
|
+
return [state.data];
|
|
1246
|
+
}
|
|
1247
|
+
function Await(props) {
|
|
1248
|
+
const awaited = useAwaited(props);
|
|
1249
|
+
return props.children(...awaited);
|
|
1250
|
+
}
|
|
1251
|
+
|
|
912
1252
|
function joinPaths(paths) {
|
|
913
1253
|
return cleanPath(paths.filter(Boolean).join('/'));
|
|
914
1254
|
}
|
|
@@ -1084,133 +1424,47 @@
|
|
|
1084
1424
|
}
|
|
1085
1425
|
if (baseSegment.value.charAt(0) !== '$') {
|
|
1086
1426
|
params[routeSegment.value.substring(1)] = baseSegment.value;
|
|
1087
|
-
}
|
|
1088
|
-
}
|
|
1089
|
-
}
|
|
1090
|
-
if (!isLastBaseSegment && isLastRouteSegment) {
|
|
1091
|
-
params['**'] = joinPaths(baseSegments.slice(i + 1).map(d => d.value));
|
|
1092
|
-
return !!matchLocation.fuzzy && routeSegment?.value !== '/';
|
|
1093
|
-
}
|
|
1094
|
-
}
|
|
1095
|
-
return true;
|
|
1096
|
-
})();
|
|
1097
|
-
return isMatch ? params : undefined;
|
|
1098
|
-
}
|
|
1099
|
-
|
|
1100
|
-
function useParams(opts) {
|
|
1101
|
-
return useRouterState({
|
|
1102
|
-
select: state => {
|
|
1103
|
-
const params = last(state.matches)?.params;
|
|
1104
|
-
return opts?.select ? opts.select(params) : params;
|
|
1105
|
-
}
|
|
1106
|
-
});
|
|
1107
|
-
}
|
|
1108
|
-
|
|
1109
|
-
function useSearch(opts) {
|
|
1110
|
-
return useMatch({
|
|
1111
|
-
...opts,
|
|
1112
|
-
select: match => {
|
|
1113
|
-
return opts?.select ? opts.select(match.search) : match.search;
|
|
1114
|
-
}
|
|
1115
|
-
});
|
|
1116
|
-
}
|
|
1117
|
-
|
|
1118
|
-
const rootRouteId = '__root__';
|
|
1119
|
-
|
|
1120
|
-
// The parse type here allows a zod schema to be passed directly to the validator
|
|
1121
|
-
|
|
1122
|
-
class RouteApi {
|
|
1123
|
-
constructor({
|
|
1124
|
-
id
|
|
1125
|
-
}) {
|
|
1126
|
-
this.id = id;
|
|
1127
|
-
}
|
|
1128
|
-
useMatch = opts => {
|
|
1129
|
-
return useMatch({
|
|
1130
|
-
...opts,
|
|
1131
|
-
from: this.id
|
|
1132
|
-
});
|
|
1133
|
-
};
|
|
1134
|
-
useRouteContext = opts => {
|
|
1135
|
-
return useMatch({
|
|
1136
|
-
...opts,
|
|
1137
|
-
from: this.id,
|
|
1138
|
-
select: d => opts?.select ? opts.select(d.context) : d.context
|
|
1139
|
-
});
|
|
1140
|
-
};
|
|
1141
|
-
useSearch = opts => {
|
|
1142
|
-
return useSearch({
|
|
1143
|
-
...opts,
|
|
1144
|
-
from: this.id
|
|
1145
|
-
});
|
|
1146
|
-
};
|
|
1147
|
-
useParams = opts => {
|
|
1148
|
-
return useParams({
|
|
1149
|
-
...opts,
|
|
1150
|
-
from: this.id
|
|
1151
|
-
});
|
|
1152
|
-
};
|
|
1153
|
-
useLoaderData = opts => {
|
|
1154
|
-
return useLoaderData({
|
|
1155
|
-
...opts,
|
|
1156
|
-
from: this.id
|
|
1157
|
-
});
|
|
1158
|
-
};
|
|
1427
|
+
}
|
|
1428
|
+
}
|
|
1429
|
+
}
|
|
1430
|
+
if (!isLastBaseSegment && isLastRouteSegment) {
|
|
1431
|
+
params['**'] = joinPaths(baseSegments.slice(i + 1).map(d => d.value));
|
|
1432
|
+
return !!matchLocation.fuzzy && routeSegment?.value !== '/';
|
|
1433
|
+
}
|
|
1434
|
+
}
|
|
1435
|
+
return true;
|
|
1436
|
+
})();
|
|
1437
|
+
return isMatch ? params : undefined;
|
|
1159
1438
|
}
|
|
1160
|
-
class Route {
|
|
1161
|
-
// Set up in this.init()
|
|
1162
|
-
|
|
1163
|
-
// customId!: TCustomId
|
|
1164
|
-
|
|
1165
|
-
// Optional
|
|
1166
1439
|
|
|
1167
|
-
|
|
1168
|
-
|
|
1169
|
-
|
|
1170
|
-
|
|
1171
|
-
|
|
1172
|
-
}
|
|
1173
|
-
init = opts => {
|
|
1174
|
-
this.originalIndex = opts.originalIndex;
|
|
1175
|
-
const options = this.options;
|
|
1176
|
-
const isRoot = !options?.path && !options?.id;
|
|
1177
|
-
this.parentRoute = this.options?.getParentRoute?.();
|
|
1178
|
-
if (isRoot) {
|
|
1179
|
-
this.path = rootRouteId;
|
|
1180
|
-
} else {
|
|
1181
|
-
invariant(this.parentRoute, `Child Route instances must pass a 'getParentRoute: () => ParentRoute' option that returns a Route instance.`);
|
|
1440
|
+
function useParams(opts) {
|
|
1441
|
+
return useRouterState({
|
|
1442
|
+
select: state => {
|
|
1443
|
+
const params = last(state.matches)?.params;
|
|
1444
|
+
return opts?.select ? opts.select(params) : params;
|
|
1182
1445
|
}
|
|
1183
|
-
|
|
1446
|
+
});
|
|
1447
|
+
}
|
|
1184
1448
|
|
|
1185
|
-
|
|
1186
|
-
|
|
1187
|
-
|
|
1449
|
+
function useSearch(opts) {
|
|
1450
|
+
return useMatch({
|
|
1451
|
+
...opts,
|
|
1452
|
+
select: match => {
|
|
1453
|
+
return opts?.select ? opts.select(match.search) : match.search;
|
|
1188
1454
|
}
|
|
1189
|
-
|
|
1455
|
+
});
|
|
1456
|
+
}
|
|
1190
1457
|
|
|
1191
|
-
|
|
1192
|
-
|
|
1193
|
-
|
|
1194
|
-
|
|
1195
|
-
|
|
1196
|
-
|
|
1197
|
-
|
|
1198
|
-
|
|
1199
|
-
const fullPath = id === rootRouteId ? '/' : joinPaths([this.parentRoute.fullPath, path]);
|
|
1200
|
-
this.path = path;
|
|
1458
|
+
const rootRouteId = '__root__';
|
|
1459
|
+
|
|
1460
|
+
// The parse type here allows a zod schema to be passed directly to the validator
|
|
1461
|
+
|
|
1462
|
+
class RouteApi {
|
|
1463
|
+
constructor({
|
|
1464
|
+
id
|
|
1465
|
+
}) {
|
|
1201
1466
|
this.id = id;
|
|
1202
|
-
|
|
1203
|
-
this.fullPath = fullPath;
|
|
1204
|
-
this.to = fullPath;
|
|
1205
|
-
};
|
|
1206
|
-
addChildren = children => {
|
|
1207
|
-
this.children = children;
|
|
1208
|
-
return this;
|
|
1209
|
-
};
|
|
1210
|
-
update = options => {
|
|
1211
|
-
Object.assign(this.options, options);
|
|
1212
|
-
return this;
|
|
1213
|
-
};
|
|
1467
|
+
}
|
|
1214
1468
|
useMatch = opts => {
|
|
1215
1469
|
return useMatch({
|
|
1216
1470
|
...opts,
|
|
@@ -1243,393 +1497,115 @@
|
|
|
1243
1497
|
});
|
|
1244
1498
|
};
|
|
1245
1499
|
}
|
|
1246
|
-
|
|
1247
|
-
|
|
1248
|
-
|
|
1249
|
-
|
|
1250
|
-
|
|
1251
|
-
|
|
1252
|
-
|
|
1253
|
-
|
|
1254
|
-
|
|
1255
|
-
|
|
1256
|
-
|
|
1257
|
-
|
|
1258
|
-
|
|
1259
|
-
|
|
1260
|
-
|
|
1261
|
-
|
|
1262
|
-
|
|
1263
|
-
|
|
1264
|
-
|
|
1265
|
-
|
|
1266
|
-
|
|
1267
|
-
|
|
1268
|
-
}
|
|
1269
|
-
}
|
|
1270
|
-
|
|
1271
|
-
const matchContext = /*#__PURE__*/React__namespace.createContext(undefined);
|
|
1272
|
-
function Matches() {
|
|
1273
|
-
const router = useRouter();
|
|
1274
|
-
const matchId = useRouterState({
|
|
1275
|
-
select: s => {
|
|
1276
|
-
return getRenderedMatches(s)[0]?.id;
|
|
1277
|
-
}
|
|
1278
|
-
});
|
|
1279
|
-
const route = router.routesById[rootRouteId];
|
|
1280
|
-
const errorComponent = React__namespace.useCallback(props => {
|
|
1281
|
-
return /*#__PURE__*/React__namespace.createElement(ErrorComponent, {
|
|
1282
|
-
...props,
|
|
1283
|
-
useMatch: route.useMatch,
|
|
1284
|
-
useRouteContext: route.useRouteContext,
|
|
1285
|
-
useSearch: route.useSearch,
|
|
1286
|
-
useParams: route.useParams
|
|
1287
|
-
});
|
|
1288
|
-
}, [route]);
|
|
1289
|
-
return /*#__PURE__*/React__namespace.createElement(matchContext.Provider, {
|
|
1290
|
-
value: matchId
|
|
1291
|
-
}, /*#__PURE__*/React__namespace.createElement(CatchBoundary, {
|
|
1292
|
-
getResetKey: () => router.state.resolvedLocation.state?.key,
|
|
1293
|
-
errorComponent: errorComponent,
|
|
1294
|
-
onCatch: () => {
|
|
1295
|
-
warning(false, `Error in router! Consider setting an 'errorComponent' in your RootRoute! 👍`);
|
|
1296
|
-
}
|
|
1297
|
-
}, matchId ? /*#__PURE__*/React__namespace.createElement(Match, {
|
|
1298
|
-
matchId: matchId
|
|
1299
|
-
}) : null));
|
|
1300
|
-
}
|
|
1301
|
-
function SafeFragment(props) {
|
|
1302
|
-
return /*#__PURE__*/React__namespace.createElement(React__namespace.Fragment, null, props.children);
|
|
1303
|
-
}
|
|
1304
|
-
function Match({
|
|
1305
|
-
matchId
|
|
1306
|
-
}) {
|
|
1307
|
-
const router = useRouter();
|
|
1308
|
-
const routeId = useRouterState({
|
|
1309
|
-
select: s => getRenderedMatches(s).find(d => d.id === matchId)?.routeId
|
|
1310
|
-
});
|
|
1311
|
-
invariant(routeId, `Could not find routeId for matchId "${matchId}". Please file an issue!`);
|
|
1312
|
-
const route = router.routesById[routeId];
|
|
1313
|
-
const PendingComponent = route.options.pendingComponent ?? router.options.defaultPendingComponent;
|
|
1314
|
-
const pendingElement = PendingComponent ? /*#__PURE__*/React__namespace.createElement(PendingComponent, {
|
|
1315
|
-
useMatch: route.useMatch,
|
|
1316
|
-
useRouteContext: route.useRouteContext,
|
|
1317
|
-
useSearch: route.useSearch,
|
|
1318
|
-
useParams: route.useParams
|
|
1319
|
-
}) : undefined;
|
|
1320
|
-
const routeErrorComponent = route.options.errorComponent ?? router.options.defaultErrorComponent ?? ErrorComponent;
|
|
1321
|
-
const ResolvedSuspenseBoundary = route.options.wrapInSuspense ?? pendingElement ? React__namespace.Suspense : SafeFragment;
|
|
1322
|
-
const errorComponent = routeErrorComponent ? React__namespace.useCallback(props => {
|
|
1323
|
-
return /*#__PURE__*/React__namespace.createElement(routeErrorComponent, {
|
|
1324
|
-
...props,
|
|
1325
|
-
useMatch: route.useMatch,
|
|
1326
|
-
useRouteContext: route.useRouteContext,
|
|
1327
|
-
useSearch: route.useSearch,
|
|
1328
|
-
useParams: route.useParams
|
|
1329
|
-
});
|
|
1330
|
-
}, [route]) : undefined;
|
|
1331
|
-
const ResolvedCatchBoundary = errorComponent ? CatchBoundary : SafeFragment;
|
|
1332
|
-
return /*#__PURE__*/React__namespace.createElement(matchContext.Provider, {
|
|
1333
|
-
value: matchId
|
|
1334
|
-
}, /*#__PURE__*/React__namespace.createElement(ResolvedSuspenseBoundary, {
|
|
1335
|
-
fallback: pendingElement
|
|
1336
|
-
}, /*#__PURE__*/React__namespace.createElement(ResolvedCatchBoundary, {
|
|
1337
|
-
getResetKey: () => router.state.resolvedLocation.state?.key,
|
|
1338
|
-
errorComponent: errorComponent,
|
|
1339
|
-
onCatch: () => {
|
|
1340
|
-
warning(false, `Error in route match: ${matchId}`);
|
|
1341
|
-
}
|
|
1342
|
-
}, /*#__PURE__*/React__namespace.createElement(MatchInner, {
|
|
1343
|
-
matchId: matchId,
|
|
1344
|
-
pendingElement: pendingElement
|
|
1345
|
-
}))));
|
|
1346
|
-
}
|
|
1347
|
-
function MatchInner({
|
|
1348
|
-
matchId,
|
|
1349
|
-
pendingElement
|
|
1350
|
-
}) {
|
|
1351
|
-
const router = useRouter();
|
|
1352
|
-
const routeId = useRouterState({
|
|
1353
|
-
select: s => getRenderedMatches(s).find(d => d.id === matchId)?.routeId
|
|
1354
|
-
});
|
|
1355
|
-
const route = router.routesById[routeId];
|
|
1356
|
-
const match = useRouterState({
|
|
1357
|
-
select: s => pick(getRenderedMatches(s).find(d => d.id === matchId), ['status', 'error', 'showPending', 'loadPromise'])
|
|
1358
|
-
});
|
|
1359
|
-
if (match.status === 'error') {
|
|
1360
|
-
throw match.error;
|
|
1361
|
-
}
|
|
1362
|
-
if (match.status === 'pending') {
|
|
1363
|
-
if (match.showPending) {
|
|
1364
|
-
return pendingElement || null;
|
|
1365
|
-
}
|
|
1366
|
-
throw match.loadPromise;
|
|
1367
|
-
}
|
|
1368
|
-
if (match.status === 'success') {
|
|
1369
|
-
let comp = route.options.component ?? router.options.defaultComponent;
|
|
1370
|
-
if (comp) {
|
|
1371
|
-
return /*#__PURE__*/React__namespace.createElement(comp, {
|
|
1372
|
-
useMatch: route.useMatch,
|
|
1373
|
-
useRouteContext: route.useRouteContext,
|
|
1374
|
-
useSearch: route.useSearch,
|
|
1375
|
-
useParams: route.useParams,
|
|
1376
|
-
useLoaderData: route.useLoaderData
|
|
1377
|
-
});
|
|
1378
|
-
}
|
|
1379
|
-
return /*#__PURE__*/React__namespace.createElement(Outlet, null);
|
|
1380
|
-
}
|
|
1381
|
-
invariant(false, 'Idle routeMatch status encountered during rendering! You should never see this. File an issue!');
|
|
1382
|
-
}
|
|
1383
|
-
const Outlet = /*#__PURE__*/React__namespace.memo(function Outlet() {
|
|
1384
|
-
const matchId = React__namespace.useContext(matchContext);
|
|
1385
|
-
const childMatchId = useRouterState({
|
|
1386
|
-
select: s => {
|
|
1387
|
-
const matches = getRenderedMatches(s);
|
|
1388
|
-
const index = matches.findIndex(d => d.id === matchId);
|
|
1389
|
-
return matches[index + 1]?.id;
|
|
1390
|
-
}
|
|
1391
|
-
});
|
|
1392
|
-
if (!childMatchId) {
|
|
1393
|
-
return null;
|
|
1394
|
-
}
|
|
1395
|
-
return /*#__PURE__*/React__namespace.createElement(Match, {
|
|
1396
|
-
matchId: childMatchId
|
|
1397
|
-
});
|
|
1398
|
-
});
|
|
1399
|
-
function useMatchRoute() {
|
|
1400
|
-
const {
|
|
1401
|
-
matchRoute
|
|
1402
|
-
} = useRouter();
|
|
1403
|
-
return React__namespace.useCallback(opts => {
|
|
1404
|
-
const {
|
|
1405
|
-
pending,
|
|
1406
|
-
caseSensitive,
|
|
1407
|
-
...rest
|
|
1408
|
-
} = opts;
|
|
1409
|
-
return matchRoute(rest, {
|
|
1410
|
-
pending,
|
|
1411
|
-
caseSensitive
|
|
1412
|
-
});
|
|
1413
|
-
}, []);
|
|
1414
|
-
}
|
|
1415
|
-
function MatchRoute(props) {
|
|
1416
|
-
const matchRoute = useMatchRoute();
|
|
1417
|
-
const params = matchRoute(props);
|
|
1418
|
-
if (typeof props.children === 'function') {
|
|
1419
|
-
return props.children(params);
|
|
1420
|
-
}
|
|
1421
|
-
return !!params ? props.children : null;
|
|
1422
|
-
}
|
|
1423
|
-
function getRenderedMatches(state) {
|
|
1424
|
-
return state.pendingMatches?.some(d => d.showPending) ? state.pendingMatches : state.matches;
|
|
1425
|
-
}
|
|
1426
|
-
function useMatch(opts) {
|
|
1427
|
-
const router = useRouter();
|
|
1428
|
-
const nearestMatchId = React__namespace.useContext(matchContext);
|
|
1429
|
-
const nearestMatchRouteId = getRenderedMatches(router.state).find(d => d.id === nearestMatchId)?.routeId;
|
|
1430
|
-
const matchRouteId = (() => {
|
|
1431
|
-
const matches = getRenderedMatches(router.state);
|
|
1432
|
-
const match = opts?.from ? matches.find(d => d.routeId === opts?.from) : matches.find(d => d.id === nearestMatchId);
|
|
1433
|
-
return match.routeId;
|
|
1434
|
-
})();
|
|
1435
|
-
if (opts?.strict ?? true) {
|
|
1436
|
-
invariant(nearestMatchRouteId == matchRouteId, `useMatch("${matchRouteId}") is being called in a component that is meant to render the '${nearestMatchRouteId}' route. Did you mean to 'useMatch("${matchRouteId}", { strict: false })' or 'useRoute("${matchRouteId}")' instead?`);
|
|
1437
|
-
}
|
|
1438
|
-
const matchSelection = useRouterState({
|
|
1439
|
-
select: state => {
|
|
1440
|
-
const match = getRenderedMatches(state).find(d => d.id === nearestMatchId);
|
|
1441
|
-
invariant(match, `Could not find ${opts?.from ? `an active match from "${opts.from}"` : 'a nearest match!'}`);
|
|
1442
|
-
return opts?.select ? opts.select(match) : match;
|
|
1443
|
-
}
|
|
1444
|
-
});
|
|
1445
|
-
return matchSelection;
|
|
1446
|
-
}
|
|
1447
|
-
function useMatches(opts) {
|
|
1448
|
-
const contextMatchId = React__namespace.useContext(matchContext);
|
|
1449
|
-
return useRouterState({
|
|
1450
|
-
select: state => {
|
|
1451
|
-
let matches = getRenderedMatches(state);
|
|
1452
|
-
matches = matches.slice(matches.findIndex(d => d.id === contextMatchId));
|
|
1453
|
-
return opts?.select ? opts.select(matches) : matches;
|
|
1454
|
-
}
|
|
1455
|
-
});
|
|
1456
|
-
}
|
|
1457
|
-
function useLoaderData(opts) {
|
|
1458
|
-
return useMatch({
|
|
1459
|
-
...opts,
|
|
1460
|
-
select: s => {
|
|
1461
|
-
return typeof opts.select === 'function' ? opts.select(s?.loaderData) : s?.loaderData;
|
|
1500
|
+
class Route {
|
|
1501
|
+
// Set up in this.init()
|
|
1502
|
+
|
|
1503
|
+
// customId!: TCustomId
|
|
1504
|
+
|
|
1505
|
+
// Optional
|
|
1506
|
+
|
|
1507
|
+
constructor(options) {
|
|
1508
|
+
this.options = options || {};
|
|
1509
|
+
this.isRoot = !options?.getParentRoute;
|
|
1510
|
+
invariant(!(options?.id && options?.path), `Route cannot have both an 'id' and a 'path' option.`);
|
|
1511
|
+
this.$$typeof = Symbol.for('react.memo');
|
|
1512
|
+
}
|
|
1513
|
+
init = opts => {
|
|
1514
|
+
this.originalIndex = opts.originalIndex;
|
|
1515
|
+
const options = this.options;
|
|
1516
|
+
const isRoot = !options?.path && !options?.id;
|
|
1517
|
+
this.parentRoute = this.options?.getParentRoute?.();
|
|
1518
|
+
if (isRoot) {
|
|
1519
|
+
this.path = rootRouteId;
|
|
1520
|
+
} else {
|
|
1521
|
+
invariant(this.parentRoute, `Child Route instances must pass a 'getParentRoute: () => ParentRoute' option that returns a Route instance.`);
|
|
1462
1522
|
}
|
|
1463
|
-
|
|
1464
|
-
}
|
|
1523
|
+
let path = isRoot ? rootRouteId : options.path;
|
|
1465
1524
|
|
|
1466
|
-
|
|
1467
|
-
|
|
1468
|
-
|
|
1469
|
-
}
|
|
1470
|
-
function RouterProvider({
|
|
1471
|
-
router,
|
|
1472
|
-
...rest
|
|
1473
|
-
}) {
|
|
1474
|
-
// Allow the router to update options on the router instance
|
|
1475
|
-
router.update({
|
|
1476
|
-
...router.options,
|
|
1477
|
-
...rest,
|
|
1478
|
-
context: {
|
|
1479
|
-
...router.options.context,
|
|
1480
|
-
...rest?.context
|
|
1525
|
+
// If the path is anything other than an index path, trim it up
|
|
1526
|
+
if (path && path !== '/') {
|
|
1527
|
+
path = trimPath(path);
|
|
1481
1528
|
}
|
|
1482
|
-
|
|
1483
|
-
|
|
1484
|
-
|
|
1485
|
-
|
|
1486
|
-
|
|
1487
|
-
|
|
1488
|
-
}
|
|
1489
|
-
return inner;
|
|
1490
|
-
}
|
|
1491
|
-
function Transitioner() {
|
|
1492
|
-
const router = useRouter();
|
|
1493
|
-
const routerState = useRouterState({
|
|
1494
|
-
select: s => pick(s, ['isLoading', 'location', 'resolvedLocation', 'isTransitioning'])
|
|
1495
|
-
});
|
|
1496
|
-
const [isTransitioning, startReactTransition] = React__namespace.useTransition();
|
|
1497
|
-
router.startReactTransition = startReactTransition;
|
|
1498
|
-
React__namespace.useEffect(() => {
|
|
1499
|
-
if (isTransitioning) {
|
|
1500
|
-
router.__store.setState(s => ({
|
|
1501
|
-
...s,
|
|
1502
|
-
isTransitioning
|
|
1503
|
-
}));
|
|
1529
|
+
const customId = options?.id || path;
|
|
1530
|
+
|
|
1531
|
+
// Strip the parentId prefix from the first level of children
|
|
1532
|
+
let id = isRoot ? rootRouteId : joinPaths([this.parentRoute.id === rootRouteId ? '' : this.parentRoute.id, customId]);
|
|
1533
|
+
if (path === rootRouteId) {
|
|
1534
|
+
path = '/';
|
|
1504
1535
|
}
|
|
1505
|
-
|
|
1506
|
-
|
|
1507
|
-
|
|
1508
|
-
|
|
1509
|
-
|
|
1510
|
-
|
|
1511
|
-
|
|
1512
|
-
|
|
1513
|
-
|
|
1514
|
-
|
|
1515
|
-
|
|
1516
|
-
|
|
1517
|
-
|
|
1518
|
-
|
|
1519
|
-
|
|
1536
|
+
if (id !== rootRouteId) {
|
|
1537
|
+
id = joinPaths(['/', id]);
|
|
1538
|
+
}
|
|
1539
|
+
const fullPath = id === rootRouteId ? '/' : joinPaths([this.parentRoute.fullPath, path]);
|
|
1540
|
+
this.path = path;
|
|
1541
|
+
this.id = id;
|
|
1542
|
+
// this.customId = customId as TCustomId
|
|
1543
|
+
this.fullPath = fullPath;
|
|
1544
|
+
this.to = fullPath;
|
|
1545
|
+
};
|
|
1546
|
+
addChildren = children => {
|
|
1547
|
+
this.children = children;
|
|
1548
|
+
return this;
|
|
1549
|
+
};
|
|
1550
|
+
update = options => {
|
|
1551
|
+
Object.assign(this.options, options);
|
|
1552
|
+
return this;
|
|
1553
|
+
};
|
|
1554
|
+
useMatch = opts => {
|
|
1555
|
+
return useMatch({
|
|
1556
|
+
...opts,
|
|
1557
|
+
from: this.id
|
|
1520
1558
|
});
|
|
1521
1559
|
};
|
|
1522
|
-
|
|
1523
|
-
|
|
1524
|
-
|
|
1525
|
-
|
|
1526
|
-
|
|
1527
|
-
}
|
|
1560
|
+
useRouteContext = opts => {
|
|
1561
|
+
return useMatch({
|
|
1562
|
+
...opts,
|
|
1563
|
+
from: this.id,
|
|
1564
|
+
select: d => opts?.select ? opts.select(d.context) : d.context
|
|
1528
1565
|
});
|
|
1529
|
-
|
|
1530
|
-
|
|
1531
|
-
|
|
1532
|
-
|
|
1533
|
-
|
|
1566
|
+
};
|
|
1567
|
+
useSearch = opts => {
|
|
1568
|
+
return useSearch({
|
|
1569
|
+
...opts,
|
|
1570
|
+
from: this.id
|
|
1534
1571
|
});
|
|
1535
|
-
|
|
1536
|
-
|
|
1537
|
-
|
|
1538
|
-
|
|
1539
|
-
|
|
1540
|
-
}
|
|
1541
|
-
|
|
1542
|
-
|
|
1543
|
-
|
|
1544
|
-
|
|
1545
|
-
|
|
1546
|
-
|
|
1547
|
-
|
|
1548
|
-
type: 'onResolved',
|
|
1549
|
-
fromLocation: routerState.resolvedLocation,
|
|
1550
|
-
toLocation: routerState.location,
|
|
1551
|
-
pathChanged: routerState.location.href !== routerState.resolvedLocation?.href
|
|
1552
|
-
});
|
|
1553
|
-
if (document.querySelector) {
|
|
1554
|
-
const el = document.getElementById(routerState.location.hash);
|
|
1555
|
-
if (el) {
|
|
1556
|
-
el.scrollIntoView();
|
|
1557
|
-
}
|
|
1558
|
-
}
|
|
1559
|
-
router.pendingMatches = [];
|
|
1560
|
-
router.__store.setState(s => ({
|
|
1561
|
-
...s,
|
|
1562
|
-
isTransitioning: false,
|
|
1563
|
-
resolvedLocation: s.location
|
|
1564
|
-
}));
|
|
1565
|
-
}
|
|
1566
|
-
}, [routerState.isTransitioning, isTransitioning, routerState.isLoading, routerState.resolvedLocation, routerState.location]);
|
|
1567
|
-
useLayoutEffect$1(() => {
|
|
1568
|
-
if (!window.__TSR_DEHYDRATED__) {
|
|
1569
|
-
tryLoad();
|
|
1570
|
-
}
|
|
1571
|
-
}, []);
|
|
1572
|
-
return null;
|
|
1573
|
-
}
|
|
1574
|
-
function getRouteMatch(state, id) {
|
|
1575
|
-
return [...(state.pendingMatches ?? []), ...state.matches].find(d => d.id === id);
|
|
1576
|
-
}
|
|
1577
|
-
function useRouterState(opts) {
|
|
1578
|
-
const router = useRouter();
|
|
1579
|
-
return useStore(router.__store, opts?.select);
|
|
1572
|
+
};
|
|
1573
|
+
useParams = opts => {
|
|
1574
|
+
return useParams({
|
|
1575
|
+
...opts,
|
|
1576
|
+
from: this.id
|
|
1577
|
+
});
|
|
1578
|
+
};
|
|
1579
|
+
useLoaderData = opts => {
|
|
1580
|
+
return useLoaderData({
|
|
1581
|
+
...opts,
|
|
1582
|
+
from: this.id
|
|
1583
|
+
});
|
|
1584
|
+
};
|
|
1580
1585
|
}
|
|
1581
|
-
function
|
|
1582
|
-
|
|
1583
|
-
|
|
1584
|
-
|
|
1585
|
-
return value;
|
|
1586
|
+
function rootRouteWithContext() {
|
|
1587
|
+
return options => {
|
|
1588
|
+
return new RootRoute(options);
|
|
1589
|
+
};
|
|
1586
1590
|
}
|
|
1587
|
-
|
|
1588
|
-
|
|
1589
|
-
|
|
1590
|
-
if (!promise.__deferredState) {
|
|
1591
|
-
promise.__deferredState = {
|
|
1592
|
-
uid: Math.random().toString(36).slice(2),
|
|
1593
|
-
status: 'pending'
|
|
1594
|
-
};
|
|
1595
|
-
const state = promise.__deferredState;
|
|
1596
|
-
promise.then(data => {
|
|
1597
|
-
state.status = 'success';
|
|
1598
|
-
state.data = data;
|
|
1599
|
-
}).catch(error => {
|
|
1600
|
-
state.status = 'error';
|
|
1601
|
-
state.error = error;
|
|
1602
|
-
});
|
|
1591
|
+
class RootRoute extends Route {
|
|
1592
|
+
constructor(options) {
|
|
1593
|
+
super(options);
|
|
1603
1594
|
}
|
|
1604
|
-
return promise;
|
|
1605
1595
|
}
|
|
1606
|
-
function
|
|
1607
|
-
return
|
|
1596
|
+
function createRouteMask(opts) {
|
|
1597
|
+
return opts;
|
|
1608
1598
|
}
|
|
1609
1599
|
|
|
1610
|
-
|
|
1611
|
-
|
|
1612
|
-
|
|
1613
|
-
|
|
1614
|
-
|
|
1615
|
-
|
|
1616
|
-
|
|
1617
|
-
|
|
1618
|
-
promise = Promise.resolve(state.data);
|
|
1619
|
-
promise.__deferredState = state;
|
|
1620
|
-
}
|
|
1621
|
-
if (state.status === 'pending') {
|
|
1622
|
-
throw new Promise(r => setTimeout(r, 1)).then(() => promise);
|
|
1623
|
-
}
|
|
1624
|
-
if (state.status === 'error') {
|
|
1625
|
-
throw state.error;
|
|
1600
|
+
//
|
|
1601
|
+
|
|
1602
|
+
class NotFoundRoute extends Route {
|
|
1603
|
+
constructor(options) {
|
|
1604
|
+
super({
|
|
1605
|
+
...options,
|
|
1606
|
+
id: '404'
|
|
1607
|
+
});
|
|
1626
1608
|
}
|
|
1627
|
-
router.dehydrateData(key, state);
|
|
1628
|
-
return [state.data];
|
|
1629
|
-
}
|
|
1630
|
-
function Await(props) {
|
|
1631
|
-
const awaited = useAwaited(props);
|
|
1632
|
-
return props.children(...awaited);
|
|
1633
1609
|
}
|
|
1634
1610
|
|
|
1635
1611
|
class FileRoute {
|
|
@@ -2310,7 +2286,6 @@
|
|
|
2310
2286
|
status: hasLoaders ? 'pending' : 'success',
|
|
2311
2287
|
showPending: false,
|
|
2312
2288
|
isFetching: false,
|
|
2313
|
-
invalid: false,
|
|
2314
2289
|
error: undefined,
|
|
2315
2290
|
paramsError: parseErrors[index],
|
|
2316
2291
|
loadPromise: Promise.resolve(),
|
|
@@ -2629,7 +2604,6 @@
|
|
|
2629
2604
|
matches[index] = match = {
|
|
2630
2605
|
...match,
|
|
2631
2606
|
fetchedAt: Date.now(),
|
|
2632
|
-
invalid: false,
|
|
2633
2607
|
showPending: false
|
|
2634
2608
|
};
|
|
2635
2609
|
const pendingMs = route.options.pendingMs ?? this.options.defaultPendingMs;
|
|
@@ -2832,7 +2806,7 @@
|
|
|
2832
2806
|
|
|
2833
2807
|
//
|
|
2834
2808
|
;
|
|
2835
|
-
[[exitingMatchIds, 'onLeave'], [enteringMatchIds, 'onEnter'], [stayingMatchIds, '
|
|
2809
|
+
[[exitingMatchIds, 'onLeave'], [enteringMatchIds, 'onEnter'], [stayingMatchIds, 'onStay']].forEach(([matches, hook]) => {
|
|
2836
2810
|
matches.forEach(match => {
|
|
2837
2811
|
this.looseRoutesById[match.routeId].options[hook]?.(match);
|
|
2838
2812
|
});
|
|
@@ -2922,7 +2896,7 @@
|
|
|
2922
2896
|
dehydrate = () => {
|
|
2923
2897
|
return {
|
|
2924
2898
|
state: {
|
|
2925
|
-
dehydratedMatches: this.state.matches.map(d => pick(d, ['fetchedAt', '
|
|
2899
|
+
dehydratedMatches: this.state.matches.map(d => pick(d, ['fetchedAt', 'id', 'status', 'updatedAt', 'loaderData']))
|
|
2926
2900
|
}
|
|
2927
2901
|
};
|
|
2928
2902
|
};
|
|
@@ -3186,9 +3160,21 @@
|
|
|
3186
3160
|
});
|
|
3187
3161
|
}, []);
|
|
3188
3162
|
}
|
|
3189
|
-
|
|
3190
|
-
|
|
3191
|
-
|
|
3163
|
+
|
|
3164
|
+
// NOTE: I don't know of anyone using this. It's undocumented, so let's wait until someone needs it
|
|
3165
|
+
// export function typedNavigate<
|
|
3166
|
+
// TRouteTree extends AnyRoute = RegisteredRouter['routeTree'],
|
|
3167
|
+
// TDefaultFrom extends RoutePaths<TRouteTree> = '/',
|
|
3168
|
+
// >(navigate: (opts: NavigateOptions<any>) => Promise<void>) {
|
|
3169
|
+
// return navigate as <
|
|
3170
|
+
// TFrom extends RoutePaths<TRouteTree> = TDefaultFrom,
|
|
3171
|
+
// TTo extends string = '',
|
|
3172
|
+
// TMaskFrom extends RoutePaths<TRouteTree> = '/',
|
|
3173
|
+
// TMaskTo extends string = '',
|
|
3174
|
+
// >(
|
|
3175
|
+
// opts?: NavigateOptions<TRouteTree, TFrom, TTo, TMaskFrom, TMaskTo>,
|
|
3176
|
+
// ) => Promise<void>
|
|
3177
|
+
// } //
|
|
3192
3178
|
|
|
3193
3179
|
function Navigate(props) {
|
|
3194
3180
|
const {
|
|
@@ -3272,7 +3258,6 @@
|
|
|
3272
3258
|
exports.trimPath = trimPath;
|
|
3273
3259
|
exports.trimPathLeft = trimPathLeft;
|
|
3274
3260
|
exports.trimPathRight = trimPathRight;
|
|
3275
|
-
exports.typedNavigate = typedNavigate;
|
|
3276
3261
|
exports.useAwaited = useAwaited;
|
|
3277
3262
|
exports.useBlocker = useBlocker;
|
|
3278
3263
|
exports.useElementScrollRestoration = useElementScrollRestoration;
|
|
@@ -3284,6 +3269,7 @@
|
|
|
3284
3269
|
exports.useMatches = useMatches;
|
|
3285
3270
|
exports.useNavigate = useNavigate;
|
|
3286
3271
|
exports.useParams = useParams;
|
|
3272
|
+
exports.useParentMatches = useParentMatches;
|
|
3287
3273
|
exports.useRouteContext = useRouteContext;
|
|
3288
3274
|
exports.useRouter = useRouter;
|
|
3289
3275
|
exports.useRouterState = useRouterState;
|