UNPKG

react-router

Version:
1,448 lines (1,435 loc) • 115 kB
import { I as InitialEntry, T as To, i as RelativeRoutingType, w as NonIndexRouteObject, ag as LazyRouteFunction, q as IndexRouteObject, a as Location, A as Action, aD as Navigator, d as Router$1, V as RouterInit, aZ as FutureConfig$1, H as HydrationState, D as DataStrategyFunction, X as PatchRoutesOnNavigationFunction, p as RouteObject, aF as RouteMatch, o as Params, U as UIMatch, af as HTMLFormMethod, ad as FormEncType, a_ as RouteManifest, a$ as ServerRouteModule, z as MiddlewareEnabled, y as unstable_RouterContextProvider, x as AppLoadContext, ah as LoaderFunctionArgs, a7 as ActionFunctionArgs, e as RouteModules, Y as DataRouteObject, K as ClientLoaderFunction, a0 as StaticHandlerContext, aK as PageLinkDescriptor, b0 as History, $ as GetScrollRestorationKeyFunction, f as NavigateOptions, a1 as Fetcher, h as SerializeFrom, B as BlockerFunction, b1 as CreateStaticHandlerOptions$1, Z as StaticHandler } from './routeModules-BR2FO0ix.js'; import * as React from 'react'; declare function mapRouteProperties(route: RouteObject): Partial<RouteObject> & { hasErrorBoundary: boolean; }; declare const hydrationRouteProperties: (keyof RouteObject)[]; /** * @category Data Routers */ interface MemoryRouterOpts { /** * Basename path for the application. */ basename?: string; /** * Function to provide the initial context values for all client side * navigations/fetches */ unstable_getContext?: RouterInit["unstable_getContext"]; /** * Future flags to enable for the router. */ future?: Partial<FutureConfig$1>; /** * Hydration data to initialize the router with if you have already performed * data loading on the server. */ hydrationData?: HydrationState; /** * Initial entries in the in-memory history stack */ initialEntries?: InitialEntry[]; /** * Index of {@link initialEntries} the application should initialize to */ initialIndex?: number; /** * Override the default data strategy of loading in parallel. * Only intended for advanced usage. */ dataStrategy?: DataStrategyFunction; /** * Lazily define portions of the route tree on navigations. */ patchRoutesOnNavigation?: PatchRoutesOnNavigationFunction; } /** * Create a new {@link DataRouter} that manages the application path using an * in-memory [`History`](https://developer.mozilla.org/en-US/docs/Web/API/History) * stack. Useful for non-browser environments without a DOM API. * * @public * @category Data Routers * @mode data * @param routes Application routes * @param opts Options * @param {MemoryRouterOpts.basename} opts.basename n/a * @param {MemoryRouterOpts.dataStrategy} opts.dataStrategy n/a * @param {MemoryRouterOpts.future} opts.future n/a * @param {MemoryRouterOpts.unstable_getContext} opts.unstable_getContext n/a * @param {MemoryRouterOpts.hydrationData} opts.hydrationData n/a * @param {MemoryRouterOpts.initialEntries} opts.initialEntries n/a * @param {MemoryRouterOpts.initialIndex} opts.initialIndex n/a * @param {MemoryRouterOpts.patchRoutesOnNavigation} opts.patchRoutesOnNavigation n/a * @returns An initialized {@link DataRouter} to pass to {@link RouterProvider | `<RouterProvider>`} */ declare function createMemoryRouter(routes: RouteObject[], opts?: MemoryRouterOpts): Router$1; /** * @category Types */ interface RouterProviderProps { /** * The {@link DataRouter} instance to use for navigation and data fetching. */ router: Router$1; /** * The [`ReactDOM.flushSync`](https://react.dev/reference/react-dom/flushSync) * implementation to use for flushing updates. * * You usually don't have to worry about this: * - The `RouterProvider` exported from `react-router/dom` handles this internally for you * - If you are rendering in a non-DOM environment, you can import * `RouterProvider` from `react-router` and ignore this prop */ flushSync?: (fn: () => unknown) => undefined; } /** * Render the UI for the given {@link DataRouter}. This component should * typically be at the top of an app's element tree. * * @example * import { createBrowserRouter } from "react-router"; * import { RouterProvider } from "react-router/dom"; * import { createRoot } from "react-dom/client"; * * const router = createBrowserRouter(routes); * createRoot(document.getElementById("root")).render( * <RouterProvider router={router} /> * ); * * @public * @category Data Routers * @mode data * @param props Props * @param {RouterProviderProps.flushSync} props.flushSync n/a * @param {RouterProviderProps.router} props.router n/a * @returns React element for the rendered router */ declare function RouterProvider({ router, flushSync: reactDomFlushSyncImpl, }: RouterProviderProps): React.ReactElement; /** * @category Types */ interface MemoryRouterProps { /** * Application basename */ basename?: string; /** * Nested {@link Route} elements describing the route tree */ children?: React.ReactNode; /** * Initial entries in the in-memory history stack */ initialEntries?: InitialEntry[]; /** * Index of {@link initialEntries} the application should initialize to */ initialIndex?: number; } /** * A declarative {@link Router | `<Router>`} that stores all entries in memory. * * @public * @category Declarative Routers * @mode declarative * @param props Props * @param {MemoryRouterProps.basename} props.basename n/a * @param {MemoryRouterProps.children} props.children n/a * @param {MemoryRouterProps.initialEntries} props.initialEntries n/a * @param {MemoryRouterProps.initialIndex} props.initialIndex n/a * @returns A declarative in memory router for client side routing. */ declare function MemoryRouter({ basename, children, initialEntries, initialIndex, }: MemoryRouterProps): React.ReactElement; /** * @category Types */ interface NavigateProps { /** * The path to navigate to. This can be a string or a {@link Path} object */ to: To; /** * Whether to replace the current entry in the [`History`](https://developer.mozilla.org/en-US/docs/Web/API/History) * stack */ replace?: boolean; /** * State to pass to the new {@link Location} to store in [`history.state`](https://developer.mozilla.org/en-US/docs/Web/API/History/state). */ state?: any; /** * How to interpret relative routing in the {@link to} prop. * See {@link RelativeRoutingType}. */ relative?: RelativeRoutingType; } /** * A component-based version of {@link useNavigate} to use in a * [`React.Component` class](https://react.dev/reference/react/Component) where * hooks cannot be used. * * It's recommended to avoid using this component in favor of {@link useNavigate}. * * @example * <Navigate to="/tasks" /> * * @public * @category Components * @param props Props * @param {NavigateProps.relative} props.relative n/a * @param {NavigateProps.replace} props.replace n/a * @param {NavigateProps.state} props.state n/a * @param {NavigateProps.to} props.to n/a * @returns {void} * */ declare function Navigate({ to, replace, state, relative, }: NavigateProps): null; /** * @category Types */ interface OutletProps { /** * Provides a context value to the element tree below the outlet. Use when * the parent route needs to provide values to child routes. * * ```tsx * <Outlet context={myContextValue} /> * ``` * * Access the context with {@link useOutletContext}. */ context?: unknown; } /** * Renders the matching child route of a parent route or nothing if no child * route matches. * * @example * import { Outlet } from "react-router"; * * export default function SomeParent() { * return ( * <div> * <h1>Parent Content</h1> * <Outlet /> * </div> * ); * } * * @public * @category Components * @param props Props * @param {OutletProps.context} props.context n/a * @returns React element for the rendered outlet or `null` if no child route matches. */ declare function Outlet(props: OutletProps): React.ReactElement | null; /** * @category Types */ interface PathRouteProps { /** * Whether the path should be case-sensitive. Defaults to `false`. */ caseSensitive?: NonIndexRouteObject["caseSensitive"]; /** * The path pattern to match. If unspecified or empty, then this becomes a * layout route. */ path?: NonIndexRouteObject["path"]; /** * The unique identifier for this route (for use with {@link DataRouter}s) */ id?: NonIndexRouteObject["id"]; /** * A function that returns a promise that resolves to the route object. * Used for code-splitting routes. * See [`lazy`](../../start/data/route-object#lazy). */ lazy?: LazyRouteFunction<NonIndexRouteObject>; /** * The route loader. * See [`loader`](../../start/data/route-object#loader). */ loader?: NonIndexRouteObject["loader"]; /** * The route action. * See [`action`](../../start/data/route-object#action). */ action?: NonIndexRouteObject["action"]; hasErrorBoundary?: NonIndexRouteObject["hasErrorBoundary"]; /** * The route shouldRevalidate function. * See [`shouldRevalidate`](../../start/data/route-object#shouldRevalidate). */ shouldRevalidate?: NonIndexRouteObject["shouldRevalidate"]; /** * The route handle. */ handle?: NonIndexRouteObject["handle"]; /** * Whether this is an index route. */ index?: false; /** * Child Route components */ children?: React.ReactNode; /** * The React element to render when this Route matches. * Mutually exclusive with {@link Component}. */ element?: React.ReactNode | null; /** * The React element to render while this router is loading data. * Mutually exclusive with {@link HydrateFallback}. */ hydrateFallbackElement?: React.ReactNode | null; /** * The React element to render at this route if an error occurs. * Mutually exclusive with {@link ErrorBoundary}. */ errorElement?: React.ReactNode | null; /** * The React Component to render when this route matches. * Mutually exclusive with {@link element}. */ Component?: React.ComponentType | null; /** * The React Component to render while this router is loading data. * Mutually exclusive with {@link hydrateFallbackElement}. */ HydrateFallback?: React.ComponentType | null; /** * The React Component to render at this route if an error occurs. * Mutually exclusive with {@link errorElement}. */ ErrorBoundary?: React.ComponentType | null; } /** * @category Types */ interface LayoutRouteProps extends PathRouteProps { } /** * @category Types */ interface IndexRouteProps { /** * Whether the path should be case-sensitive. Defaults to `false`. */ caseSensitive?: IndexRouteObject["caseSensitive"]; /** * The path pattern to match. If unspecified or empty, then this becomes a * layout route. */ path?: IndexRouteObject["path"]; /** * The unique identifier for this route (for use with {@link DataRouter}s) */ id?: IndexRouteObject["id"]; /** * A function that returns a promise that resolves to the route object. * Used for code-splitting routes. * See [`lazy`](../../start/data/route-object#lazy). */ lazy?: LazyRouteFunction<IndexRouteObject>; /** * The route loader. * See [`loader`](../../start/data/route-object#loader). */ loader?: IndexRouteObject["loader"]; /** * The route action. * See [`action`](../../start/data/route-object#action). */ action?: IndexRouteObject["action"]; hasErrorBoundary?: IndexRouteObject["hasErrorBoundary"]; /** * The route shouldRevalidate function. * See [`shouldRevalidate`](../../start/data/route-object#shouldRevalidate). */ shouldRevalidate?: IndexRouteObject["shouldRevalidate"]; /** * The route handle. */ handle?: IndexRouteObject["handle"]; /** * Whether this is an index route. */ index: true; /** * Child Route components */ children?: undefined; /** * The React element to render when this Route matches. * Mutually exclusive with {@link Component}. */ element?: React.ReactNode | null; /** * The React element to render while this router is loading data. * Mutually exclusive with {@link HydrateFallback}. */ hydrateFallbackElement?: React.ReactNode | null; /** * The React element to render at this route if an error occurs. * Mutually exclusive with {@link ErrorBoundary}. */ errorElement?: React.ReactNode | null; /** * The React Component to render when this route matches. * Mutually exclusive with {@link element}. */ Component?: React.ComponentType | null; /** * The React Component to render while this router is loading data. * Mutually exclusive with {@link hydrateFallbackElement}. */ HydrateFallback?: React.ComponentType | null; /** * The React Component to render at this route if an error occurs. * Mutually exclusive with {@link errorElement}. */ ErrorBoundary?: React.ComponentType | null; } type RouteProps = PathRouteProps | LayoutRouteProps | IndexRouteProps; /** * Configures an element to render when a pattern matches the current location. * It must be rendered within a {@link Routes} element. Note that these routes * do not participate in data loading, actions, code splitting, or any other * route module features. * * @example * // Usually used in a declarative router * function App() { * return ( * <BrowserRouter> * <Routes> * <Route index element={<StepOne />} /> * <Route path="step-2" element={<StepTwo />} /> * <Route path="step-3" element={<StepThree />} /> * </Routes> * </BrowserRouter> * ); * } * * // But can be used with a data router as well if you prefer the JSX notation * const routes = createRoutesFromElements( * <> * <Route index loader={step1Loader} Component={StepOne} /> * <Route path="step-2" loader={step2Loader} Component={StepTwo} /> * <Route path="step-3" loader={step3Loader} Component={StepThree} /> * </> * ); * * const router = createBrowserRouter(routes); * * function App() { * return <RouterProvider router={router} />; * } * * @public * @category Components * @param props Props * @param {PathRouteProps.action} props.action n/a * @param {PathRouteProps.caseSensitive} props.caseSensitive n/a * @param {PathRouteProps.Component} props.Component n/a * @param {PathRouteProps.children} props.children n/a * @param {PathRouteProps.element} props.element n/a * @param {PathRouteProps.ErrorBoundary} props.ErrorBoundary n/a * @param {PathRouteProps.errorElement} props.errorElement n/a * @param {PathRouteProps.handle} props.handle n/a * @param {PathRouteProps.HydrateFallback} props.HydrateFallback n/a * @param {PathRouteProps.hydrateFallbackElement} props.hydrateFallbackElement n/a * @param {PathRouteProps.id} props.id n/a * @param {PathRouteProps.index} props.index n/a * @param {PathRouteProps.lazy} props.lazy n/a * @param {PathRouteProps.loader} props.loader n/a * @param {PathRouteProps.path} props.path n/a * @param {PathRouteProps.shouldRevalidate} props.shouldRevalidate n/a * @returns {void} */ declare function Route$1(props: RouteProps): React.ReactElement | null; /** * @category Types */ interface RouterProps { /** * The base path for the application. This is prepended to all locations */ basename?: string; /** * Nested {@link Route} elements describing the route tree */ children?: React.ReactNode; /** * The location to match against. Defaults to the current location. * This can be a string or a {@link Location} object. */ location: Partial<Location> | string; /** * The type of navigation that triggered this location change. * Defaults to {@link NavigationType.Pop}. */ navigationType?: Action; /** * The navigator to use for navigation. This is usually a history object * or a custom navigator that implements the {@link Navigator} interface. */ navigator: Navigator; /** * Whether this router is static or not (used for SSR). If `true`, the router * will not be reactive to location changes. */ static?: boolean; } /** * Provides location context for the rest of the app. * * Note: You usually won't render a `<Router>` directly. Instead, you'll render a * router that is more specific to your environment such as a {@link BrowserRouter} * in web browsers or a {@link ServerRouter} for server rendering. * * @public * @category Declarative Routers * @mode declarative * @param props Props * @param {RouterProps.basename} props.basename n/a * @param {RouterProps.children} props.children n/a * @param {RouterProps.location} props.location n/a * @param {RouterProps.navigationType} props.navigationType n/a * @param {RouterProps.navigator} props.navigator n/a * @param {RouterProps.static} props.static n/a * @returns React element for the rendered router or `null` if the location does * not match the {@link props.basename} */ declare function Router({ basename: basenameProp, children, location: locationProp, navigationType, navigator, static: staticProp, }: RouterProps): React.ReactElement | null; /** * @category Types */ interface RoutesProps { /** * Nested {@link Route} elements */ children?: React.ReactNode; /** * The {@link Location} to match against. Defaults to the current location. */ location?: Partial<Location> | string; } /** * Renders a branch of {@link Route | `<Route>`s} that best matches the current * location. Note that these routes do not participate in [data loading](../../start/framework/route-module#loader), * [`action`](../../start/framework/route-module#action), code splitting, or * any other [route module](../../start/framework/route-module) features. * * @example * import { Route, Routes } from "react-router"; * * <Routes> * <Route index element={<StepOne />} /> * <Route path="step-2" element={<StepTwo />} /> * <Route path="step-3" element={<StepThree />}> * </Routes> * * @public * @category Components * @param props Props * @param {RoutesProps.children} props.children n/a * @param {RoutesProps.location} props.location n/a * @returns React element for the rendered routes or `null` if no route matches */ declare function Routes({ children, location, }: RoutesProps): React.ReactElement | null; interface AwaitResolveRenderFunction<Resolve = any> { (data: Awaited<Resolve>): React.ReactNode; } /** * @category Types */ interface AwaitProps<Resolve> { /** * When using a function, the resolved value is provided as the parameter. * * ```tsx [2] * <Await resolve={reviewsPromise}> * {(resolvedReviews) => <Reviews items={resolvedReviews} />} * </Await> * ``` * * When using React elements, {@link useAsyncValue} will provide the * resolved value: * * ```tsx [2] * <Await resolve={reviewsPromise}> * <Reviews /> * </Await> * * function Reviews() { * const resolvedReviews = useAsyncValue(); * return <div>...</div>; * } * ``` */ children: React.ReactNode | AwaitResolveRenderFunction<Resolve>; /** * The error element renders instead of the `children` when the [`Promise`](https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Promise) * rejects. * * ```tsx * <Await * errorElement={<div>Oops</div>} * resolve={reviewsPromise} * > * <Reviews /> * </Await> * ``` * * To provide a more contextual error, you can use the {@link useAsyncError} in a * child component * * ```tsx * <Await * errorElement={<ReviewsError />} * resolve={reviewsPromise} * > * <Reviews /> * </Await> * * function ReviewsError() { * const error = useAsyncError(); * return <div>Error loading reviews: {error.message}</div>; * } * ``` * * If you do not provide an `errorElement`, the rejected value will bubble up * to the nearest route-level [`ErrorBoundary`](../../start/framework/route-module#errorboundary) * and be accessible via the {@link useRouteError} hook. */ errorElement?: React.ReactNode; /** * Takes a [`Promise`](https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Promise) * returned from a [`loader`](../../start/framework/route-module#loader) to be * resolved and rendered. * * ```tsx * import { Await, useLoaderData } from "react-router"; * * export async function loader() { * let reviews = getReviews(); // not awaited * let book = await getBook(); * return { * book, * reviews, // this is a promise * }; * } * * export default function Book() { * const { * book, * reviews, // this is the same promise * } = useLoaderData(); * * return ( * <div> * <h1>{book.title}</h1> * <p>{book.description}</p> * <React.Suspense fallback={<ReviewsSkeleton />}> * <Await * // and is the promise we pass to Await * resolve={reviews} * > * <Reviews /> * </Await> * </React.Suspense> * </div> * ); * } * ``` */ resolve: Resolve; } /** * Used to render promise values with automatic error handling. * * **Note:** `<Await>` expects to be rendered inside a [`<React.Suspense>`](https://react.dev/reference/react/Suspense) * * @example * import { Await, useLoaderData } from "react-router"; * * export async function loader() { * // not awaited * const reviews = getReviews(); * // awaited (blocks the transition) * const book = await fetch("/api/book").then((res) => res.json()); * return { book, reviews }; * } * * function Book() { * const { book, reviews } = useLoaderData(); * return ( * <div> * <h1>{book.title}</h1> * <p>{book.description}</p> * <React.Suspense fallback={<ReviewsSkeleton />}> * <Await * resolve={reviews} * errorElement={ * <div>Could not load reviews 😬</div> * } * children={(resolvedReviews) => ( * <Reviews items={resolvedReviews} /> * )} * /> * </React.Suspense> * </div> * ); * } * * @public * @category Components * @mode framework * @mode data * @param props Props * @param {AwaitProps.children} props.children n/a * @param {AwaitProps.errorElement} props.errorElement n/a * @param {AwaitProps.resolve} props.resolve n/a * @returns React element for the rendered awaited value */ declare function Await<Resolve>({ children, errorElement, resolve, }: AwaitProps<Resolve>): React.JSX.Element; /** * Creates a route config from a React "children" object, which is usually * either a `<Route>` element or an array of them. Used internally by * `<Routes>` to create a route config from its children. * * @category Utils * @mode data * @param children The React children to convert into a route config * @param parentPath The path of the parent route, used to generate unique IDs. * @returns An array of {@link RouteObject}s that can be used with a {@link DataRouter} */ declare function createRoutesFromChildren(children: React.ReactNode, parentPath?: number[]): RouteObject[]; /** * Create route objects from JSX elements instead of arrays of objects. * * @example * const routes = createRoutesFromElements( * <> * <Route index loader={step1Loader} Component={StepOne} /> * <Route path="step-2" loader={step2Loader} Component={StepTwo} /> * <Route path="step-3" loader={step3Loader} Component={StepThree} /> * </> * ); * * const router = createBrowserRouter(routes); * * function App() { * return <RouterProvider router={router} />; * } * * @name createRoutesFromElements * @public * @category Utils * @mode data * @param children The React children to convert into a route config * @param parentPath The path of the parent route, used to generate unique IDs. * This is used for internal recursion and is not intended to be used by the * application developer. * @returns An array of {@link RouteObject}s that can be used with a {@link DataRouter} */ declare const createRoutesFromElements: typeof createRoutesFromChildren; /** * Renders the result of {@link matchRoutes} into a React element. * * @public * @category Utils * @param matches The array of {@link RouteMatch | route matches} to render * @returns A React element that renders the matched routes or `null` if no matches */ declare function renderMatches(matches: RouteMatch[] | null): React.ReactElement | null; declare function useRouteComponentProps(): { params: Readonly<Params<string>>; loaderData: any; actionData: any; matches: UIMatch<unknown, unknown>[]; }; type RouteComponentProps = ReturnType<typeof useRouteComponentProps>; type RouteComponentType = React.ComponentType<RouteComponentProps>; declare function WithComponentProps({ children, }: { children: React.ReactElement; }): React.ReactElement<any, string | React.JSXElementConstructor<any>>; declare function withComponentProps(Component: RouteComponentType): () => React.ReactElement<{ params: Readonly<Params<string>>; loaderData: any; actionData: any; matches: UIMatch<unknown, unknown>[]; }, string | React.JSXElementConstructor<any>>; declare function useHydrateFallbackProps(): { params: Readonly<Params<string>>; loaderData: any; actionData: any; }; type HydrateFallbackProps = ReturnType<typeof useHydrateFallbackProps>; type HydrateFallbackType = React.ComponentType<HydrateFallbackProps>; declare function WithHydrateFallbackProps({ children, }: { children: React.ReactElement; }): React.ReactElement<any, string | React.JSXElementConstructor<any>>; declare function withHydrateFallbackProps(HydrateFallback: HydrateFallbackType): () => React.ReactElement<{ params: Readonly<Params<string>>; loaderData: any; actionData: any; }, string | React.JSXElementConstructor<any>>; declare function useErrorBoundaryProps(): { params: Readonly<Params<string>>; loaderData: any; actionData: any; error: unknown; }; type ErrorBoundaryProps = ReturnType<typeof useErrorBoundaryProps>; type ErrorBoundaryType = React.ComponentType<ErrorBoundaryProps>; declare function WithErrorBoundaryProps({ children, }: { children: React.ReactElement; }): React.ReactElement<any, string | React.JSXElementConstructor<any>>; declare function withErrorBoundaryProps(ErrorBoundary: ErrorBoundaryType): () => React.ReactElement<{ params: Readonly<Params<string>>; loaderData: any; actionData: any; error: unknown; }, string | React.JSXElementConstructor<any>>; type ParamKeyValuePair = [string, string]; type URLSearchParamsInit = string | ParamKeyValuePair[] | Record<string, string | string[]> | URLSearchParams; /** Creates a URLSearchParams object using the given initializer. This is identical to `new URLSearchParams(init)` except it also supports arrays as values in the object form of the initializer instead of just strings. This is convenient when you need multiple values for a given key, but don't want to use an array initializer. For example, instead of: ```tsx let searchParams = new URLSearchParams([ ['sort', 'name'], ['sort', 'price'] ]); ``` you can do: ``` let searchParams = createSearchParams({ sort: ['name', 'price'] }); ``` @category Utils */ declare function createSearchParams(init?: URLSearchParamsInit): URLSearchParams; type JsonObject = { [Key in string]: JsonValue; } & { [Key in string]?: JsonValue | undefined; }; type JsonArray = JsonValue[] | readonly JsonValue[]; type JsonPrimitive = string | number | boolean | null; type JsonValue = JsonPrimitive | JsonObject | JsonArray; type SubmitTarget = HTMLFormElement | HTMLButtonElement | HTMLInputElement | FormData | URLSearchParams | JsonValue | null; /** * Submit options shared by both navigations and fetchers */ interface SharedSubmitOptions { /** * The HTTP method used to submit the form. Overrides `<form method>`. * Defaults to "GET". */ method?: HTMLFormMethod; /** * The action URL path used to submit the form. Overrides `<form action>`. * Defaults to the path of the current route. */ action?: string; /** * The encoding used to submit the form. Overrides `<form encType>`. * Defaults to "application/x-www-form-urlencoded". */ encType?: FormEncType; /** * Determines whether the form action is relative to the route hierarchy or * the pathname. Use this if you want to opt out of navigating the route * hierarchy and want to instead route based on /-delimited URL segments */ relative?: RelativeRoutingType; /** * In browser-based environments, prevent resetting scroll after this * navigation when using the <ScrollRestoration> component */ preventScrollReset?: boolean; /** * Enable flushSync for this submission's state updates */ flushSync?: boolean; } /** * Submit options available to fetchers */ interface FetcherSubmitOptions extends SharedSubmitOptions { } /** * Submit options available to navigations */ interface SubmitOptions extends FetcherSubmitOptions { /** * Set `true` to replace the current entry in the browser's history stack * instead of creating a new one (i.e. stay on "the same page"). Defaults * to `false`. */ replace?: boolean; /** * State object to add to the history stack entry for this navigation */ state?: any; /** * Indicate a specific fetcherKey to use when using navigate=false */ fetcherKey?: string; /** * navigate=false will use a fetcher instead of a navigation */ navigate?: boolean; /** * Enable view transitions on this submission navigation */ viewTransition?: boolean; } type ServerRouteManifest = RouteManifest<Omit<ServerRoute, "children">>; interface ServerRoute extends Route { children: ServerRoute[]; module: ServerRouteModule; } type OptionalCriticalCss = CriticalCss | undefined; /** * The output of the compiler for the server build. */ interface ServerBuild { entry: { module: ServerEntryModule; }; routes: ServerRouteManifest; assets: AssetsManifest; basename?: string; publicPath: string; assetsBuildDirectory: string; future: FutureConfig; ssr: boolean; unstable_getCriticalCss?: (args: { pathname: string; }) => OptionalCriticalCss | Promise<OptionalCriticalCss>; /** * @deprecated This is now done via a custom header during prerendering */ isSpaMode: boolean; prerender: string[]; routeDiscovery: { mode: "lazy" | "initial"; manifestPath: string; }; } interface HandleDocumentRequestFunction { (request: Request, responseStatusCode: number, responseHeaders: Headers, context: EntryContext, loadContext: MiddlewareEnabled extends true ? unstable_RouterContextProvider : AppLoadContext): Promise<Response> | Response; } interface HandleDataRequestFunction { (response: Response, args: LoaderFunctionArgs | ActionFunctionArgs): Promise<Response> | Response; } interface HandleErrorFunction { (error: unknown, args: LoaderFunctionArgs | ActionFunctionArgs): void; } /** * A module that serves as the entry point for a Remix app during server * rendering. */ interface ServerEntryModule { default: HandleDocumentRequestFunction; handleDataRequest?: HandleDataRequestFunction; handleError?: HandleErrorFunction; streamTimeout?: number; } interface Route { index?: boolean; caseSensitive?: boolean; id: string; parentId?: string; path?: string; } interface EntryRoute extends Route { hasAction: boolean; hasLoader: boolean; hasClientAction: boolean; hasClientLoader: boolean; hasClientMiddleware: boolean; hasErrorBoundary: boolean; imports?: string[]; css?: string[]; module: string; clientActionModule: string | undefined; clientLoaderModule: string | undefined; clientMiddlewareModule: string | undefined; hydrateFallbackModule: string | undefined; parentId?: string; } declare function createClientRoutesWithHMRRevalidationOptOut(needsRevalidation: Set<string>, manifest: RouteManifest<EntryRoute>, routeModulesCache: RouteModules, initialState: HydrationState, ssr: boolean, isSpaMode: boolean): DataRouteObject[]; declare function createClientRoutes(manifest: RouteManifest<EntryRoute>, routeModulesCache: RouteModules, initialState: HydrationState | null, ssr: boolean, isSpaMode: boolean, parentId?: string, routesByParentId?: Record<string, Omit<EntryRoute, "children">[]>, needsRevalidation?: Set<string>): DataRouteObject[]; declare function shouldHydrateRouteLoader(routeId: string, clientLoader: ClientLoaderFunction | undefined, hasLoader: boolean, isSpaMode: boolean): boolean; type SerializedError = { message: string; stack?: string; }; interface FrameworkContextObject { manifest: AssetsManifest; routeModules: RouteModules; criticalCss?: CriticalCss; serverHandoffString?: string; future: FutureConfig; ssr: boolean; isSpaMode: boolean; routeDiscovery: ServerBuild["routeDiscovery"]; serializeError?(error: Error): SerializedError; renderMeta?: { didRenderScripts?: boolean; streamCache?: Record<number, Promise<void> & { result?: { done: boolean; value: string; }; error?: unknown; }>; }; } interface EntryContext extends FrameworkContextObject { staticHandlerContext: StaticHandlerContext; serverHandoffStream?: ReadableStream<Uint8Array>; } interface FutureConfig { unstable_subResourceIntegrity: boolean; unstable_middleware: boolean; } type CriticalCss = string | { rel: "stylesheet"; href: string; }; interface AssetsManifest { entry: { imports: string[]; module: string; }; routes: RouteManifest<EntryRoute>; url: string; version: string; hmr?: { timestamp?: number; runtime: string; }; sri?: Record<string, string> | true; } declare const FrameworkContext: React.Context<FrameworkContextObject | undefined>; /** * Defines the discovery behavior of the link: * * - "render" - default, discover the route when the link renders * - "none" - don't eagerly discover, only discover if the link is clicked */ type DiscoverBehavior = "render" | "none"; /** * Defines the prefetching behavior of the link: * * - "none": Never fetched * - "intent": Fetched when the user focuses or hovers the link * - "render": Fetched when the link is rendered * - "viewport": Fetched when the link is in the viewport */ type PrefetchBehavior = "intent" | "render" | "none" | "viewport"; /** * Renders all of the `<link>` tags created by the route module * [`links`](../../start/framework/route-module#links) export. You should render * it inside the `<head>` of your document. * * @example * import { Links } from "react-router"; * * export default function Root() { * return ( * <html> * <head> * <Links /> * </head> * <body></body> * </html> * ); * } * * @public * @category Components * @mode framework * @returns A collection of React elements for `<link>` tags */ declare function Links(): React.JSX.Element; /** * Renders `<link rel=prefetch|modulepreload>` tags for modules and data of * another page to enable an instant navigation to that page. * [`<Link prefetch>`](../../components/Link#prefetch) uses this internally, but * you can render it to prefetch a page for any other reason. * * For example, you may render one of this as the user types into a search field * to prefetch search results before they click through to their selection. * * @example * import { PrefetchPageLinks } from "react-router"; * * <PrefetchPageLinks page="/absolute/path" /> * * @public * @category Components * @mode framework * @param props Props * @param props.page The absolute path of the page to prefetch, e.g. `/absolute/path`. * @param props.linkProps Additional props to spread onto the * [`<link>`](https://developer.mozilla.org/en-US/docs/Web/HTML/Reference/Elements/link) * tags, such as `crossOrigin`, `integrity`, `rel`, etc. * @returns A collection of React elements for `<link>` tags */ declare function PrefetchPageLinks({ page, ...linkProps }: PageLinkDescriptor): React.JSX.Element | null; /** * Renders all the `<meta>` tags created by the route module * [`meta`](../../start/framework/route-module#meta) exports. You should render * it inside the `<head>` of your HTML. * * @example * import { Meta } from "react-router"; * * export default function Root() { * return ( * <html> * <head> * <Meta /> * </head> * </html> * ); * } * * @public * @category Components * @mode framework * @returns A collection of React elements for `<meta>` tags */ declare function Meta(): React.JSX.Element; /** * A couple common attributes: * * - `<Scripts crossOrigin>` for hosting your static assets on a different server than your app. * - `<Scripts nonce>` to support a [content security policy for scripts](https://developer.mozilla.org/en-US/docs/Web/HTTP/Headers/Content-Security-Policy/script-src) with [nonce-sources](https://developer.mozilla.org/en-US/docs/Web/HTTP/Headers/Content-Security-Policy/Sources#sources) for your `<script>` tags. * * You cannot pass through attributes such as `async`, `defer`, `src`, `type`, `noModule` because they are managed by React Router internally. * * @category Types */ type ScriptsProps = Omit<React.HTMLProps<HTMLScriptElement>, "async" | "children" | "dangerouslySetInnerHTML" | "defer" | "src" | "type" | "noModule" | "suppressHydrationWarning"> & { /** * A [`nonce`](https://developer.mozilla.org/en-US/docs/Web/HTML/Reference/Global_attributes/nonce) * attribute to render on [the `<script>` element](https://developer.mozilla.org/en-US/docs/Web/HTML/Reference/Elements/script) */ nonce?: string | undefined; }; /** * Renders the client runtime of your app. It should be rendered inside the * [`<body>`](https://developer.mozilla.org/en-US/docs/Web/HTML/Reference/Elements/body) * of the document. * * If server rendering, you can omit `<Scripts/>` and the app will work as a * traditional web app without JavaScript, relying solely on HTML and browser * behaviors. * * @example * import { Scripts } from "react-router"; * * export default function Root() { * return ( * <html> * <head /> * <body> * <Scripts /> * </body> * </html> * ); * } * * @public * @category Components * @mode framework * @param scriptProps Additional props to spread onto the * [`<script>`](https://developer.mozilla.org/en-US/docs/Web/HTML/Reference/Elements/script) * tag, such as `crossOrigin`, `nonce`, etc. * @returns A collection of React elements for `<script>` tags */ declare function Scripts(scriptProps: ScriptsProps): React.JSX.Element | null; /** * @category Data Routers */ interface DOMRouterOpts { /** * Basename path for the application. */ basename?: string; /** * Function to provide the initial `context` values for all client side navigations/fetches */ unstable_getContext?: RouterInit["unstable_getContext"]; /** * Future flags to enable for the router. */ future?: Partial<FutureConfig$1>; /** * When Server-Rendering and opting-out of automatic hydration, the `hydrationData` * option allows you to pass in hydration data from your server-render. This will * almost always be a subset of data from the {@link StaticHandlerContext} value you * get back from the `{@link StaticHandler} `query()` method: * * ```tsx * const router = createBrowserRouter(routes, { * hydrationData: { * loaderData: { * // [routeId]: serverLoaderData * }, * // may also include `errors` and/or `actionData` * }, * }); * ``` * * **Partial Hydration Data** * * You will almost always include a complete set of `loaderData` to hydrate a * server-rendered app. But in advanced use-cases (such as Framework Mode's * `clientLoader`), you may want to include `loaderData` for only some routes * that were loaded/rendered on the server. This allows you to hydrate _some_ * of the routes (such as the app layout/shell) while showing a `HydrateFallback` * and running the loaders for other routes during hydration. * * A route `loader` will run during hydration in 2 scenarios: * * - No hydration data is provided * - In these cases the `HydrateFallback` component will render on initial hydration * - The `loader.hydrate` property is set to true * - This allows you to run the loader even if you did not render a fallback * on initial hydration (i.e., to prime a cache with hydration data) * * ```tsx * const router = createBrowserRouter( * [ * { * id: "root", * loader: rootLoader, * Component: Root, * children: [ * { * id: "index", * loader: indexLoader, * HydrateFallback: IndexSkeleton, * Component: Index, * }, * ], * }, * ], * { * hydrationData: { * loaderData: { * root: "ROOT DATA", * // No index data provided * }, * }, * } * ); * ``` */ hydrationData?: HydrationState; /** * Override the default data strategy of running loaders in parallel. * See {@link DataStrategyFunction}. * * <docs-warning>This is a low-level API intended for advanced use-cases. This * overrides React Router's internal handling of `loader`/`action` execution, * and if done incorrectly will break your app code. Please use with caution * and perform the appropriate testing.</docs-warning> * * By default, React Router is opinionated about how your data is loaded/submitted - * and most notably, executes all of your loaders in parallel for optimal data * fetching. While we think this is the right behavior for most use-cases, we * realize that there is no "one size fits all" solution when it comes to data * fetching for the wide landscape of application requirements. * * The `dataStrategy` option gives you full control over how your loaders and * actions are executed and lays the foundation to build in more advanced APIs * such as middleware, context, and caching layers. Over time, we expect that * we'll leverage this API internally to bring more first class APIs to React * Router, but until then (and beyond), this is your way to add more advanced * functionality for your applications data needs. * * The `dataStrategy` function should return a key/value object of * `routeId` -> {@link DataStrategyResult} and should include entries for any routes * where a handler was executed. A `DataStrategyResult` indicates if the handler * was successful or not based on the `DataStrategyResult.type` field. If the * returned `DataStrategyResult["result"]` is a `Response`, React Router will * unwrap it for you (via `res.json` or `res.text`). If you need to do custom * decoding of a `Response` but want to preserve the status code, you can use * the `data` utility to return your decoded data along with a `ResponseInit`. * * <details> * <summary><b>Example <code>dataStrategy</code> Use Cases</b></summary> * * **Adding logging** * * In the simplest case, let's look at hooking into this API to add some logging * for when our route loaders/actions execute: * * ```ts * let router = createBrowserRouter(routes, { * async dataStrategy({ request, matches }) { * const matchesToLoad = matches.filter((m) => m.shouldLoad); * const results = {}; * await Promise.all( * matchesToLoad.map(async (match) => { * console.log(`Processing ${match.route.id}`); * results[match.route.id] = await match.resolve();; * }) * ); * return results; * }, * }); * ``` * * **Middleware** * * Let's define a middleware on each route via `handle` and call middleware * sequentially first, then call all loaders in parallel - providing any data * made available via the middleware: * * ```ts * const routes = [ * { * id: "parent", * path: "/parent", * loader({ request }, context) { * // ... * }, * handle: { * async middleware({ request }, context) { * context.parent = "PARENT MIDDLEWARE"; * }, * }, * children: [ * { * id: "child", * path: "child", * loader({ request }, context) { * // ... * }, * handle: { * async middleware({ request }, context) { * context.child = "CHILD MIDDLEWARE"; * }, * }, * }, * ], * }, * ]; * * let router = createBrowserRouter(routes, { * async dataStrategy({ request, params, matches }) { * // Run middleware sequentially and let them add data to `context` * let context = {}; * for (const match of matches) { * if (match.route.handle?.middleware) { * await match.route.handle.middleware( * { request, params }, * context * ); * } * } * * // Run loaders in parallel with the `context` value * let matchesToLoad = matches.filter((m) => m.shouldLoad); * let results = await Promise.all( * matchesToLoad.map((match, i) => * match.resolve((handler) => { * // Whatever you pass to `handler` will be passed as the 2nd parameter * // to your loader/action * return handler(context); * }) * ) * ); * return results.reduce( * (acc, result, i) => * Object.assign(acc, { * [matchesToLoad[i].route.id]: result, * }), * {} * ); * }, * }); * ``` * * **Custom Handler** * * It's also possible you don't even want to define a loader implementation at * the route level. Maybe you want to just determine the routes and issue a single * GraphQL request for all of your data? You can do that by setting your * `route.loader=true` so it qualifies as "having a loader", and then store GQL * fragments on `route.handle`: * * ```ts * const routes = [ * { * id: "parent", * path: "/parent", * loader: true, * handle: { * gql: gql` * fragment Parent on Whatever { * parentField * } * `, * }, * children: [ * { * id: "child", * path: "child", * loader: true, * handle: { * gql: gql` * fragment Child on Whatever { * childField * } * `, * }, * }, * ], * }, * ]; * * let router = createBrowserRouter(routes, { * async dataStrategy({ request, params, matches }) { * // Compose route fragments into a single GQL payload * let gql = getFragmentsFromRouteHandles(matches); * let data = await fetchGql(gql); * // Parse results back out into individual route level `DataStrategyResult`'s * // keyed by `routeId` * let results = parseResultsFromGql(data); * return results; * }, * }); * ``` *</details> */ dataStrategy?: DataStrategyFunction; /** * Lazily define portions of the route tree on navigations. * See {@link PatchRoutesOnNavigationFunction}. * * By default, React Router wants you to provide a full route tree up front via * `createBrowserRouter(routes)`. This allows React Router to perform synchronous * route matching, execute loaders, and then render route components in the most * optimistic manner without introducing waterfalls. The tradeoff is that your * initial JS bundle is larger by def