diff --git a/e2e/react-router/basic-file-based/src/routeTree.gen.ts b/e2e/react-router/basic-file-based/src/routeTree.gen.ts
index e44ac41896..62af050d6e 100644
--- a/e2e/react-router/basic-file-based/src/routeTree.gen.ts
+++ b/e2e/react-router/basic-file-based/src/routeTree.gen.ts
@@ -23,6 +23,7 @@ import { Route as LayoutRouteImport } from './routes/_layout'
import { Route as SearchParamsRouteRouteImport } from './routes/search-params/route'
import { Route as IndexRouteImport } from './routes/index'
import { Route as SearchParamsIndexRouteImport } from './routes/search-params/index'
+import { Route as RelativeIndexRouteImport } from './routes/relative/index'
import { Route as RedirectIndexRouteImport } from './routes/redirect/index'
import { Route as PostsIndexRouteImport } from './routes/posts.index'
import { Route as ParamsPsIndexRouteImport } from './routes/params-ps/index'
@@ -35,9 +36,15 @@ import { Route as groupLazyinsideRouteImport } from './routes/(group)/lazyinside
import { Route as groupInsideRouteImport } from './routes/(group)/inside'
import { Route as groupLayoutRouteImport } from './routes/(group)/_layout'
import { Route as anotherGroupOnlyrouteinsideRouteImport } from './routes/(another-group)/onlyrouteinside'
+import { Route as RelativeUseNavigateRouteRouteImport } from './routes/relative/useNavigate/route'
+import { Route as RelativeLinkRouteRouteImport } from './routes/relative/link/route'
import { Route as RedirectTargetIndexRouteImport } from './routes/redirect/$target/index'
import { Route as ParamsPsWildcardIndexRouteImport } from './routes/params-ps/wildcard/index'
import { Route as ParamsPsNamedIndexRouteImport } from './routes/params-ps/named/index'
+import { Route as RelativeUseNavigateRelativeUseNavigateBRouteImport } from './routes/relative/useNavigate/relative-useNavigate-b'
+import { Route as RelativeUseNavigateRelativeUseNavigateARouteImport } from './routes/relative/useNavigate/relative-useNavigate-a'
+import { Route as RelativeLinkRelativeLinkBRouteImport } from './routes/relative/link/relative-link-b'
+import { Route as RelativeLinkRelativeLinkARouteImport } from './routes/relative/link/relative-link-a'
import { Route as RedirectPreloadThirdRouteImport } from './routes/redirect/preload/third'
import { Route as RedirectPreloadSecondRouteImport } from './routes/redirect/preload/second'
import { Route as RedirectPreloadFirstRouteImport } from './routes/redirect/preload/first'
@@ -55,6 +62,16 @@ import { Route as LayoutLayout2LayoutBRouteImport } from './routes/_layout/_layo
import { Route as LayoutLayout2LayoutARouteImport } from './routes/_layout/_layout-2/layout-a'
import { Route as groupSubfolderInsideRouteImport } from './routes/(group)/subfolder/inside'
import { Route as groupLayoutInsidelayoutRouteImport } from './routes/(group)/_layout.insidelayout'
+import { Route as RelativeUseNavigateWithSearchIndexRouteImport } from './routes/relative/useNavigate/with-search/index'
+import { Route as RelativeUseNavigatePathIndexRouteImport } from './routes/relative/useNavigate/path/index'
+import { Route as RelativeUseNavigateNestedIndexRouteImport } from './routes/relative/useNavigate/nested/index'
+import { Route as RelativeLinkWithSearchIndexRouteImport } from './routes/relative/link/with-search/index'
+import { Route as RelativeLinkPathIndexRouteImport } from './routes/relative/link/path/index'
+import { Route as RelativeLinkNestedIndexRouteImport } from './routes/relative/link/nested/index'
+import { Route as RelativeUseNavigatePathPathIndexRouteImport } from './routes/relative/useNavigate/path/$path/index'
+import { Route as RelativeUseNavigateNestedDeepIndexRouteImport } from './routes/relative/useNavigate/nested/deep/index'
+import { Route as RelativeLinkPathPathIndexRouteImport } from './routes/relative/link/path/$path/index'
+import { Route as RelativeLinkNestedDeepIndexRouteImport } from './routes/relative/link/nested/deep/index'
const groupRouteImport = createFileRoute('/(group)')()
@@ -122,6 +139,11 @@ const SearchParamsIndexRoute = SearchParamsIndexRouteImport.update({
path: '/',
getParentRoute: () => SearchParamsRouteRoute,
} as any)
+const RelativeIndexRoute = RelativeIndexRouteImport.update({
+ id: '/relative/',
+ path: '/relative/',
+ getParentRoute: () => rootRouteImport,
+} as any)
const RedirectIndexRoute = RedirectIndexRouteImport.update({
id: '/redirect/',
path: '/redirect/',
@@ -184,6 +206,17 @@ const anotherGroupOnlyrouteinsideRoute =
path: '/onlyrouteinside',
getParentRoute: () => rootRouteImport,
} as any)
+const RelativeUseNavigateRouteRoute =
+ RelativeUseNavigateRouteRouteImport.update({
+ id: '/relative/useNavigate',
+ path: '/relative/useNavigate',
+ getParentRoute: () => rootRouteImport,
+ } as any)
+const RelativeLinkRouteRoute = RelativeLinkRouteRouteImport.update({
+ id: '/relative/link',
+ path: '/relative/link',
+ getParentRoute: () => rootRouteImport,
+} as any)
const RedirectTargetIndexRoute = RedirectTargetIndexRouteImport.update({
id: '/',
path: '/',
@@ -199,6 +232,30 @@ const ParamsPsNamedIndexRoute = ParamsPsNamedIndexRouteImport.update({
path: '/params-ps/named/',
getParentRoute: () => rootRouteImport,
} as any)
+const RelativeUseNavigateRelativeUseNavigateBRoute =
+ RelativeUseNavigateRelativeUseNavigateBRouteImport.update({
+ id: '/relative-useNavigate-b',
+ path: '/relative-useNavigate-b',
+ getParentRoute: () => RelativeUseNavigateRouteRoute,
+ } as any)
+const RelativeUseNavigateRelativeUseNavigateARoute =
+ RelativeUseNavigateRelativeUseNavigateARouteImport.update({
+ id: '/relative-useNavigate-a',
+ path: '/relative-useNavigate-a',
+ getParentRoute: () => RelativeUseNavigateRouteRoute,
+ } as any)
+const RelativeLinkRelativeLinkBRoute =
+ RelativeLinkRelativeLinkBRouteImport.update({
+ id: '/relative-link-b',
+ path: '/relative-link-b',
+ getParentRoute: () => RelativeLinkRouteRoute,
+ } as any)
+const RelativeLinkRelativeLinkARoute =
+ RelativeLinkRelativeLinkARouteImport.update({
+ id: '/relative-link-a',
+ path: '/relative-link-a',
+ getParentRoute: () => RelativeLinkRouteRoute,
+ } as any)
const RedirectPreloadThirdRoute = RedirectPreloadThirdRouteImport.update({
id: '/redirect/preload/third',
path: '/redirect/preload/third',
@@ -289,6 +346,64 @@ const groupLayoutInsidelayoutRoute = groupLayoutInsidelayoutRouteImport.update({
path: '/insidelayout',
getParentRoute: () => groupLayoutRoute,
} as any)
+const RelativeUseNavigateWithSearchIndexRoute =
+ RelativeUseNavigateWithSearchIndexRouteImport.update({
+ id: '/with-search/',
+ path: '/with-search/',
+ getParentRoute: () => RelativeUseNavigateRouteRoute,
+ } as any)
+const RelativeUseNavigatePathIndexRoute =
+ RelativeUseNavigatePathIndexRouteImport.update({
+ id: '/path/',
+ path: '/path/',
+ getParentRoute: () => RelativeUseNavigateRouteRoute,
+ } as any)
+const RelativeUseNavigateNestedIndexRoute =
+ RelativeUseNavigateNestedIndexRouteImport.update({
+ id: '/nested/',
+ path: '/nested/',
+ getParentRoute: () => RelativeUseNavigateRouteRoute,
+ } as any)
+const RelativeLinkWithSearchIndexRoute =
+ RelativeLinkWithSearchIndexRouteImport.update({
+ id: '/with-search/',
+ path: '/with-search/',
+ getParentRoute: () => RelativeLinkRouteRoute,
+ } as any)
+const RelativeLinkPathIndexRoute = RelativeLinkPathIndexRouteImport.update({
+ id: '/path/',
+ path: '/path/',
+ getParentRoute: () => RelativeLinkRouteRoute,
+} as any)
+const RelativeLinkNestedIndexRoute = RelativeLinkNestedIndexRouteImport.update({
+ id: '/nested/',
+ path: '/nested/',
+ getParentRoute: () => RelativeLinkRouteRoute,
+} as any)
+const RelativeUseNavigatePathPathIndexRoute =
+ RelativeUseNavigatePathPathIndexRouteImport.update({
+ id: '/path/$path/',
+ path: '/path/$path/',
+ getParentRoute: () => RelativeUseNavigateRouteRoute,
+ } as any)
+const RelativeUseNavigateNestedDeepIndexRoute =
+ RelativeUseNavigateNestedDeepIndexRouteImport.update({
+ id: '/nested/deep/',
+ path: '/nested/deep/',
+ getParentRoute: () => RelativeUseNavigateRouteRoute,
+ } as any)
+const RelativeLinkPathPathIndexRoute =
+ RelativeLinkPathPathIndexRouteImport.update({
+ id: '/path/$path/',
+ path: '/path/$path/',
+ getParentRoute: () => RelativeLinkRouteRoute,
+ } as any)
+const RelativeLinkNestedDeepIndexRoute =
+ RelativeLinkNestedDeepIndexRouteImport.update({
+ id: '/nested/deep/',
+ path: '/nested/deep/',
+ getParentRoute: () => RelativeLinkRouteRoute,
+ } as any)
export interface FileRoutesByFullPath {
'/': typeof groupLayoutRouteWithChildren
@@ -301,6 +416,8 @@ export interface FileRoutesByFullPath {
'/posts': typeof PostsRouteWithChildren
'/remountDeps': typeof RemountDepsRoute
'/대한민국': typeof Char45824Char54620Char48124Char44397Route
+ '/relative/link': typeof RelativeLinkRouteRouteWithChildren
+ '/relative/useNavigate': typeof RelativeUseNavigateRouteRouteWithChildren
'/onlyrouteinside': typeof anotherGroupOnlyrouteinsideRoute
'/inside': typeof groupInsideRoute
'/lazyinside': typeof groupLazyinsideRoute
@@ -311,6 +428,7 @@ export interface FileRoutesByFullPath {
'/params-ps': typeof ParamsPsIndexRoute
'/posts/': typeof PostsIndexRoute
'/redirect': typeof RedirectIndexRoute
+ '/relative': typeof RelativeIndexRoute
'/search-params/': typeof SearchParamsIndexRoute
'/insidelayout': typeof groupLayoutInsidelayoutRoute
'/subfolder/inside': typeof groupSubfolderInsideRoute
@@ -329,9 +447,23 @@ export interface FileRoutesByFullPath {
'/redirect/preload/first': typeof RedirectPreloadFirstRoute
'/redirect/preload/second': typeof RedirectPreloadSecondRoute
'/redirect/preload/third': typeof RedirectPreloadThirdRoute
+ '/relative/link/relative-link-a': typeof RelativeLinkRelativeLinkARoute
+ '/relative/link/relative-link-b': typeof RelativeLinkRelativeLinkBRoute
+ '/relative/useNavigate/relative-useNavigate-a': typeof RelativeUseNavigateRelativeUseNavigateARoute
+ '/relative/useNavigate/relative-useNavigate-b': typeof RelativeUseNavigateRelativeUseNavigateBRoute
'/params-ps/named': typeof ParamsPsNamedIndexRoute
'/params-ps/wildcard': typeof ParamsPsWildcardIndexRoute
'/redirect/$target/': typeof RedirectTargetIndexRoute
+ '/relative/link/nested': typeof RelativeLinkNestedIndexRoute
+ '/relative/link/path': typeof RelativeLinkPathIndexRoute
+ '/relative/link/with-search': typeof RelativeLinkWithSearchIndexRoute
+ '/relative/useNavigate/nested': typeof RelativeUseNavigateNestedIndexRoute
+ '/relative/useNavigate/path': typeof RelativeUseNavigatePathIndexRoute
+ '/relative/useNavigate/with-search': typeof RelativeUseNavigateWithSearchIndexRoute
+ '/relative/link/nested/deep': typeof RelativeLinkNestedDeepIndexRoute
+ '/relative/link/path/$path': typeof RelativeLinkPathPathIndexRoute
+ '/relative/useNavigate/nested/deep': typeof RelativeUseNavigateNestedDeepIndexRoute
+ '/relative/useNavigate/path/$path': typeof RelativeUseNavigatePathPathIndexRoute
}
export interface FileRoutesByTo {
'/': typeof groupLayoutRouteWithChildren
@@ -342,6 +474,8 @@ export interface FileRoutesByTo {
'/notRemountDeps': typeof NotRemountDepsRoute
'/remountDeps': typeof RemountDepsRoute
'/대한민국': typeof Char45824Char54620Char48124Char44397Route
+ '/relative/link': typeof RelativeLinkRouteRouteWithChildren
+ '/relative/useNavigate': typeof RelativeUseNavigateRouteRouteWithChildren
'/onlyrouteinside': typeof anotherGroupOnlyrouteinsideRoute
'/inside': typeof groupInsideRoute
'/lazyinside': typeof groupLazyinsideRoute
@@ -351,6 +485,7 @@ export interface FileRoutesByTo {
'/params-ps': typeof ParamsPsIndexRoute
'/posts': typeof PostsIndexRoute
'/redirect': typeof RedirectIndexRoute
+ '/relative': typeof RelativeIndexRoute
'/search-params': typeof SearchParamsIndexRoute
'/insidelayout': typeof groupLayoutInsidelayoutRoute
'/subfolder/inside': typeof groupSubfolderInsideRoute
@@ -369,9 +504,23 @@ export interface FileRoutesByTo {
'/redirect/preload/first': typeof RedirectPreloadFirstRoute
'/redirect/preload/second': typeof RedirectPreloadSecondRoute
'/redirect/preload/third': typeof RedirectPreloadThirdRoute
+ '/relative/link/relative-link-a': typeof RelativeLinkRelativeLinkARoute
+ '/relative/link/relative-link-b': typeof RelativeLinkRelativeLinkBRoute
+ '/relative/useNavigate/relative-useNavigate-a': typeof RelativeUseNavigateRelativeUseNavigateARoute
+ '/relative/useNavigate/relative-useNavigate-b': typeof RelativeUseNavigateRelativeUseNavigateBRoute
'/params-ps/named': typeof ParamsPsNamedIndexRoute
'/params-ps/wildcard': typeof ParamsPsWildcardIndexRoute
'/redirect/$target': typeof RedirectTargetIndexRoute
+ '/relative/link/nested': typeof RelativeLinkNestedIndexRoute
+ '/relative/link/path': typeof RelativeLinkPathIndexRoute
+ '/relative/link/with-search': typeof RelativeLinkWithSearchIndexRoute
+ '/relative/useNavigate/nested': typeof RelativeUseNavigateNestedIndexRoute
+ '/relative/useNavigate/path': typeof RelativeUseNavigatePathIndexRoute
+ '/relative/useNavigate/with-search': typeof RelativeUseNavigateWithSearchIndexRoute
+ '/relative/link/nested/deep': typeof RelativeLinkNestedDeepIndexRoute
+ '/relative/link/path/$path': typeof RelativeLinkPathPathIndexRoute
+ '/relative/useNavigate/nested/deep': typeof RelativeUseNavigateNestedDeepIndexRoute
+ '/relative/useNavigate/path/$path': typeof RelativeUseNavigatePathPathIndexRoute
}
export interface FileRoutesById {
__root__: typeof rootRouteImport
@@ -386,6 +535,8 @@ export interface FileRoutesById {
'/posts': typeof PostsRouteWithChildren
'/remountDeps': typeof RemountDepsRoute
'/대한민국': typeof Char45824Char54620Char48124Char44397Route
+ '/relative/link': typeof RelativeLinkRouteRouteWithChildren
+ '/relative/useNavigate': typeof RelativeUseNavigateRouteRouteWithChildren
'/(another-group)/onlyrouteinside': typeof anotherGroupOnlyrouteinsideRoute
'/(group)': typeof groupRouteWithChildren
'/(group)/_layout': typeof groupLayoutRouteWithChildren
@@ -399,6 +550,7 @@ export interface FileRoutesById {
'/params-ps/': typeof ParamsPsIndexRoute
'/posts/': typeof PostsIndexRoute
'/redirect/': typeof RedirectIndexRoute
+ '/relative/': typeof RelativeIndexRoute
'/search-params/': typeof SearchParamsIndexRoute
'/(group)/_layout/insidelayout': typeof groupLayoutInsidelayoutRoute
'/(group)/subfolder/inside': typeof groupSubfolderInsideRoute
@@ -417,9 +569,23 @@ export interface FileRoutesById {
'/redirect/preload/first': typeof RedirectPreloadFirstRoute
'/redirect/preload/second': typeof RedirectPreloadSecondRoute
'/redirect/preload/third': typeof RedirectPreloadThirdRoute
+ '/relative/link/relative-link-a': typeof RelativeLinkRelativeLinkARoute
+ '/relative/link/relative-link-b': typeof RelativeLinkRelativeLinkBRoute
+ '/relative/useNavigate/relative-useNavigate-a': typeof RelativeUseNavigateRelativeUseNavigateARoute
+ '/relative/useNavigate/relative-useNavigate-b': typeof RelativeUseNavigateRelativeUseNavigateBRoute
'/params-ps/named/': typeof ParamsPsNamedIndexRoute
'/params-ps/wildcard/': typeof ParamsPsWildcardIndexRoute
'/redirect/$target/': typeof RedirectTargetIndexRoute
+ '/relative/link/nested/': typeof RelativeLinkNestedIndexRoute
+ '/relative/link/path/': typeof RelativeLinkPathIndexRoute
+ '/relative/link/with-search/': typeof RelativeLinkWithSearchIndexRoute
+ '/relative/useNavigate/nested/': typeof RelativeUseNavigateNestedIndexRoute
+ '/relative/useNavigate/path/': typeof RelativeUseNavigatePathIndexRoute
+ '/relative/useNavigate/with-search/': typeof RelativeUseNavigateWithSearchIndexRoute
+ '/relative/link/nested/deep/': typeof RelativeLinkNestedDeepIndexRoute
+ '/relative/link/path/$path/': typeof RelativeLinkPathPathIndexRoute
+ '/relative/useNavigate/nested/deep/': typeof RelativeUseNavigateNestedDeepIndexRoute
+ '/relative/useNavigate/path/$path/': typeof RelativeUseNavigatePathPathIndexRoute
}
export interface FileRouteTypes {
fileRoutesByFullPath: FileRoutesByFullPath
@@ -434,6 +600,8 @@ export interface FileRouteTypes {
| '/posts'
| '/remountDeps'
| '/대한민국'
+ | '/relative/link'
+ | '/relative/useNavigate'
| '/onlyrouteinside'
| '/inside'
| '/lazyinside'
@@ -444,6 +612,7 @@ export interface FileRouteTypes {
| '/params-ps'
| '/posts/'
| '/redirect'
+ | '/relative'
| '/search-params/'
| '/insidelayout'
| '/subfolder/inside'
@@ -462,9 +631,23 @@ export interface FileRouteTypes {
| '/redirect/preload/first'
| '/redirect/preload/second'
| '/redirect/preload/third'
+ | '/relative/link/relative-link-a'
+ | '/relative/link/relative-link-b'
+ | '/relative/useNavigate/relative-useNavigate-a'
+ | '/relative/useNavigate/relative-useNavigate-b'
| '/params-ps/named'
| '/params-ps/wildcard'
| '/redirect/$target/'
+ | '/relative/link/nested'
+ | '/relative/link/path'
+ | '/relative/link/with-search'
+ | '/relative/useNavigate/nested'
+ | '/relative/useNavigate/path'
+ | '/relative/useNavigate/with-search'
+ | '/relative/link/nested/deep'
+ | '/relative/link/path/$path'
+ | '/relative/useNavigate/nested/deep'
+ | '/relative/useNavigate/path/$path'
fileRoutesByTo: FileRoutesByTo
to:
| '/'
@@ -475,6 +658,8 @@ export interface FileRouteTypes {
| '/notRemountDeps'
| '/remountDeps'
| '/대한민국'
+ | '/relative/link'
+ | '/relative/useNavigate'
| '/onlyrouteinside'
| '/inside'
| '/lazyinside'
@@ -484,6 +669,7 @@ export interface FileRouteTypes {
| '/params-ps'
| '/posts'
| '/redirect'
+ | '/relative'
| '/search-params'
| '/insidelayout'
| '/subfolder/inside'
@@ -502,9 +688,23 @@ export interface FileRouteTypes {
| '/redirect/preload/first'
| '/redirect/preload/second'
| '/redirect/preload/third'
+ | '/relative/link/relative-link-a'
+ | '/relative/link/relative-link-b'
+ | '/relative/useNavigate/relative-useNavigate-a'
+ | '/relative/useNavigate/relative-useNavigate-b'
| '/params-ps/named'
| '/params-ps/wildcard'
| '/redirect/$target'
+ | '/relative/link/nested'
+ | '/relative/link/path'
+ | '/relative/link/with-search'
+ | '/relative/useNavigate/nested'
+ | '/relative/useNavigate/path'
+ | '/relative/useNavigate/with-search'
+ | '/relative/link/nested/deep'
+ | '/relative/link/path/$path'
+ | '/relative/useNavigate/nested/deep'
+ | '/relative/useNavigate/path/$path'
id:
| '__root__'
| '/'
@@ -518,6 +718,8 @@ export interface FileRouteTypes {
| '/posts'
| '/remountDeps'
| '/대한민국'
+ | '/relative/link'
+ | '/relative/useNavigate'
| '/(another-group)/onlyrouteinside'
| '/(group)'
| '/(group)/_layout'
@@ -531,6 +733,7 @@ export interface FileRouteTypes {
| '/params-ps/'
| '/posts/'
| '/redirect/'
+ | '/relative/'
| '/search-params/'
| '/(group)/_layout/insidelayout'
| '/(group)/subfolder/inside'
@@ -549,9 +752,23 @@ export interface FileRouteTypes {
| '/redirect/preload/first'
| '/redirect/preload/second'
| '/redirect/preload/third'
+ | '/relative/link/relative-link-a'
+ | '/relative/link/relative-link-b'
+ | '/relative/useNavigate/relative-useNavigate-a'
+ | '/relative/useNavigate/relative-useNavigate-b'
| '/params-ps/named/'
| '/params-ps/wildcard/'
| '/redirect/$target/'
+ | '/relative/link/nested/'
+ | '/relative/link/path/'
+ | '/relative/link/with-search/'
+ | '/relative/useNavigate/nested/'
+ | '/relative/useNavigate/path/'
+ | '/relative/useNavigate/with-search/'
+ | '/relative/link/nested/deep/'
+ | '/relative/link/path/$path/'
+ | '/relative/useNavigate/nested/deep/'
+ | '/relative/useNavigate/path/$path/'
fileRoutesById: FileRoutesById
}
export interface RootRouteChildren {
@@ -566,12 +783,15 @@ export interface RootRouteChildren {
PostsRoute: typeof PostsRouteWithChildren
RemountDepsRoute: typeof RemountDepsRoute
Char45824Char54620Char48124Char44397Route: typeof Char45824Char54620Char48124Char44397Route
+ RelativeLinkRouteRoute: typeof RelativeLinkRouteRouteWithChildren
+ RelativeUseNavigateRouteRoute: typeof RelativeUseNavigateRouteRouteWithChildren
anotherGroupOnlyrouteinsideRoute: typeof anotherGroupOnlyrouteinsideRoute
groupRoute: typeof groupRouteWithChildren
RedirectTargetRoute: typeof RedirectTargetRouteWithChildren
StructuralSharingEnabledRoute: typeof StructuralSharingEnabledRoute
ParamsPsIndexRoute: typeof ParamsPsIndexRoute
RedirectIndexRoute: typeof RedirectIndexRoute
+ RelativeIndexRoute: typeof RelativeIndexRoute
ParamsPsNamedFooRoute: typeof ParamsPsNamedFooRoute
ParamsPsNamedPrefixChar123fooChar125Route: typeof ParamsPsNamedPrefixChar123fooChar125Route
ParamsPsNamedChar123fooChar125suffixRoute: typeof ParamsPsNamedChar123fooChar125suffixRoute
@@ -680,6 +900,13 @@ declare module '@tanstack/react-router' {
preLoaderRoute: typeof SearchParamsIndexRouteImport
parentRoute: typeof SearchParamsRouteRoute
}
+ '/relative/': {
+ id: '/relative/'
+ path: '/relative'
+ fullPath: '/relative'
+ preLoaderRoute: typeof RelativeIndexRouteImport
+ parentRoute: typeof rootRouteImport
+ }
'/redirect/': {
id: '/redirect/'
path: '/redirect'
@@ -764,6 +991,20 @@ declare module '@tanstack/react-router' {
preLoaderRoute: typeof anotherGroupOnlyrouteinsideRouteImport
parentRoute: typeof rootRouteImport
}
+ '/relative/useNavigate': {
+ id: '/relative/useNavigate'
+ path: '/relative/useNavigate'
+ fullPath: '/relative/useNavigate'
+ preLoaderRoute: typeof RelativeUseNavigateRouteRouteImport
+ parentRoute: typeof rootRouteImport
+ }
+ '/relative/link': {
+ id: '/relative/link'
+ path: '/relative/link'
+ fullPath: '/relative/link'
+ preLoaderRoute: typeof RelativeLinkRouteRouteImport
+ parentRoute: typeof rootRouteImport
+ }
'/redirect/$target/': {
id: '/redirect/$target/'
path: '/'
@@ -785,6 +1026,34 @@ declare module '@tanstack/react-router' {
preLoaderRoute: typeof ParamsPsNamedIndexRouteImport
parentRoute: typeof rootRouteImport
}
+ '/relative/useNavigate/relative-useNavigate-b': {
+ id: '/relative/useNavigate/relative-useNavigate-b'
+ path: '/relative-useNavigate-b'
+ fullPath: '/relative/useNavigate/relative-useNavigate-b'
+ preLoaderRoute: typeof RelativeUseNavigateRelativeUseNavigateBRouteImport
+ parentRoute: typeof RelativeUseNavigateRouteRoute
+ }
+ '/relative/useNavigate/relative-useNavigate-a': {
+ id: '/relative/useNavigate/relative-useNavigate-a'
+ path: '/relative-useNavigate-a'
+ fullPath: '/relative/useNavigate/relative-useNavigate-a'
+ preLoaderRoute: typeof RelativeUseNavigateRelativeUseNavigateARouteImport
+ parentRoute: typeof RelativeUseNavigateRouteRoute
+ }
+ '/relative/link/relative-link-b': {
+ id: '/relative/link/relative-link-b'
+ path: '/relative-link-b'
+ fullPath: '/relative/link/relative-link-b'
+ preLoaderRoute: typeof RelativeLinkRelativeLinkBRouteImport
+ parentRoute: typeof RelativeLinkRouteRoute
+ }
+ '/relative/link/relative-link-a': {
+ id: '/relative/link/relative-link-a'
+ path: '/relative-link-a'
+ fullPath: '/relative/link/relative-link-a'
+ preLoaderRoute: typeof RelativeLinkRelativeLinkARouteImport
+ parentRoute: typeof RelativeLinkRouteRoute
+ }
'/redirect/preload/third': {
id: '/redirect/preload/third'
path: '/redirect/preload/third'
@@ -904,6 +1173,76 @@ declare module '@tanstack/react-router' {
preLoaderRoute: typeof groupLayoutInsidelayoutRouteImport
parentRoute: typeof groupLayoutRoute
}
+ '/relative/useNavigate/with-search/': {
+ id: '/relative/useNavigate/with-search/'
+ path: '/with-search'
+ fullPath: '/relative/useNavigate/with-search'
+ preLoaderRoute: typeof RelativeUseNavigateWithSearchIndexRouteImport
+ parentRoute: typeof RelativeUseNavigateRouteRoute
+ }
+ '/relative/useNavigate/path/': {
+ id: '/relative/useNavigate/path/'
+ path: '/path'
+ fullPath: '/relative/useNavigate/path'
+ preLoaderRoute: typeof RelativeUseNavigatePathIndexRouteImport
+ parentRoute: typeof RelativeUseNavigateRouteRoute
+ }
+ '/relative/useNavigate/nested/': {
+ id: '/relative/useNavigate/nested/'
+ path: '/nested'
+ fullPath: '/relative/useNavigate/nested'
+ preLoaderRoute: typeof RelativeUseNavigateNestedIndexRouteImport
+ parentRoute: typeof RelativeUseNavigateRouteRoute
+ }
+ '/relative/link/with-search/': {
+ id: '/relative/link/with-search/'
+ path: '/with-search'
+ fullPath: '/relative/link/with-search'
+ preLoaderRoute: typeof RelativeLinkWithSearchIndexRouteImport
+ parentRoute: typeof RelativeLinkRouteRoute
+ }
+ '/relative/link/path/': {
+ id: '/relative/link/path/'
+ path: '/path'
+ fullPath: '/relative/link/path'
+ preLoaderRoute: typeof RelativeLinkPathIndexRouteImport
+ parentRoute: typeof RelativeLinkRouteRoute
+ }
+ '/relative/link/nested/': {
+ id: '/relative/link/nested/'
+ path: '/nested'
+ fullPath: '/relative/link/nested'
+ preLoaderRoute: typeof RelativeLinkNestedIndexRouteImport
+ parentRoute: typeof RelativeLinkRouteRoute
+ }
+ '/relative/useNavigate/path/$path/': {
+ id: '/relative/useNavigate/path/$path/'
+ path: '/path/$path'
+ fullPath: '/relative/useNavigate/path/$path'
+ preLoaderRoute: typeof RelativeUseNavigatePathPathIndexRouteImport
+ parentRoute: typeof RelativeUseNavigateRouteRoute
+ }
+ '/relative/useNavigate/nested/deep/': {
+ id: '/relative/useNavigate/nested/deep/'
+ path: '/nested/deep'
+ fullPath: '/relative/useNavigate/nested/deep'
+ preLoaderRoute: typeof RelativeUseNavigateNestedDeepIndexRouteImport
+ parentRoute: typeof RelativeUseNavigateRouteRoute
+ }
+ '/relative/link/path/$path/': {
+ id: '/relative/link/path/$path/'
+ path: '/path/$path'
+ fullPath: '/relative/link/path/$path'
+ preLoaderRoute: typeof RelativeLinkPathPathIndexRouteImport
+ parentRoute: typeof RelativeLinkRouteRoute
+ }
+ '/relative/link/nested/deep/': {
+ id: '/relative/link/nested/deep/'
+ path: '/nested/deep'
+ fullPath: '/relative/link/nested/deep'
+ preLoaderRoute: typeof RelativeLinkNestedDeepIndexRouteImport
+ parentRoute: typeof RelativeLinkRouteRoute
+ }
}
}
@@ -957,6 +1296,60 @@ const PostsRouteChildren: PostsRouteChildren = {
const PostsRouteWithChildren = PostsRoute._addFileChildren(PostsRouteChildren)
+interface RelativeLinkRouteRouteChildren {
+ RelativeLinkRelativeLinkARoute: typeof RelativeLinkRelativeLinkARoute
+ RelativeLinkRelativeLinkBRoute: typeof RelativeLinkRelativeLinkBRoute
+ RelativeLinkNestedIndexRoute: typeof RelativeLinkNestedIndexRoute
+ RelativeLinkPathIndexRoute: typeof RelativeLinkPathIndexRoute
+ RelativeLinkWithSearchIndexRoute: typeof RelativeLinkWithSearchIndexRoute
+ RelativeLinkNestedDeepIndexRoute: typeof RelativeLinkNestedDeepIndexRoute
+ RelativeLinkPathPathIndexRoute: typeof RelativeLinkPathPathIndexRoute
+}
+
+const RelativeLinkRouteRouteChildren: RelativeLinkRouteRouteChildren = {
+ RelativeLinkRelativeLinkARoute: RelativeLinkRelativeLinkARoute,
+ RelativeLinkRelativeLinkBRoute: RelativeLinkRelativeLinkBRoute,
+ RelativeLinkNestedIndexRoute: RelativeLinkNestedIndexRoute,
+ RelativeLinkPathIndexRoute: RelativeLinkPathIndexRoute,
+ RelativeLinkWithSearchIndexRoute: RelativeLinkWithSearchIndexRoute,
+ RelativeLinkNestedDeepIndexRoute: RelativeLinkNestedDeepIndexRoute,
+ RelativeLinkPathPathIndexRoute: RelativeLinkPathPathIndexRoute,
+}
+
+const RelativeLinkRouteRouteWithChildren =
+ RelativeLinkRouteRoute._addFileChildren(RelativeLinkRouteRouteChildren)
+
+interface RelativeUseNavigateRouteRouteChildren {
+ RelativeUseNavigateRelativeUseNavigateARoute: typeof RelativeUseNavigateRelativeUseNavigateARoute
+ RelativeUseNavigateRelativeUseNavigateBRoute: typeof RelativeUseNavigateRelativeUseNavigateBRoute
+ RelativeUseNavigateNestedIndexRoute: typeof RelativeUseNavigateNestedIndexRoute
+ RelativeUseNavigatePathIndexRoute: typeof RelativeUseNavigatePathIndexRoute
+ RelativeUseNavigateWithSearchIndexRoute: typeof RelativeUseNavigateWithSearchIndexRoute
+ RelativeUseNavigateNestedDeepIndexRoute: typeof RelativeUseNavigateNestedDeepIndexRoute
+ RelativeUseNavigatePathPathIndexRoute: typeof RelativeUseNavigatePathPathIndexRoute
+}
+
+const RelativeUseNavigateRouteRouteChildren: RelativeUseNavigateRouteRouteChildren =
+ {
+ RelativeUseNavigateRelativeUseNavigateARoute:
+ RelativeUseNavigateRelativeUseNavigateARoute,
+ RelativeUseNavigateRelativeUseNavigateBRoute:
+ RelativeUseNavigateRelativeUseNavigateBRoute,
+ RelativeUseNavigateNestedIndexRoute: RelativeUseNavigateNestedIndexRoute,
+ RelativeUseNavigatePathIndexRoute: RelativeUseNavigatePathIndexRoute,
+ RelativeUseNavigateWithSearchIndexRoute:
+ RelativeUseNavigateWithSearchIndexRoute,
+ RelativeUseNavigateNestedDeepIndexRoute:
+ RelativeUseNavigateNestedDeepIndexRoute,
+ RelativeUseNavigatePathPathIndexRoute:
+ RelativeUseNavigatePathPathIndexRoute,
+ }
+
+const RelativeUseNavigateRouteRouteWithChildren =
+ RelativeUseNavigateRouteRoute._addFileChildren(
+ RelativeUseNavigateRouteRouteChildren,
+ )
+
interface groupLayoutRouteChildren {
groupLayoutInsidelayoutRoute: typeof groupLayoutInsidelayoutRoute
}
@@ -1014,12 +1407,15 @@ const rootRouteChildren: RootRouteChildren = {
RemountDepsRoute: RemountDepsRoute,
Char45824Char54620Char48124Char44397Route:
Char45824Char54620Char48124Char44397Route,
+ RelativeLinkRouteRoute: RelativeLinkRouteRouteWithChildren,
+ RelativeUseNavigateRouteRoute: RelativeUseNavigateRouteRouteWithChildren,
anotherGroupOnlyrouteinsideRoute: anotherGroupOnlyrouteinsideRoute,
groupRoute: groupRouteWithChildren,
RedirectTargetRoute: RedirectTargetRouteWithChildren,
StructuralSharingEnabledRoute: StructuralSharingEnabledRoute,
ParamsPsIndexRoute: ParamsPsIndexRoute,
RedirectIndexRoute: RedirectIndexRoute,
+ RelativeIndexRoute: RelativeIndexRoute,
ParamsPsNamedFooRoute: ParamsPsNamedFooRoute,
ParamsPsNamedPrefixChar123fooChar125Route:
ParamsPsNamedPrefixChar123fooChar125Route,
diff --git a/e2e/react-router/basic-file-based/src/routes/__root.tsx b/e2e/react-router/basic-file-based/src/routes/__root.tsx
index 4062165c86..06734a3b95 100644
--- a/e2e/react-router/basic-file-based/src/routes/__root.tsx
+++ b/e2e/react-router/basic-file-based/src/routes/__root.tsx
@@ -122,6 +122,14 @@ function RootComponent() {
>
redirect
{' '}
+
+ relative routing
+ {' '}
+
+ Relative Routing Tests - Home
+
+
+ Using Links
+ Using useNavigate
+
+
+
+
+
+ )
+}
diff --git a/e2e/react-router/basic-file-based/src/routes/relative/link/nested/deep/index.tsx b/e2e/react-router/basic-file-based/src/routes/relative/link/nested/deep/index.tsx
new file mode 100644
index 0000000000..5cc4b4e58a
--- /dev/null
+++ b/e2e/react-router/basic-file-based/src/routes/relative/link/nested/deep/index.tsx
@@ -0,0 +1,13 @@
+import { createFileRoute } from '@tanstack/react-router'
+
+export const Route = createFileRoute('/relative/link/nested/deep/')({
+ component: RouteComponent,
+})
+
+function RouteComponent() {
+ return (
+
+ Hello "/relative/link/nested/deep/"!
+
+ )
+}
diff --git a/e2e/react-router/basic-file-based/src/routes/relative/link/nested/index.tsx b/e2e/react-router/basic-file-based/src/routes/relative/link/nested/index.tsx
new file mode 100644
index 0000000000..afca201e02
--- /dev/null
+++ b/e2e/react-router/basic-file-based/src/routes/relative/link/nested/index.tsx
@@ -0,0 +1,13 @@
+import { createFileRoute } from '@tanstack/react-router'
+
+export const Route = createFileRoute('/relative/link/nested/')({
+ component: RouteComponent,
+})
+
+function RouteComponent() {
+ return (
+
+ Hello "/relative/link/nested/"!
+
+ )
+}
diff --git a/e2e/react-router/basic-file-based/src/routes/relative/link/path/$path/index.tsx b/e2e/react-router/basic-file-based/src/routes/relative/link/path/$path/index.tsx
new file mode 100644
index 0000000000..30b13cb09d
--- /dev/null
+++ b/e2e/react-router/basic-file-based/src/routes/relative/link/path/$path/index.tsx
@@ -0,0 +1,31 @@
+import { Link, createFileRoute } from '@tanstack/react-router'
+
+export const Route = createFileRoute('/relative/link/path/$path/')({
+ component: RouteComponent,
+ loader: ({ params }) => {
+ return params
+ },
+})
+
+function RouteComponent() {
+ const { path } = Route.useParams()
+
+ return (
+
+
+ Hello from "/relative/links/path/{path}"!
+
+
+
+ To {path === 'a' ? 'b' : 'a'}
+
+
+
+ )
+}
diff --git a/e2e/react-router/basic-file-based/src/routes/relative/link/path/index.tsx b/e2e/react-router/basic-file-based/src/routes/relative/link/path/index.tsx
new file mode 100644
index 0000000000..be1c7b7a47
--- /dev/null
+++ b/e2e/react-router/basic-file-based/src/routes/relative/link/path/index.tsx
@@ -0,0 +1,18 @@
+import { Outlet, createFileRoute } from '@tanstack/react-router'
+
+export const Route = createFileRoute('/relative/link/path/')({
+ component: RouteComponent,
+})
+
+function RouteComponent() {
+ return (
+
+
+ Relative Routing Tests - Path Params
+
+
+
+
+
+ )
+}
diff --git a/e2e/react-router/basic-file-based/src/routes/relative/link/relative-link-a.tsx b/e2e/react-router/basic-file-based/src/routes/relative/link/relative-link-a.tsx
new file mode 100644
index 0000000000..72a1ee20ec
--- /dev/null
+++ b/e2e/react-router/basic-file-based/src/routes/relative/link/relative-link-a.tsx
@@ -0,0 +1,13 @@
+import { createFileRoute } from '@tanstack/react-router'
+
+export const Route = createFileRoute('/relative/link/relative-link-a')({
+ component: RouteComponent,
+})
+
+function RouteComponent() {
+ return (
+
+ Hello "/relative/link/relative-link-a"!
+
+ )
+}
diff --git a/e2e/react-router/basic-file-based/src/routes/relative/link/relative-link-b.tsx b/e2e/react-router/basic-file-based/src/routes/relative/link/relative-link-b.tsx
new file mode 100644
index 0000000000..e751331b3f
--- /dev/null
+++ b/e2e/react-router/basic-file-based/src/routes/relative/link/relative-link-b.tsx
@@ -0,0 +1,13 @@
+import { createFileRoute } from '@tanstack/react-router'
+
+export const Route = createFileRoute('/relative/link/relative-link-b')({
+ component: RouteComponent,
+})
+
+function RouteComponent() {
+ return (
+
+ Hello "/relative/link/relative-link-b"!
+
+ )
+}
diff --git a/e2e/react-router/basic-file-based/src/routes/relative/link/route.tsx b/e2e/react-router/basic-file-based/src/routes/relative/link/route.tsx
new file mode 100644
index 0000000000..ae3193613f
--- /dev/null
+++ b/e2e/react-router/basic-file-based/src/routes/relative/link/route.tsx
@@ -0,0 +1,103 @@
+import {
+ Link,
+ Outlet,
+ createFileRoute,
+ useNavigate,
+} from '@tanstack/react-router'
+import { useEffect } from 'react'
+
+export const Route = createFileRoute('/relative/link')({
+ component: RouteComponent,
+})
+
+function RouteComponent() {
+ const navigate = useNavigate()
+
+ useEffect(() => {
+ console.log('navigate')
+ }, [navigate])
+
+ return (
+
+
+ Relative Routing - Links - Index
+
+
+
+ Return To Home
+
+
+ Return To Index
+
+
+ Reload
+
+
+ Back
+
+
+ To Relative Link A
+
+
+ To Relative Link B
+
+
+ To Deeply Nested
+
+
+ To Path Param A
+
+
+ To With Search Params
+
+
+
+
+
+
+ )
+}
diff --git a/e2e/react-router/basic-file-based/src/routes/relative/link/with-search/index.tsx b/e2e/react-router/basic-file-based/src/routes/relative/link/with-search/index.tsx
new file mode 100644
index 0000000000..fd7515ac11
--- /dev/null
+++ b/e2e/react-router/basic-file-based/src/routes/relative/link/with-search/index.tsx
@@ -0,0 +1,28 @@
+import { createFileRoute, Link } from '@tanstack/react-router'
+import { z } from 'zod'
+
+export const Route = createFileRoute('/relative/link/with-search/')({
+ component: RouteComponent,
+ validateSearch: z.object({
+ searchParam: z.string().default('1'),
+ }),
+})
+
+function RouteComponent() {
+ const { searchParam } = Route.useSearch()
+ return (
+ <>
+
+ Hello "/relative/link/with-search/" searchParam: {searchParam}!
+
+
+
+ Update Search
+
+ >
+ )
+}
diff --git a/e2e/react-router/basic-file-based/src/routes/relative/useNavigate/nested/deep/index.tsx b/e2e/react-router/basic-file-based/src/routes/relative/useNavigate/nested/deep/index.tsx
new file mode 100644
index 0000000000..453a088d63
--- /dev/null
+++ b/e2e/react-router/basic-file-based/src/routes/relative/useNavigate/nested/deep/index.tsx
@@ -0,0 +1,13 @@
+import { createFileRoute } from '@tanstack/react-router'
+
+export const Route = createFileRoute('/relative/useNavigate/nested/deep/')({
+ component: RouteComponent,
+})
+
+function RouteComponent() {
+ return (
+
+ Hello "/relative/useNavigate/nested/deep/"!
+
+ )
+}
diff --git a/e2e/react-router/basic-file-based/src/routes/relative/useNavigate/nested/index.tsx b/e2e/react-router/basic-file-based/src/routes/relative/useNavigate/nested/index.tsx
new file mode 100644
index 0000000000..ace502df18
--- /dev/null
+++ b/e2e/react-router/basic-file-based/src/routes/relative/useNavigate/nested/index.tsx
@@ -0,0 +1,13 @@
+import { createFileRoute } from '@tanstack/react-router'
+
+export const Route = createFileRoute('/relative/useNavigate/nested/')({
+ component: RouteComponent,
+})
+
+function RouteComponent() {
+ return (
+
+ Hello "/relative/useNavigate/nested/"!
+
+ )
+}
diff --git a/e2e/react-router/basic-file-based/src/routes/relative/useNavigate/path/$path/index.tsx b/e2e/react-router/basic-file-based/src/routes/relative/useNavigate/path/$path/index.tsx
new file mode 100644
index 0000000000..2e6d4c59de
--- /dev/null
+++ b/e2e/react-router/basic-file-based/src/routes/relative/useNavigate/path/$path/index.tsx
@@ -0,0 +1,40 @@
+import { createFileRoute, useNavigate } from '@tanstack/react-router'
+
+export const Route = createFileRoute('/relative/useNavigate/path/$path/')({
+ component: RouteComponent,
+ loader: ({ params }) => {
+ return params
+ },
+})
+
+function RouteComponent() {
+ const navigate = useNavigate()
+
+ const { path } = Route.useParams()
+
+ return (
+
+
+ Hello from "/relative/useNavigate/path/{path}"!
+
+
+
+ navigate({
+ from: '/relative/useNavigate/path',
+ to: './$path',
+ params: { path: path === 'a' ? 'b' : 'a' },
+ })
+ }
+ className="mr-2"
+ data-testid="relative-useNavigate-path-param-switchAB"
+ >
+ To {path === 'a' ? 'b' : 'a'}
+
+
+
+ )
+}
diff --git a/e2e/react-router/basic-file-based/src/routes/relative/useNavigate/path/index.tsx b/e2e/react-router/basic-file-based/src/routes/relative/useNavigate/path/index.tsx
new file mode 100644
index 0000000000..18abb4af18
--- /dev/null
+++ b/e2e/react-router/basic-file-based/src/routes/relative/useNavigate/path/index.tsx
@@ -0,0 +1,18 @@
+import { Outlet, createFileRoute } from '@tanstack/react-router'
+
+export const Route = createFileRoute('/relative/useNavigate/path/')({
+ component: RouteComponent,
+})
+
+function RouteComponent() {
+ return (
+
+
+ Relative Routing Tests - Path Params
+
+
+
+
+
+ )
+}
diff --git a/e2e/react-router/basic-file-based/src/routes/relative/useNavigate/relative-useNavigate-a.tsx b/e2e/react-router/basic-file-based/src/routes/relative/useNavigate/relative-useNavigate-a.tsx
new file mode 100644
index 0000000000..e236d80f63
--- /dev/null
+++ b/e2e/react-router/basic-file-based/src/routes/relative/useNavigate/relative-useNavigate-a.tsx
@@ -0,0 +1,15 @@
+import { createFileRoute } from '@tanstack/react-router'
+
+export const Route = createFileRoute(
+ '/relative/useNavigate/relative-useNavigate-a',
+)({
+ component: RouteComponent,
+})
+
+function RouteComponent() {
+ return (
+
+ Hello "/relative/useNavigate/relative-useNavigate-a"!
+
+ )
+}
diff --git a/e2e/react-router/basic-file-based/src/routes/relative/useNavigate/relative-useNavigate-b.tsx b/e2e/react-router/basic-file-based/src/routes/relative/useNavigate/relative-useNavigate-b.tsx
new file mode 100644
index 0000000000..b6e1d607dd
--- /dev/null
+++ b/e2e/react-router/basic-file-based/src/routes/relative/useNavigate/relative-useNavigate-b.tsx
@@ -0,0 +1,15 @@
+import { createFileRoute } from '@tanstack/react-router'
+
+export const Route = createFileRoute(
+ '/relative/useNavigate/relative-useNavigate-b',
+)({
+ component: RouteComponent,
+})
+
+function RouteComponent() {
+ return (
+
+ Hello "/relative/useNavigate/relative-useNavigate-b"!
+
+ )
+}
diff --git a/e2e/react-router/basic-file-based/src/routes/relative/useNavigate/route.tsx b/e2e/react-router/basic-file-based/src/routes/relative/useNavigate/route.tsx
new file mode 100644
index 0000000000..567df92e8b
--- /dev/null
+++ b/e2e/react-router/basic-file-based/src/routes/relative/useNavigate/route.tsx
@@ -0,0 +1,134 @@
+import { Outlet, createFileRoute, useNavigate } from '@tanstack/react-router'
+import { useEffect } from 'react'
+
+export const Route = createFileRoute('/relative/useNavigate')({
+ component: RouteComponent,
+})
+
+function RouteComponent() {
+ const navigate = useNavigate()
+
+ useEffect(() => {
+ console.log('navigate')
+ }, [navigate])
+
+ return (
+
+
+ Relative Routing - Links - Index
+
+
+
+ navigate({
+ from: '/relative/useNavigate',
+ to: '..',
+ })
+ }
+ data-testid="relative-useNavigate-home"
+ className="mr-2 underline"
+ >
+ Return To Home
+
+
+ navigate({
+ from: '/relative/useNavigate',
+ to: '.',
+ })
+ }
+ data-testid="relative-useNavigate-index"
+ className="mr-2 underline"
+ >
+ Return To Index
+
+
+ navigate({
+ to: '.',
+ })
+ }
+ data-testid="relative-useNavigate-reload"
+ className="mr-2 underline"
+ >
+ Reload
+
+
+ navigate({
+ to: '..',
+ })
+ }
+ data-testid="relative-useNavigate-back"
+ className="mr-2 underline"
+ >
+ Back
+
+
+ navigate({
+ from: '/relative/useNavigate',
+ to: './relative-useNavigate-a',
+ })
+ }
+ data-testid="relative-useNavigate-a"
+ className="mr-2 underline"
+ >
+ To Relative useNavigate A
+
+
+ navigate({
+ from: '/relative/useNavigate',
+ to: './relative-useNavigate-b',
+ })
+ }
+ data-testid="relative-useNavigate-b"
+ className="mr-2 underline"
+ >
+ To Relative Link B
+
+
+ navigate({
+ from: '/relative/useNavigate',
+ to: './nested/deep',
+ })
+ }
+ data-testid="relative-useNavigate-deeply-nested"
+ className="mr-2 underline"
+ >
+ To Deeply Nested
+
+
+ navigate({
+ to: '/relative/useNavigate/path/$path',
+ params: { path: 'a' },
+ })
+ }
+ data-testid="relative-useNavigate-path"
+ className="mr-2 underline"
+ >
+ To Path Param A
+
+
+ navigate({
+ from: '/relative/useNavigate',
+ to: './with-search',
+ search: { searchParam: '1' },
+ })
+ }
+ data-testid="relative-useNavigate-withSearch"
+ className="mr-2 underline"
+ >
+ To With Search Params
+
+
+
+
+
+
+ )
+}
diff --git a/e2e/react-router/basic-file-based/src/routes/relative/useNavigate/with-search/index.tsx b/e2e/react-router/basic-file-based/src/routes/relative/useNavigate/with-search/index.tsx
new file mode 100644
index 0000000000..7342202e1d
--- /dev/null
+++ b/e2e/react-router/basic-file-based/src/routes/relative/useNavigate/with-search/index.tsx
@@ -0,0 +1,34 @@
+import { createFileRoute, useNavigate } from '@tanstack/react-router'
+import { z } from 'zod'
+
+export const Route = createFileRoute('/relative/useNavigate/with-search/')({
+ component: RouteComponent,
+ validateSearch: z.object({
+ searchParam: z.string().default('1'),
+ }),
+})
+
+function RouteComponent() {
+ const navigate = useNavigate()
+ const { searchParam } = Route.useSearch()
+
+ return (
+ <>
+
+ Hello "/relative/useNavigate/with-search/" searchParam: {searchParam}!
+
+
+
+ navigate({
+ to: '.',
+ search: { searchParam: '2' },
+ })
+ }
+ data-testid="relative-useNavigate-withSearch-update-param"
+ >
+ Update Search
+
+ >
+ )
+}
diff --git a/e2e/react-router/basic-file-based/tests/relative.spec.ts b/e2e/react-router/basic-file-based/tests/relative.spec.ts
new file mode 100644
index 0000000000..4850d3630d
--- /dev/null
+++ b/e2e/react-router/basic-file-based/tests/relative.spec.ts
@@ -0,0 +1,273 @@
+import { expect, test } from '@playwright/test'
+import combinateImport from 'combinate'
+import { getTestServerPort } from '@tanstack/router-e2e-utils'
+import packageJson from '../package.json' with { type: 'json' }
+
+// somehow playwright does not correctly import default exports
+const combinate = (combinateImport as any).default as typeof combinateImport
+
+const PORT = await getTestServerPort(packageJson.name)
+
+test.describe('relative_routing', () => {
+ const internalNavigationTestMatrix = combinate({
+ navigation: ['link', 'useNavigate'] as const,
+ })
+
+ internalNavigationTestMatrix.forEach(({ navigation }) => {
+ test(`simple relative navigation. navigation: ${navigation}`, async ({
+ page,
+ }) => {
+ await page.waitForLoadState('networkidle')
+ await page.goto(`/relative/${navigation}`)
+ await page.waitForURL(`http://localhost:${PORT}/relative/${navigation}`)
+
+ await expect(
+ page.getByTestId(`relative-${navigation}-header`),
+ ).toBeInViewport()
+
+ const indexLink = page.getByTestId(`relative-${navigation}-index`)
+ const backLink = page.getByTestId(`relative-${navigation}-back`)
+ const relativeRouteA = page.getByTestId(`relative-${navigation}-a`)
+ const relativeRouteB = page.getByTestId(`relative-${navigation}-b`)
+
+ await relativeRouteA.click()
+
+ await page.waitForURL(
+ `http://localhost:${PORT}/relative/${navigation}/relative-${navigation}-a`,
+ )
+
+ await expect(
+ page.getByTestId(`relative-${navigation}-header`),
+ ).toBeInViewport()
+
+ await expect(
+ page.getByTestId(`relative-${navigation}-a-header`),
+ ).toBeInViewport()
+
+ await relativeRouteB.click()
+
+ await page.waitForURL(
+ `http://localhost:${PORT}/relative/${navigation}/relative-${navigation}-b`,
+ )
+
+ await expect(
+ page.getByTestId(`relative-${navigation}-header`),
+ ).toBeInViewport()
+
+ await expect(
+ page.getByTestId(`relative-${navigation}-b-header`),
+ ).toBeInViewport()
+
+ await indexLink.click()
+
+ await page.waitForURL(`http://localhost:${PORT}/relative/${navigation}`)
+
+ await expect(
+ page.getByTestId(`relative-${navigation}-header`),
+ ).toBeInViewport()
+
+ await expect(
+ page.getByTestId(`relative-${navigation}-b-header`),
+ ).not.toBeInViewport()
+
+ await backLink.click()
+
+ await page.waitForURL(`http://localhost:${PORT}/relative`)
+
+ await expect(page.getByTestId(`relative-routing-home`)).toBeInViewport()
+ })
+
+ test(`nested chilren. navigation: ${navigation}`, async ({ page }) => {
+ await page.waitForLoadState('networkidle')
+ await page.goto(`/relative/${navigation}`)
+ await page.waitForURL(`http://localhost:${PORT}/relative/${navigation}`)
+
+ await expect(
+ page.getByTestId(`relative-${navigation}-header`),
+ ).toBeInViewport()
+
+ const backLink = page.getByTestId(`relative-${navigation}-back`)
+
+ const deeplyNestedChildRoute = page.getByTestId(
+ `relative-${navigation}-deeply-nested`,
+ )
+
+ await deeplyNestedChildRoute.click()
+
+ await page.waitForURL(
+ `http://localhost:${PORT}/relative/${navigation}/nested/deep`,
+ )
+
+ await expect(
+ page.getByTestId(`relative-${navigation}-nested-deep-header`),
+ ).toBeInViewport()
+
+ await backLink.click()
+
+ await page.waitForURL(
+ `http://localhost:${PORT}/relative/${navigation}/nested`,
+ )
+
+ await expect(
+ page.getByTestId(`relative-${navigation}-nested-header`),
+ ).toBeInViewport()
+ })
+
+ test(`with path params. navigation: ${navigation}`, async ({ page }) => {
+ await page.waitForLoadState('networkidle')
+ await page.goto(`/relative/${navigation}`)
+ await page.waitForURL(`http://localhost:${PORT}/relative/${navigation}`)
+
+ await expect(
+ page.getByTestId(`relative-${navigation}-header`),
+ ).toBeInViewport()
+
+ const pathParamRoute = page.getByTestId(`relative-${navigation}-path`)
+
+ await pathParamRoute.click()
+
+ await page.waitForURL(
+ `http://localhost:${PORT}/relative/${navigation}/path/a`,
+ )
+
+ expect(page.url().endsWith('/path/a')).toBe(true)
+
+ await expect(
+ page.getByTestId(`relative-${navigation}-path-param-header`),
+ ).toBeInViewport()
+
+ const switchParamLink = page.getByTestId(
+ `relative-${navigation}-path-param-switchAB`,
+ )
+
+ await switchParamLink.click()
+
+ await page.waitForURL(
+ `http://localhost:${PORT}/relative/${navigation}/path/b`,
+ )
+
+ expect(page.url().endsWith('/path/b')).toBe(true)
+
+ await expect(
+ page.getByTestId(`relative-${navigation}-path-param-header`),
+ ).toBeInViewport()
+ })
+
+ test(`with search params. navigation: ${navigation}`, async ({ page }) => {
+ await page.waitForLoadState('networkidle')
+ await page.goto(`/relative/${navigation}`)
+ await page.waitForURL(`http://localhost:${PORT}/relative/${navigation}`)
+
+ await expect(
+ page.getByTestId(`relative-${navigation}-header`),
+ ).toBeInViewport()
+
+ const searchParamRoute = page.getByTestId(
+ `relative-${navigation}-withSearch`,
+ )
+
+ await searchParamRoute.click()
+
+ let expectedUrl = new URL(
+ `http://localhost:${PORT}/relative/${navigation}/with-search?searchParam="1"`,
+ )
+
+ await page.waitForLoadState('domcontentloaded')
+
+ expect(page.url().toString()).toBe(expectedUrl.toString())
+
+ await expect(
+ page.getByTestId(`relative-${navigation}-withSearch-header`),
+ ).toBeInViewport()
+
+ await expect(
+ page.getByTestId(`relative-${navigation}-withSearch-header`),
+ ).toContainText('searchParam: 1')
+
+ const updateSearchLink = page.getByTestId(
+ `relative-${navigation}-withSearch-update-param`,
+ )
+
+ await updateSearchLink.click()
+
+ await page.waitForLoadState('domcontentloaded')
+
+ expectedUrl = new URL(
+ `http://localhost:${PORT}/relative/${navigation}/with-search?searchParam="2"`,
+ )
+
+ expect(page.url().toString()).toBe(expectedUrl.toString())
+
+ await expect(
+ page.getByTestId(`relative-${navigation}-withSearch-header`),
+ ).toContainText('searchParam: 2')
+
+ await expect(
+ page.getByTestId(`relative-${navigation}-withSearch-header`),
+ ).toBeInViewport()
+ })
+
+ test(`shouldn't cause excessive rendering. navigation: ${navigation}`, async ({
+ page,
+ }) => {
+ let navigateMsgs = 0
+
+ page.on('console', (msg) => {
+ if (msg.text() === 'navigate') {
+ navigateMsgs++
+ }
+ })
+
+ await page.waitForLoadState('networkidle')
+ await page.goto(`/relative/${navigation}`)
+ await page.waitForURL(`http://localhost:${PORT}/relative/${navigation}`)
+
+ await expect(
+ page.getByTestId(`relative-${navigation}-header`),
+ ).toBeInViewport()
+
+ expect(navigateMsgs).toBe(1)
+ const indexLink = page.getByTestId(`relative-${navigation}-index`)
+ const backLink = page.getByTestId(`relative-${navigation}-back`)
+ const relativeRouteA = page.getByTestId(`relative-${navigation}-a`)
+ const relativeRouteB = page.getByTestId(`relative-${navigation}-b`)
+ const deeplyNestedChildRoute = page.getByTestId(
+ `relative-${navigation}-deeply-nested`,
+ )
+ const pathParamRoute = page.getByTestId(`relative-${navigation}-path`)
+ const searchParamRoute = page.getByTestId(
+ `relative-${navigation}-withSearch`,
+ )
+
+ await relativeRouteA.click()
+ await page.waitForLoadState('domcontentloaded')
+ await relativeRouteB.click()
+ await page.waitForLoadState('domcontentloaded')
+ await deeplyNestedChildRoute.click()
+ await page.waitForLoadState('domcontentloaded')
+ await backLink.click()
+ await page.waitForLoadState('domcontentloaded')
+ await pathParamRoute.click()
+ await page.waitForLoadState('domcontentloaded')
+ const switchParamLink = page.getByTestId(
+ `relative-${navigation}-path-param-switchAB`,
+ )
+ await switchParamLink.click()
+ await page.waitForLoadState('domcontentloaded')
+ await searchParamRoute.click()
+ await page.waitForLoadState('domcontentloaded')
+
+ const updateSearchLink = page.getByTestId(
+ `relative-${navigation}-withSearch-update-param`,
+ )
+
+ await updateSearchLink.click()
+ await page.waitForLoadState('domcontentloaded')
+
+ await indexLink.click()
+ await page.waitForLoadState('domcontentloaded')
+
+ expect(navigateMsgs).toBe(1)
+ })
+ })
+})
diff --git a/e2e/solid-router/basic-file-based/src/routeTree.gen.ts b/e2e/solid-router/basic-file-based/src/routeTree.gen.ts
index 08d8fb4978..b81fbe69d5 100644
--- a/e2e/solid-router/basic-file-based/src/routeTree.gen.ts
+++ b/e2e/solid-router/basic-file-based/src/routeTree.gen.ts
@@ -22,6 +22,7 @@ import { Route as LayoutRouteImport } from './routes/_layout'
import { Route as SearchParamsRouteRouteImport } from './routes/search-params/route'
import { Route as IndexRouteImport } from './routes/index'
import { Route as SearchParamsIndexRouteImport } from './routes/search-params/index'
+import { Route as RelativeIndexRouteImport } from './routes/relative/index'
import { Route as RedirectIndexRouteImport } from './routes/redirect/index'
import { Route as PostsIndexRouteImport } from './routes/posts.index'
import { Route as SearchParamsDefaultRouteImport } from './routes/search-params/default'
@@ -32,7 +33,13 @@ import { Route as groupLazyinsideRouteImport } from './routes/(group)/lazyinside
import { Route as groupInsideRouteImport } from './routes/(group)/inside'
import { Route as groupLayoutRouteImport } from './routes/(group)/_layout'
import { Route as anotherGroupOnlyrouteinsideRouteImport } from './routes/(another-group)/onlyrouteinside'
+import { Route as RelativeUseNavigateRouteRouteImport } from './routes/relative/useNavigate/route'
+import { Route as RelativeLinkRouteRouteImport } from './routes/relative/link/route'
import { Route as RedirectTargetIndexRouteImport } from './routes/redirect/$target/index'
+import { Route as RelativeUseNavigateRelativeUseNavigateBRouteImport } from './routes/relative/useNavigate/relative-useNavigate-b'
+import { Route as RelativeUseNavigateRelativeUseNavigateARouteImport } from './routes/relative/useNavigate/relative-useNavigate-a'
+import { Route as RelativeLinkRelativeLinkBRouteImport } from './routes/relative/link/relative-link-b'
+import { Route as RelativeLinkRelativeLinkARouteImport } from './routes/relative/link/relative-link-a'
import { Route as RedirectPreloadThirdRouteImport } from './routes/redirect/preload/third'
import { Route as RedirectPreloadSecondRouteImport } from './routes/redirect/preload/second'
import { Route as RedirectPreloadFirstRouteImport } from './routes/redirect/preload/first'
@@ -44,6 +51,16 @@ import { Route as LayoutLayout2LayoutBRouteImport } from './routes/_layout/_layo
import { Route as LayoutLayout2LayoutARouteImport } from './routes/_layout/_layout-2/layout-a'
import { Route as groupSubfolderInsideRouteImport } from './routes/(group)/subfolder/inside'
import { Route as groupLayoutInsidelayoutRouteImport } from './routes/(group)/_layout.insidelayout'
+import { Route as RelativeUseNavigateWithSearchIndexRouteImport } from './routes/relative/useNavigate/with-search/index'
+import { Route as RelativeUseNavigatePathIndexRouteImport } from './routes/relative/useNavigate/path/index'
+import { Route as RelativeUseNavigateNestedIndexRouteImport } from './routes/relative/useNavigate/nested/index'
+import { Route as RelativeLinkWithSearchIndexRouteImport } from './routes/relative/link/with-search/index'
+import { Route as RelativeLinkPathIndexRouteImport } from './routes/relative/link/path/index'
+import { Route as RelativeLinkNestedIndexRouteImport } from './routes/relative/link/nested/index'
+import { Route as RelativeUseNavigatePathPathIndexRouteImport } from './routes/relative/useNavigate/path/$path/index'
+import { Route as RelativeUseNavigateNestedDeepIndexRouteImport } from './routes/relative/useNavigate/nested/deep/index'
+import { Route as RelativeLinkPathPathIndexRouteImport } from './routes/relative/link/path/$path/index'
+import { Route as RelativeLinkNestedDeepIndexRouteImport } from './routes/relative/link/nested/deep/index'
const groupRouteImport = createFileRoute('/(group)')()
@@ -105,6 +122,11 @@ const SearchParamsIndexRoute = SearchParamsIndexRouteImport.update({
path: '/',
getParentRoute: () => SearchParamsRouteRoute,
} as any)
+const RelativeIndexRoute = RelativeIndexRouteImport.update({
+ id: '/relative/',
+ path: '/relative/',
+ getParentRoute: () => rootRouteImport,
+} as any)
const RedirectIndexRoute = RedirectIndexRouteImport.update({
id: '/redirect/',
path: '/redirect/',
@@ -156,11 +178,46 @@ const anotherGroupOnlyrouteinsideRoute =
path: '/onlyrouteinside',
getParentRoute: () => rootRouteImport,
} as any)
+const RelativeUseNavigateRouteRoute =
+ RelativeUseNavigateRouteRouteImport.update({
+ id: '/relative/useNavigate',
+ path: '/relative/useNavigate',
+ getParentRoute: () => rootRouteImport,
+ } as any)
+const RelativeLinkRouteRoute = RelativeLinkRouteRouteImport.update({
+ id: '/relative/link',
+ path: '/relative/link',
+ getParentRoute: () => rootRouteImport,
+} as any)
const RedirectTargetIndexRoute = RedirectTargetIndexRouteImport.update({
id: '/',
path: '/',
getParentRoute: () => RedirectTargetRoute,
} as any)
+const RelativeUseNavigateRelativeUseNavigateBRoute =
+ RelativeUseNavigateRelativeUseNavigateBRouteImport.update({
+ id: '/relative-useNavigate-b',
+ path: '/relative-useNavigate-b',
+ getParentRoute: () => RelativeUseNavigateRouteRoute,
+ } as any)
+const RelativeUseNavigateRelativeUseNavigateARoute =
+ RelativeUseNavigateRelativeUseNavigateARouteImport.update({
+ id: '/relative-useNavigate-a',
+ path: '/relative-useNavigate-a',
+ getParentRoute: () => RelativeUseNavigateRouteRoute,
+ } as any)
+const RelativeLinkRelativeLinkBRoute =
+ RelativeLinkRelativeLinkBRouteImport.update({
+ id: '/relative-link-b',
+ path: '/relative-link-b',
+ getParentRoute: () => RelativeLinkRouteRoute,
+ } as any)
+const RelativeLinkRelativeLinkARoute =
+ RelativeLinkRelativeLinkARouteImport.update({
+ id: '/relative-link-a',
+ path: '/relative-link-a',
+ getParentRoute: () => RelativeLinkRouteRoute,
+ } as any)
const RedirectPreloadThirdRoute = RedirectPreloadThirdRouteImport.update({
id: '/redirect/preload/third',
path: '/redirect/preload/third',
@@ -217,6 +274,64 @@ const groupLayoutInsidelayoutRoute = groupLayoutInsidelayoutRouteImport.update({
path: '/insidelayout',
getParentRoute: () => groupLayoutRoute,
} as any)
+const RelativeUseNavigateWithSearchIndexRoute =
+ RelativeUseNavigateWithSearchIndexRouteImport.update({
+ id: '/with-search/',
+ path: '/with-search/',
+ getParentRoute: () => RelativeUseNavigateRouteRoute,
+ } as any)
+const RelativeUseNavigatePathIndexRoute =
+ RelativeUseNavigatePathIndexRouteImport.update({
+ id: '/path/',
+ path: '/path/',
+ getParentRoute: () => RelativeUseNavigateRouteRoute,
+ } as any)
+const RelativeUseNavigateNestedIndexRoute =
+ RelativeUseNavigateNestedIndexRouteImport.update({
+ id: '/nested/',
+ path: '/nested/',
+ getParentRoute: () => RelativeUseNavigateRouteRoute,
+ } as any)
+const RelativeLinkWithSearchIndexRoute =
+ RelativeLinkWithSearchIndexRouteImport.update({
+ id: '/with-search/',
+ path: '/with-search/',
+ getParentRoute: () => RelativeLinkRouteRoute,
+ } as any)
+const RelativeLinkPathIndexRoute = RelativeLinkPathIndexRouteImport.update({
+ id: '/path/',
+ path: '/path/',
+ getParentRoute: () => RelativeLinkRouteRoute,
+} as any)
+const RelativeLinkNestedIndexRoute = RelativeLinkNestedIndexRouteImport.update({
+ id: '/nested/',
+ path: '/nested/',
+ getParentRoute: () => RelativeLinkRouteRoute,
+} as any)
+const RelativeUseNavigatePathPathIndexRoute =
+ RelativeUseNavigatePathPathIndexRouteImport.update({
+ id: '/path/$path/',
+ path: '/path/$path/',
+ getParentRoute: () => RelativeUseNavigateRouteRoute,
+ } as any)
+const RelativeUseNavigateNestedDeepIndexRoute =
+ RelativeUseNavigateNestedDeepIndexRouteImport.update({
+ id: '/nested/deep/',
+ path: '/nested/deep/',
+ getParentRoute: () => RelativeUseNavigateRouteRoute,
+ } as any)
+const RelativeLinkPathPathIndexRoute =
+ RelativeLinkPathPathIndexRouteImport.update({
+ id: '/path/$path/',
+ path: '/path/$path/',
+ getParentRoute: () => RelativeLinkRouteRoute,
+ } as any)
+const RelativeLinkNestedDeepIndexRoute =
+ RelativeLinkNestedDeepIndexRouteImport.update({
+ id: '/nested/deep/',
+ path: '/nested/deep/',
+ getParentRoute: () => RelativeLinkRouteRoute,
+ } as any)
export interface FileRoutesByFullPath {
'/': typeof groupLayoutRouteWithChildren
@@ -228,6 +343,8 @@ export interface FileRoutesByFullPath {
'/notRemountDeps': typeof NotRemountDepsRoute
'/posts': typeof PostsRouteWithChildren
'/remountDeps': typeof RemountDepsRoute
+ '/relative/link': typeof RelativeLinkRouteRouteWithChildren
+ '/relative/useNavigate': typeof RelativeUseNavigateRouteRouteWithChildren
'/onlyrouteinside': typeof anotherGroupOnlyrouteinsideRoute
'/inside': typeof groupInsideRoute
'/lazyinside': typeof groupLazyinsideRoute
@@ -236,6 +353,7 @@ export interface FileRoutesByFullPath {
'/search-params/default': typeof SearchParamsDefaultRoute
'/posts/': typeof PostsIndexRoute
'/redirect': typeof RedirectIndexRoute
+ '/relative': typeof RelativeIndexRoute
'/search-params/': typeof SearchParamsIndexRoute
'/insidelayout': typeof groupLayoutInsidelayoutRoute
'/subfolder/inside': typeof groupSubfolderInsideRoute
@@ -248,7 +366,21 @@ export interface FileRoutesByFullPath {
'/redirect/preload/first': typeof RedirectPreloadFirstRoute
'/redirect/preload/second': typeof RedirectPreloadSecondRoute
'/redirect/preload/third': typeof RedirectPreloadThirdRoute
+ '/relative/link/relative-link-a': typeof RelativeLinkRelativeLinkARoute
+ '/relative/link/relative-link-b': typeof RelativeLinkRelativeLinkBRoute
+ '/relative/useNavigate/relative-useNavigate-a': typeof RelativeUseNavigateRelativeUseNavigateARoute
+ '/relative/useNavigate/relative-useNavigate-b': typeof RelativeUseNavigateRelativeUseNavigateBRoute
'/redirect/$target/': typeof RedirectTargetIndexRoute
+ '/relative/link/nested': typeof RelativeLinkNestedIndexRoute
+ '/relative/link/path': typeof RelativeLinkPathIndexRoute
+ '/relative/link/with-search': typeof RelativeLinkWithSearchIndexRoute
+ '/relative/useNavigate/nested': typeof RelativeUseNavigateNestedIndexRoute
+ '/relative/useNavigate/path': typeof RelativeUseNavigatePathIndexRoute
+ '/relative/useNavigate/with-search': typeof RelativeUseNavigateWithSearchIndexRoute
+ '/relative/link/nested/deep': typeof RelativeLinkNestedDeepIndexRoute
+ '/relative/link/path/$path': typeof RelativeLinkPathPathIndexRoute
+ '/relative/useNavigate/nested/deep': typeof RelativeUseNavigateNestedDeepIndexRoute
+ '/relative/useNavigate/path/$path': typeof RelativeUseNavigatePathPathIndexRoute
}
export interface FileRoutesByTo {
'/': typeof groupLayoutRouteWithChildren
@@ -258,6 +390,8 @@ export interface FileRoutesByTo {
'/editing-b': typeof EditingBRoute
'/notRemountDeps': typeof NotRemountDepsRoute
'/remountDeps': typeof RemountDepsRoute
+ '/relative/link': typeof RelativeLinkRouteRouteWithChildren
+ '/relative/useNavigate': typeof RelativeUseNavigateRouteRouteWithChildren
'/onlyrouteinside': typeof anotherGroupOnlyrouteinsideRoute
'/inside': typeof groupInsideRoute
'/lazyinside': typeof groupLazyinsideRoute
@@ -265,6 +399,7 @@ export interface FileRoutesByTo {
'/search-params/default': typeof SearchParamsDefaultRoute
'/posts': typeof PostsIndexRoute
'/redirect': typeof RedirectIndexRoute
+ '/relative': typeof RelativeIndexRoute
'/search-params': typeof SearchParamsIndexRoute
'/insidelayout': typeof groupLayoutInsidelayoutRoute
'/subfolder/inside': typeof groupSubfolderInsideRoute
@@ -277,7 +412,21 @@ export interface FileRoutesByTo {
'/redirect/preload/first': typeof RedirectPreloadFirstRoute
'/redirect/preload/second': typeof RedirectPreloadSecondRoute
'/redirect/preload/third': typeof RedirectPreloadThirdRoute
+ '/relative/link/relative-link-a': typeof RelativeLinkRelativeLinkARoute
+ '/relative/link/relative-link-b': typeof RelativeLinkRelativeLinkBRoute
+ '/relative/useNavigate/relative-useNavigate-a': typeof RelativeUseNavigateRelativeUseNavigateARoute
+ '/relative/useNavigate/relative-useNavigate-b': typeof RelativeUseNavigateRelativeUseNavigateBRoute
'/redirect/$target': typeof RedirectTargetIndexRoute
+ '/relative/link/nested': typeof RelativeLinkNestedIndexRoute
+ '/relative/link/path': typeof RelativeLinkPathIndexRoute
+ '/relative/link/with-search': typeof RelativeLinkWithSearchIndexRoute
+ '/relative/useNavigate/nested': typeof RelativeUseNavigateNestedIndexRoute
+ '/relative/useNavigate/path': typeof RelativeUseNavigatePathIndexRoute
+ '/relative/useNavigate/with-search': typeof RelativeUseNavigateWithSearchIndexRoute
+ '/relative/link/nested/deep': typeof RelativeLinkNestedDeepIndexRoute
+ '/relative/link/path/$path': typeof RelativeLinkPathPathIndexRoute
+ '/relative/useNavigate/nested/deep': typeof RelativeUseNavigateNestedDeepIndexRoute
+ '/relative/useNavigate/path/$path': typeof RelativeUseNavigatePathPathIndexRoute
}
export interface FileRoutesById {
__root__: typeof rootRouteImport
@@ -291,6 +440,8 @@ export interface FileRoutesById {
'/notRemountDeps': typeof NotRemountDepsRoute
'/posts': typeof PostsRouteWithChildren
'/remountDeps': typeof RemountDepsRoute
+ '/relative/link': typeof RelativeLinkRouteRouteWithChildren
+ '/relative/useNavigate': typeof RelativeUseNavigateRouteRouteWithChildren
'/(another-group)/onlyrouteinside': typeof anotherGroupOnlyrouteinsideRoute
'/(group)': typeof groupRouteWithChildren
'/(group)/_layout': typeof groupLayoutRouteWithChildren
@@ -302,6 +453,7 @@ export interface FileRoutesById {
'/search-params/default': typeof SearchParamsDefaultRoute
'/posts/': typeof PostsIndexRoute
'/redirect/': typeof RedirectIndexRoute
+ '/relative/': typeof RelativeIndexRoute
'/search-params/': typeof SearchParamsIndexRoute
'/(group)/_layout/insidelayout': typeof groupLayoutInsidelayoutRoute
'/(group)/subfolder/inside': typeof groupSubfolderInsideRoute
@@ -314,7 +466,21 @@ export interface FileRoutesById {
'/redirect/preload/first': typeof RedirectPreloadFirstRoute
'/redirect/preload/second': typeof RedirectPreloadSecondRoute
'/redirect/preload/third': typeof RedirectPreloadThirdRoute
+ '/relative/link/relative-link-a': typeof RelativeLinkRelativeLinkARoute
+ '/relative/link/relative-link-b': typeof RelativeLinkRelativeLinkBRoute
+ '/relative/useNavigate/relative-useNavigate-a': typeof RelativeUseNavigateRelativeUseNavigateARoute
+ '/relative/useNavigate/relative-useNavigate-b': typeof RelativeUseNavigateRelativeUseNavigateBRoute
'/redirect/$target/': typeof RedirectTargetIndexRoute
+ '/relative/link/nested/': typeof RelativeLinkNestedIndexRoute
+ '/relative/link/path/': typeof RelativeLinkPathIndexRoute
+ '/relative/link/with-search/': typeof RelativeLinkWithSearchIndexRoute
+ '/relative/useNavigate/nested/': typeof RelativeUseNavigateNestedIndexRoute
+ '/relative/useNavigate/path/': typeof RelativeUseNavigatePathIndexRoute
+ '/relative/useNavigate/with-search/': typeof RelativeUseNavigateWithSearchIndexRoute
+ '/relative/link/nested/deep/': typeof RelativeLinkNestedDeepIndexRoute
+ '/relative/link/path/$path/': typeof RelativeLinkPathPathIndexRoute
+ '/relative/useNavigate/nested/deep/': typeof RelativeUseNavigateNestedDeepIndexRoute
+ '/relative/useNavigate/path/$path/': typeof RelativeUseNavigatePathPathIndexRoute
}
export interface FileRouteTypes {
fileRoutesByFullPath: FileRoutesByFullPath
@@ -328,6 +494,8 @@ export interface FileRouteTypes {
| '/notRemountDeps'
| '/posts'
| '/remountDeps'
+ | '/relative/link'
+ | '/relative/useNavigate'
| '/onlyrouteinside'
| '/inside'
| '/lazyinside'
@@ -336,6 +504,7 @@ export interface FileRouteTypes {
| '/search-params/default'
| '/posts/'
| '/redirect'
+ | '/relative'
| '/search-params/'
| '/insidelayout'
| '/subfolder/inside'
@@ -348,7 +517,21 @@ export interface FileRouteTypes {
| '/redirect/preload/first'
| '/redirect/preload/second'
| '/redirect/preload/third'
+ | '/relative/link/relative-link-a'
+ | '/relative/link/relative-link-b'
+ | '/relative/useNavigate/relative-useNavigate-a'
+ | '/relative/useNavigate/relative-useNavigate-b'
| '/redirect/$target/'
+ | '/relative/link/nested'
+ | '/relative/link/path'
+ | '/relative/link/with-search'
+ | '/relative/useNavigate/nested'
+ | '/relative/useNavigate/path'
+ | '/relative/useNavigate/with-search'
+ | '/relative/link/nested/deep'
+ | '/relative/link/path/$path'
+ | '/relative/useNavigate/nested/deep'
+ | '/relative/useNavigate/path/$path'
fileRoutesByTo: FileRoutesByTo
to:
| '/'
@@ -358,6 +541,8 @@ export interface FileRouteTypes {
| '/editing-b'
| '/notRemountDeps'
| '/remountDeps'
+ | '/relative/link'
+ | '/relative/useNavigate'
| '/onlyrouteinside'
| '/inside'
| '/lazyinside'
@@ -365,6 +550,7 @@ export interface FileRouteTypes {
| '/search-params/default'
| '/posts'
| '/redirect'
+ | '/relative'
| '/search-params'
| '/insidelayout'
| '/subfolder/inside'
@@ -377,7 +563,21 @@ export interface FileRouteTypes {
| '/redirect/preload/first'
| '/redirect/preload/second'
| '/redirect/preload/third'
+ | '/relative/link/relative-link-a'
+ | '/relative/link/relative-link-b'
+ | '/relative/useNavigate/relative-useNavigate-a'
+ | '/relative/useNavigate/relative-useNavigate-b'
| '/redirect/$target'
+ | '/relative/link/nested'
+ | '/relative/link/path'
+ | '/relative/link/with-search'
+ | '/relative/useNavigate/nested'
+ | '/relative/useNavigate/path'
+ | '/relative/useNavigate/with-search'
+ | '/relative/link/nested/deep'
+ | '/relative/link/path/$path'
+ | '/relative/useNavigate/nested/deep'
+ | '/relative/useNavigate/path/$path'
id:
| '__root__'
| '/'
@@ -390,6 +590,8 @@ export interface FileRouteTypes {
| '/notRemountDeps'
| '/posts'
| '/remountDeps'
+ | '/relative/link'
+ | '/relative/useNavigate'
| '/(another-group)/onlyrouteinside'
| '/(group)'
| '/(group)/_layout'
@@ -401,6 +603,7 @@ export interface FileRouteTypes {
| '/search-params/default'
| '/posts/'
| '/redirect/'
+ | '/relative/'
| '/search-params/'
| '/(group)/_layout/insidelayout'
| '/(group)/subfolder/inside'
@@ -413,7 +616,21 @@ export interface FileRouteTypes {
| '/redirect/preload/first'
| '/redirect/preload/second'
| '/redirect/preload/third'
+ | '/relative/link/relative-link-a'
+ | '/relative/link/relative-link-b'
+ | '/relative/useNavigate/relative-useNavigate-a'
+ | '/relative/useNavigate/relative-useNavigate-b'
| '/redirect/$target/'
+ | '/relative/link/nested/'
+ | '/relative/link/path/'
+ | '/relative/link/with-search/'
+ | '/relative/useNavigate/nested/'
+ | '/relative/useNavigate/path/'
+ | '/relative/useNavigate/with-search/'
+ | '/relative/link/nested/deep/'
+ | '/relative/link/path/$path/'
+ | '/relative/useNavigate/nested/deep/'
+ | '/relative/useNavigate/path/$path/'
fileRoutesById: FileRoutesById
}
export interface RootRouteChildren {
@@ -427,10 +644,13 @@ export interface RootRouteChildren {
NotRemountDepsRoute: typeof NotRemountDepsRoute
PostsRoute: typeof PostsRouteWithChildren
RemountDepsRoute: typeof RemountDepsRoute
+ RelativeLinkRouteRoute: typeof RelativeLinkRouteRouteWithChildren
+ RelativeUseNavigateRouteRoute: typeof RelativeUseNavigateRouteRouteWithChildren
anotherGroupOnlyrouteinsideRoute: typeof anotherGroupOnlyrouteinsideRoute
groupRoute: typeof groupRouteWithChildren
RedirectTargetRoute: typeof RedirectTargetRouteWithChildren
RedirectIndexRoute: typeof RedirectIndexRoute
+ RelativeIndexRoute: typeof RelativeIndexRoute
ParamsSingleValueRoute: typeof ParamsSingleValueRoute
PostsPostIdEditRoute: typeof PostsPostIdEditRoute
RedirectPreloadFirstRoute: typeof RedirectPreloadFirstRoute
@@ -524,6 +744,13 @@ declare module '@tanstack/solid-router' {
preLoaderRoute: typeof SearchParamsIndexRouteImport
parentRoute: typeof SearchParamsRouteRoute
}
+ '/relative/': {
+ id: '/relative/'
+ path: '/relative'
+ fullPath: '/relative'
+ preLoaderRoute: typeof RelativeIndexRouteImport
+ parentRoute: typeof rootRouteImport
+ }
'/redirect/': {
id: '/redirect/'
path: '/redirect'
@@ -594,6 +821,20 @@ declare module '@tanstack/solid-router' {
preLoaderRoute: typeof anotherGroupOnlyrouteinsideRouteImport
parentRoute: typeof rootRouteImport
}
+ '/relative/useNavigate': {
+ id: '/relative/useNavigate'
+ path: '/relative/useNavigate'
+ fullPath: '/relative/useNavigate'
+ preLoaderRoute: typeof RelativeUseNavigateRouteRouteImport
+ parentRoute: typeof rootRouteImport
+ }
+ '/relative/link': {
+ id: '/relative/link'
+ path: '/relative/link'
+ fullPath: '/relative/link'
+ preLoaderRoute: typeof RelativeLinkRouteRouteImport
+ parentRoute: typeof rootRouteImport
+ }
'/redirect/$target/': {
id: '/redirect/$target/'
path: '/'
@@ -601,6 +842,34 @@ declare module '@tanstack/solid-router' {
preLoaderRoute: typeof RedirectTargetIndexRouteImport
parentRoute: typeof RedirectTargetRoute
}
+ '/relative/useNavigate/relative-useNavigate-b': {
+ id: '/relative/useNavigate/relative-useNavigate-b'
+ path: '/relative-useNavigate-b'
+ fullPath: '/relative/useNavigate/relative-useNavigate-b'
+ preLoaderRoute: typeof RelativeUseNavigateRelativeUseNavigateBRouteImport
+ parentRoute: typeof RelativeUseNavigateRouteRoute
+ }
+ '/relative/useNavigate/relative-useNavigate-a': {
+ id: '/relative/useNavigate/relative-useNavigate-a'
+ path: '/relative-useNavigate-a'
+ fullPath: '/relative/useNavigate/relative-useNavigate-a'
+ preLoaderRoute: typeof RelativeUseNavigateRelativeUseNavigateARouteImport
+ parentRoute: typeof RelativeUseNavigateRouteRoute
+ }
+ '/relative/link/relative-link-b': {
+ id: '/relative/link/relative-link-b'
+ path: '/relative-link-b'
+ fullPath: '/relative/link/relative-link-b'
+ preLoaderRoute: typeof RelativeLinkRelativeLinkBRouteImport
+ parentRoute: typeof RelativeLinkRouteRoute
+ }
+ '/relative/link/relative-link-a': {
+ id: '/relative/link/relative-link-a'
+ path: '/relative-link-a'
+ fullPath: '/relative/link/relative-link-a'
+ preLoaderRoute: typeof RelativeLinkRelativeLinkARouteImport
+ parentRoute: typeof RelativeLinkRouteRoute
+ }
'/redirect/preload/third': {
id: '/redirect/preload/third'
path: '/redirect/preload/third'
@@ -678,6 +947,76 @@ declare module '@tanstack/solid-router' {
preLoaderRoute: typeof groupLayoutInsidelayoutRouteImport
parentRoute: typeof groupLayoutRoute
}
+ '/relative/useNavigate/with-search/': {
+ id: '/relative/useNavigate/with-search/'
+ path: '/with-search'
+ fullPath: '/relative/useNavigate/with-search'
+ preLoaderRoute: typeof RelativeUseNavigateWithSearchIndexRouteImport
+ parentRoute: typeof RelativeUseNavigateRouteRoute
+ }
+ '/relative/useNavigate/path/': {
+ id: '/relative/useNavigate/path/'
+ path: '/path'
+ fullPath: '/relative/useNavigate/path'
+ preLoaderRoute: typeof RelativeUseNavigatePathIndexRouteImport
+ parentRoute: typeof RelativeUseNavigateRouteRoute
+ }
+ '/relative/useNavigate/nested/': {
+ id: '/relative/useNavigate/nested/'
+ path: '/nested'
+ fullPath: '/relative/useNavigate/nested'
+ preLoaderRoute: typeof RelativeUseNavigateNestedIndexRouteImport
+ parentRoute: typeof RelativeUseNavigateRouteRoute
+ }
+ '/relative/link/with-search/': {
+ id: '/relative/link/with-search/'
+ path: '/with-search'
+ fullPath: '/relative/link/with-search'
+ preLoaderRoute: typeof RelativeLinkWithSearchIndexRouteImport
+ parentRoute: typeof RelativeLinkRouteRoute
+ }
+ '/relative/link/path/': {
+ id: '/relative/link/path/'
+ path: '/path'
+ fullPath: '/relative/link/path'
+ preLoaderRoute: typeof RelativeLinkPathIndexRouteImport
+ parentRoute: typeof RelativeLinkRouteRoute
+ }
+ '/relative/link/nested/': {
+ id: '/relative/link/nested/'
+ path: '/nested'
+ fullPath: '/relative/link/nested'
+ preLoaderRoute: typeof RelativeLinkNestedIndexRouteImport
+ parentRoute: typeof RelativeLinkRouteRoute
+ }
+ '/relative/useNavigate/path/$path/': {
+ id: '/relative/useNavigate/path/$path/'
+ path: '/path/$path'
+ fullPath: '/relative/useNavigate/path/$path'
+ preLoaderRoute: typeof RelativeUseNavigatePathPathIndexRouteImport
+ parentRoute: typeof RelativeUseNavigateRouteRoute
+ }
+ '/relative/useNavigate/nested/deep/': {
+ id: '/relative/useNavigate/nested/deep/'
+ path: '/nested/deep'
+ fullPath: '/relative/useNavigate/nested/deep'
+ preLoaderRoute: typeof RelativeUseNavigateNestedDeepIndexRouteImport
+ parentRoute: typeof RelativeUseNavigateRouteRoute
+ }
+ '/relative/link/path/$path/': {
+ id: '/relative/link/path/$path/'
+ path: '/path/$path'
+ fullPath: '/relative/link/path/$path'
+ preLoaderRoute: typeof RelativeLinkPathPathIndexRouteImport
+ parentRoute: typeof RelativeLinkRouteRoute
+ }
+ '/relative/link/nested/deep/': {
+ id: '/relative/link/nested/deep/'
+ path: '/nested/deep'
+ fullPath: '/relative/link/nested/deep'
+ preLoaderRoute: typeof RelativeLinkNestedDeepIndexRouteImport
+ parentRoute: typeof RelativeLinkRouteRoute
+ }
}
}
@@ -731,6 +1070,60 @@ const PostsRouteChildren: PostsRouteChildren = {
const PostsRouteWithChildren = PostsRoute._addFileChildren(PostsRouteChildren)
+interface RelativeLinkRouteRouteChildren {
+ RelativeLinkRelativeLinkARoute: typeof RelativeLinkRelativeLinkARoute
+ RelativeLinkRelativeLinkBRoute: typeof RelativeLinkRelativeLinkBRoute
+ RelativeLinkNestedIndexRoute: typeof RelativeLinkNestedIndexRoute
+ RelativeLinkPathIndexRoute: typeof RelativeLinkPathIndexRoute
+ RelativeLinkWithSearchIndexRoute: typeof RelativeLinkWithSearchIndexRoute
+ RelativeLinkNestedDeepIndexRoute: typeof RelativeLinkNestedDeepIndexRoute
+ RelativeLinkPathPathIndexRoute: typeof RelativeLinkPathPathIndexRoute
+}
+
+const RelativeLinkRouteRouteChildren: RelativeLinkRouteRouteChildren = {
+ RelativeLinkRelativeLinkARoute: RelativeLinkRelativeLinkARoute,
+ RelativeLinkRelativeLinkBRoute: RelativeLinkRelativeLinkBRoute,
+ RelativeLinkNestedIndexRoute: RelativeLinkNestedIndexRoute,
+ RelativeLinkPathIndexRoute: RelativeLinkPathIndexRoute,
+ RelativeLinkWithSearchIndexRoute: RelativeLinkWithSearchIndexRoute,
+ RelativeLinkNestedDeepIndexRoute: RelativeLinkNestedDeepIndexRoute,
+ RelativeLinkPathPathIndexRoute: RelativeLinkPathPathIndexRoute,
+}
+
+const RelativeLinkRouteRouteWithChildren =
+ RelativeLinkRouteRoute._addFileChildren(RelativeLinkRouteRouteChildren)
+
+interface RelativeUseNavigateRouteRouteChildren {
+ RelativeUseNavigateRelativeUseNavigateARoute: typeof RelativeUseNavigateRelativeUseNavigateARoute
+ RelativeUseNavigateRelativeUseNavigateBRoute: typeof RelativeUseNavigateRelativeUseNavigateBRoute
+ RelativeUseNavigateNestedIndexRoute: typeof RelativeUseNavigateNestedIndexRoute
+ RelativeUseNavigatePathIndexRoute: typeof RelativeUseNavigatePathIndexRoute
+ RelativeUseNavigateWithSearchIndexRoute: typeof RelativeUseNavigateWithSearchIndexRoute
+ RelativeUseNavigateNestedDeepIndexRoute: typeof RelativeUseNavigateNestedDeepIndexRoute
+ RelativeUseNavigatePathPathIndexRoute: typeof RelativeUseNavigatePathPathIndexRoute
+}
+
+const RelativeUseNavigateRouteRouteChildren: RelativeUseNavigateRouteRouteChildren =
+ {
+ RelativeUseNavigateRelativeUseNavigateARoute:
+ RelativeUseNavigateRelativeUseNavigateARoute,
+ RelativeUseNavigateRelativeUseNavigateBRoute:
+ RelativeUseNavigateRelativeUseNavigateBRoute,
+ RelativeUseNavigateNestedIndexRoute: RelativeUseNavigateNestedIndexRoute,
+ RelativeUseNavigatePathIndexRoute: RelativeUseNavigatePathIndexRoute,
+ RelativeUseNavigateWithSearchIndexRoute:
+ RelativeUseNavigateWithSearchIndexRoute,
+ RelativeUseNavigateNestedDeepIndexRoute:
+ RelativeUseNavigateNestedDeepIndexRoute,
+ RelativeUseNavigatePathPathIndexRoute:
+ RelativeUseNavigatePathPathIndexRoute,
+ }
+
+const RelativeUseNavigateRouteRouteWithChildren =
+ RelativeUseNavigateRouteRoute._addFileChildren(
+ RelativeUseNavigateRouteRouteChildren,
+ )
+
interface groupLayoutRouteChildren {
groupLayoutInsidelayoutRoute: typeof groupLayoutInsidelayoutRoute
}
@@ -786,10 +1179,13 @@ const rootRouteChildren: RootRouteChildren = {
NotRemountDepsRoute: NotRemountDepsRoute,
PostsRoute: PostsRouteWithChildren,
RemountDepsRoute: RemountDepsRoute,
+ RelativeLinkRouteRoute: RelativeLinkRouteRouteWithChildren,
+ RelativeUseNavigateRouteRoute: RelativeUseNavigateRouteRouteWithChildren,
anotherGroupOnlyrouteinsideRoute: anotherGroupOnlyrouteinsideRoute,
groupRoute: groupRouteWithChildren,
RedirectTargetRoute: RedirectTargetRouteWithChildren,
RedirectIndexRoute: RedirectIndexRoute,
+ RelativeIndexRoute: RelativeIndexRoute,
ParamsSingleValueRoute: ParamsSingleValueRoute,
PostsPostIdEditRoute: PostsPostIdEditRoute,
RedirectPreloadFirstRoute: RedirectPreloadFirstRoute,
diff --git a/e2e/solid-router/basic-file-based/src/routes/__root.tsx b/e2e/solid-router/basic-file-based/src/routes/__root.tsx
index c9ff803463..0997c45b37 100644
--- a/e2e/solid-router/basic-file-based/src/routes/__root.tsx
+++ b/e2e/solid-router/basic-file-based/src/routes/__root.tsx
@@ -122,6 +122,14 @@ function RootComponent() {
>
redirect
{' '}
+
+ relative routing
+ {' '}
+
+ Relative Routing Tests - Home
+
+
+ Using Links
+ Using useNavigate
+
+
+
+
+
+ )
+}
diff --git a/e2e/solid-router/basic-file-based/src/routes/relative/link/nested/deep/index.tsx b/e2e/solid-router/basic-file-based/src/routes/relative/link/nested/deep/index.tsx
new file mode 100644
index 0000000000..d92d2b5e7c
--- /dev/null
+++ b/e2e/solid-router/basic-file-based/src/routes/relative/link/nested/deep/index.tsx
@@ -0,0 +1,13 @@
+import { createFileRoute } from '@tanstack/solid-router'
+
+export const Route = createFileRoute('/relative/link/nested/deep/')({
+ component: RouteComponent,
+})
+
+function RouteComponent() {
+ return (
+
+ Hello "/relative/link/nested/deep/"!
+
+ )
+}
diff --git a/e2e/solid-router/basic-file-based/src/routes/relative/link/nested/index.tsx b/e2e/solid-router/basic-file-based/src/routes/relative/link/nested/index.tsx
new file mode 100644
index 0000000000..5ddaa68d75
--- /dev/null
+++ b/e2e/solid-router/basic-file-based/src/routes/relative/link/nested/index.tsx
@@ -0,0 +1,13 @@
+import { createFileRoute } from '@tanstack/solid-router'
+
+export const Route = createFileRoute('/relative/link/nested/')({
+ component: RouteComponent,
+})
+
+function RouteComponent() {
+ return (
+
+ Hello "/relative/link/nested/"!
+
+ )
+}
diff --git a/e2e/solid-router/basic-file-based/src/routes/relative/link/path/$path/index.tsx b/e2e/solid-router/basic-file-based/src/routes/relative/link/path/$path/index.tsx
new file mode 100644
index 0000000000..1cf079d4b8
--- /dev/null
+++ b/e2e/solid-router/basic-file-based/src/routes/relative/link/path/$path/index.tsx
@@ -0,0 +1,31 @@
+import { Link, createFileRoute } from '@tanstack/solid-router'
+
+export const Route = createFileRoute('/relative/link/path/$path/')({
+ component: RouteComponent,
+ loader: ({ params }) => {
+ return params
+ },
+})
+
+function RouteComponent() {
+ const params = Route.useParams()
+
+ return (
+
+
+ Hello from "/relative/links/path/{params().path}"!
+
+
+
+ To {params().path === 'a' ? 'b' : 'a'}
+
+
+
+ )
+}
diff --git a/e2e/solid-router/basic-file-based/src/routes/relative/link/path/index.tsx b/e2e/solid-router/basic-file-based/src/routes/relative/link/path/index.tsx
new file mode 100644
index 0000000000..36bf3f5cde
--- /dev/null
+++ b/e2e/solid-router/basic-file-based/src/routes/relative/link/path/index.tsx
@@ -0,0 +1,18 @@
+import { Outlet, createFileRoute } from '@tanstack/solid-router'
+
+export const Route = createFileRoute('/relative/link/path/')({
+ component: RouteComponent,
+})
+
+function RouteComponent() {
+ return (
+
+
+ Relative Routing Tests - Path Params
+
+
+
+
+
+ )
+}
diff --git a/e2e/solid-router/basic-file-based/src/routes/relative/link/relative-link-a.tsx b/e2e/solid-router/basic-file-based/src/routes/relative/link/relative-link-a.tsx
new file mode 100644
index 0000000000..daa2cea064
--- /dev/null
+++ b/e2e/solid-router/basic-file-based/src/routes/relative/link/relative-link-a.tsx
@@ -0,0 +1,13 @@
+import { createFileRoute } from '@tanstack/solid-router'
+
+export const Route = createFileRoute('/relative/link/relative-link-a')({
+ component: RouteComponent,
+})
+
+function RouteComponent() {
+ return (
+
+ Hello "/relative/link/relative-link-a"!
+
+ )
+}
diff --git a/e2e/solid-router/basic-file-based/src/routes/relative/link/relative-link-b.tsx b/e2e/solid-router/basic-file-based/src/routes/relative/link/relative-link-b.tsx
new file mode 100644
index 0000000000..9f80899b73
--- /dev/null
+++ b/e2e/solid-router/basic-file-based/src/routes/relative/link/relative-link-b.tsx
@@ -0,0 +1,13 @@
+import { createFileRoute } from '@tanstack/solid-router'
+
+export const Route = createFileRoute('/relative/link/relative-link-b')({
+ component: RouteComponent,
+})
+
+function RouteComponent() {
+ return (
+
+ Hello "/relative/link/relative-link-b"!
+
+ )
+}
diff --git a/e2e/solid-router/basic-file-based/src/routes/relative/link/route.tsx b/e2e/solid-router/basic-file-based/src/routes/relative/link/route.tsx
new file mode 100644
index 0000000000..2d77690c4e
--- /dev/null
+++ b/e2e/solid-router/basic-file-based/src/routes/relative/link/route.tsx
@@ -0,0 +1,95 @@
+import {
+ Link,
+ Outlet,
+ createFileRoute,
+ useNavigate,
+} from '@tanstack/solid-router'
+import { createEffect } from 'solid-js'
+
+export const Route = createFileRoute('/relative/link')({
+ component: RouteComponent,
+})
+
+function RouteComponent() {
+ const navigate = useNavigate()
+
+ createEffect(() => {
+ console.log('navigate')
+ })
+
+ return (
+
+
+ Relative Routing - Links - Index
+
+
+
+ Return To Home
+
+
+ Return To Index
+
+
+ Reload
+
+
+ Back
+
+
+ To Relative Link A
+
+
+ To Relative Link B
+
+
+ To Deeply Nested
+
+
+ To Path Param A
+
+
+ To With Search Params
+
+
+
+
+
+
+ )
+}
diff --git a/e2e/solid-router/basic-file-based/src/routes/relative/link/with-search/index.tsx b/e2e/solid-router/basic-file-based/src/routes/relative/link/with-search/index.tsx
new file mode 100644
index 0000000000..f571340a56
--- /dev/null
+++ b/e2e/solid-router/basic-file-based/src/routes/relative/link/with-search/index.tsx
@@ -0,0 +1,29 @@
+import { Link, createFileRoute } from '@tanstack/solid-router'
+import { z } from 'zod'
+
+export const Route = createFileRoute('/relative/link/with-search/')({
+ component: RouteComponent,
+ validateSearch: z.object({
+ searchParam: z.string().default('1'),
+ }),
+})
+
+function RouteComponent() {
+ const searchParams = Route.useSearch()
+ return (
+ <>
+
+ Hello "/relative/link/with-search/" searchParam:{' '}
+ {searchParams().searchParam}!
+
+
+
+ Update Search
+
+ >
+ )
+}
diff --git a/e2e/solid-router/basic-file-based/src/routes/relative/useNavigate/nested/deep/index.tsx b/e2e/solid-router/basic-file-based/src/routes/relative/useNavigate/nested/deep/index.tsx
new file mode 100644
index 0000000000..a373967b11
--- /dev/null
+++ b/e2e/solid-router/basic-file-based/src/routes/relative/useNavigate/nested/deep/index.tsx
@@ -0,0 +1,13 @@
+import { createFileRoute } from '@tanstack/solid-router'
+
+export const Route = createFileRoute('/relative/useNavigate/nested/deep/')({
+ component: RouteComponent,
+})
+
+function RouteComponent() {
+ return (
+
+ Hello "/relative/useNavigate/nested/deep/"!
+
+ )
+}
diff --git a/e2e/solid-router/basic-file-based/src/routes/relative/useNavigate/nested/index.tsx b/e2e/solid-router/basic-file-based/src/routes/relative/useNavigate/nested/index.tsx
new file mode 100644
index 0000000000..5e41c4c6db
--- /dev/null
+++ b/e2e/solid-router/basic-file-based/src/routes/relative/useNavigate/nested/index.tsx
@@ -0,0 +1,13 @@
+import { createFileRoute } from '@tanstack/solid-router'
+
+export const Route = createFileRoute('/relative/useNavigate/nested/')({
+ component: RouteComponent,
+})
+
+function RouteComponent() {
+ return (
+
+ Hello "/relative/useNavigate/nested/"!
+
+ )
+}
diff --git a/e2e/solid-router/basic-file-based/src/routes/relative/useNavigate/path/$path/index.tsx b/e2e/solid-router/basic-file-based/src/routes/relative/useNavigate/path/$path/index.tsx
new file mode 100644
index 0000000000..167aca58d7
--- /dev/null
+++ b/e2e/solid-router/basic-file-based/src/routes/relative/useNavigate/path/$path/index.tsx
@@ -0,0 +1,40 @@
+import { createFileRoute, useNavigate } from '@tanstack/solid-router'
+
+export const Route = createFileRoute('/relative/useNavigate/path/$path/')({
+ component: RouteComponent,
+ loader: ({ params }) => {
+ return params
+ },
+})
+
+function RouteComponent() {
+ const navigate = useNavigate()
+
+ const params = Route.useParams()
+
+ return (
+
+
+ Hello from "/relative/useNavigate/path/{params().path}"!
+
+
+
+ navigate({
+ from: '/relative/useNavigate/path',
+ to: './$path',
+ params: { path: params().path === 'a' ? 'b' : 'a' },
+ })
+ }
+ class="mr-2"
+ data-testid="relative-useNavigate-path-param-switchAB"
+ >
+ To {params().path === 'a' ? 'b' : 'a'}
+
+
+
+ )
+}
diff --git a/e2e/solid-router/basic-file-based/src/routes/relative/useNavigate/path/index.tsx b/e2e/solid-router/basic-file-based/src/routes/relative/useNavigate/path/index.tsx
new file mode 100644
index 0000000000..6734648ae5
--- /dev/null
+++ b/e2e/solid-router/basic-file-based/src/routes/relative/useNavigate/path/index.tsx
@@ -0,0 +1,18 @@
+import { Outlet, createFileRoute } from '@tanstack/solid-router'
+
+export const Route = createFileRoute('/relative/useNavigate/path/')({
+ component: RouteComponent,
+})
+
+function RouteComponent() {
+ return (
+
+
+ Relative Routing Tests - Path Params
+
+
+
+
+
+ )
+}
diff --git a/e2e/solid-router/basic-file-based/src/routes/relative/useNavigate/relative-useNavigate-a.tsx b/e2e/solid-router/basic-file-based/src/routes/relative/useNavigate/relative-useNavigate-a.tsx
new file mode 100644
index 0000000000..bbe5625a62
--- /dev/null
+++ b/e2e/solid-router/basic-file-based/src/routes/relative/useNavigate/relative-useNavigate-a.tsx
@@ -0,0 +1,15 @@
+import { createFileRoute } from '@tanstack/solid-router'
+
+export const Route = createFileRoute(
+ '/relative/useNavigate/relative-useNavigate-a',
+)({
+ component: RouteComponent,
+})
+
+function RouteComponent() {
+ return (
+
+ Hello "/relative/useNavigate/relative-useNavigate-a"!
+
+ )
+}
diff --git a/e2e/solid-router/basic-file-based/src/routes/relative/useNavigate/relative-useNavigate-b.tsx b/e2e/solid-router/basic-file-based/src/routes/relative/useNavigate/relative-useNavigate-b.tsx
new file mode 100644
index 0000000000..9be49cfcdc
--- /dev/null
+++ b/e2e/solid-router/basic-file-based/src/routes/relative/useNavigate/relative-useNavigate-b.tsx
@@ -0,0 +1,15 @@
+import { createFileRoute } from '@tanstack/solid-router'
+
+export const Route = createFileRoute(
+ '/relative/useNavigate/relative-useNavigate-b',
+)({
+ component: RouteComponent,
+})
+
+function RouteComponent() {
+ return (
+
+ Hello "/relative/useNavigate/relative-useNavigate-b"!
+
+ )
+}
diff --git a/e2e/solid-router/basic-file-based/src/routes/relative/useNavigate/route.tsx b/e2e/solid-router/basic-file-based/src/routes/relative/useNavigate/route.tsx
new file mode 100644
index 0000000000..7bdaeaecb5
--- /dev/null
+++ b/e2e/solid-router/basic-file-based/src/routes/relative/useNavigate/route.tsx
@@ -0,0 +1,134 @@
+import { Outlet, createFileRoute, useNavigate } from '@tanstack/solid-router'
+import { createEffect } from 'solid-js'
+
+export const Route = createFileRoute('/relative/useNavigate')({
+ component: RouteComponent,
+})
+
+function RouteComponent() {
+ const navigate = useNavigate()
+
+ createEffect(() => {
+ console.log('navigate')
+ })
+
+ return (
+
+
+ Relative Routing - Links - Index
+
+
+
+ navigate({
+ from: '/relative/useNavigate',
+ to: '..',
+ })
+ }
+ data-testid="relative-useNavigate-home"
+ class="mr-2 underline"
+ >
+ Return To Home
+
+
+ navigate({
+ from: '/relative/useNavigate',
+ to: '.',
+ })
+ }
+ data-testid="relative-useNavigate-index"
+ class="mr-2 underline"
+ >
+ Return To Index
+
+
+ navigate({
+ to: '.',
+ })
+ }
+ data-testid="relative-useNavigate-reload"
+ class="mr-2 underline"
+ >
+ Reload
+
+
+ navigate({
+ to: '..',
+ })
+ }
+ data-testid="relative-useNavigate-back"
+ class="mr-2 underline"
+ >
+ Back
+
+
+ navigate({
+ from: '/relative/useNavigate',
+ to: './relative-useNavigate-a',
+ })
+ }
+ data-testid="relative-useNavigate-a"
+ class="mr-2 underline"
+ >
+ To Relative useNavigate A
+
+
+ navigate({
+ from: '/relative/useNavigate',
+ to: './relative-useNavigate-b',
+ })
+ }
+ data-testid="relative-useNavigate-b"
+ class="mr-2 underline"
+ >
+ To Relative Link B
+
+
+ navigate({
+ from: '/relative/useNavigate',
+ to: './nested/deep',
+ })
+ }
+ data-testid="relative-useNavigate-deeply-nested"
+ class="mr-2 underline"
+ >
+ To Deeply Nested
+
+
+ navigate({
+ to: '/relative/useNavigate/path/$path',
+ params: { path: 'a' },
+ })
+ }
+ data-testid="relative-useNavigate-path"
+ class="mr-2 underline"
+ >
+ To Path Param A
+
+
+ navigate({
+ from: '/relative/useNavigate',
+ to: './with-search',
+ search: { searchParam: '1' },
+ })
+ }
+ data-testid="relative-useNavigate-withSearch"
+ class="mr-2 underline"
+ >
+ To With Search Params
+
+
+
+
+
+
+ )
+}
diff --git a/e2e/solid-router/basic-file-based/src/routes/relative/useNavigate/with-search/index.tsx b/e2e/solid-router/basic-file-based/src/routes/relative/useNavigate/with-search/index.tsx
new file mode 100644
index 0000000000..524eae04a7
--- /dev/null
+++ b/e2e/solid-router/basic-file-based/src/routes/relative/useNavigate/with-search/index.tsx
@@ -0,0 +1,35 @@
+import { createFileRoute, useNavigate } from '@tanstack/solid-router'
+import { z } from 'zod'
+
+export const Route = createFileRoute('/relative/useNavigate/with-search/')({
+ component: RouteComponent,
+ validateSearch: z.object({
+ searchParam: z.string().default('1'),
+ }),
+})
+
+function RouteComponent() {
+ const navigate = useNavigate()
+ const searchParams = Route.useSearch()
+
+ return (
+ <>
+
+ Hello "/relative/useNavigate/with-search/" searchParam:{' '}
+ {searchParams().searchParam}!
+
+
+
+ navigate({
+ to: '.',
+ search: { searchParam: '2' },
+ })
+ }
+ data-testid="relative-useNavigate-withSearch-update-param"
+ >
+ Update Search
+
+ >
+ )
+}
diff --git a/e2e/solid-router/basic-file-based/tests/relative.spec.ts b/e2e/solid-router/basic-file-based/tests/relative.spec.ts
new file mode 100644
index 0000000000..4850d3630d
--- /dev/null
+++ b/e2e/solid-router/basic-file-based/tests/relative.spec.ts
@@ -0,0 +1,273 @@
+import { expect, test } from '@playwright/test'
+import combinateImport from 'combinate'
+import { getTestServerPort } from '@tanstack/router-e2e-utils'
+import packageJson from '../package.json' with { type: 'json' }
+
+// somehow playwright does not correctly import default exports
+const combinate = (combinateImport as any).default as typeof combinateImport
+
+const PORT = await getTestServerPort(packageJson.name)
+
+test.describe('relative_routing', () => {
+ const internalNavigationTestMatrix = combinate({
+ navigation: ['link', 'useNavigate'] as const,
+ })
+
+ internalNavigationTestMatrix.forEach(({ navigation }) => {
+ test(`simple relative navigation. navigation: ${navigation}`, async ({
+ page,
+ }) => {
+ await page.waitForLoadState('networkidle')
+ await page.goto(`/relative/${navigation}`)
+ await page.waitForURL(`http://localhost:${PORT}/relative/${navigation}`)
+
+ await expect(
+ page.getByTestId(`relative-${navigation}-header`),
+ ).toBeInViewport()
+
+ const indexLink = page.getByTestId(`relative-${navigation}-index`)
+ const backLink = page.getByTestId(`relative-${navigation}-back`)
+ const relativeRouteA = page.getByTestId(`relative-${navigation}-a`)
+ const relativeRouteB = page.getByTestId(`relative-${navigation}-b`)
+
+ await relativeRouteA.click()
+
+ await page.waitForURL(
+ `http://localhost:${PORT}/relative/${navigation}/relative-${navigation}-a`,
+ )
+
+ await expect(
+ page.getByTestId(`relative-${navigation}-header`),
+ ).toBeInViewport()
+
+ await expect(
+ page.getByTestId(`relative-${navigation}-a-header`),
+ ).toBeInViewport()
+
+ await relativeRouteB.click()
+
+ await page.waitForURL(
+ `http://localhost:${PORT}/relative/${navigation}/relative-${navigation}-b`,
+ )
+
+ await expect(
+ page.getByTestId(`relative-${navigation}-header`),
+ ).toBeInViewport()
+
+ await expect(
+ page.getByTestId(`relative-${navigation}-b-header`),
+ ).toBeInViewport()
+
+ await indexLink.click()
+
+ await page.waitForURL(`http://localhost:${PORT}/relative/${navigation}`)
+
+ await expect(
+ page.getByTestId(`relative-${navigation}-header`),
+ ).toBeInViewport()
+
+ await expect(
+ page.getByTestId(`relative-${navigation}-b-header`),
+ ).not.toBeInViewport()
+
+ await backLink.click()
+
+ await page.waitForURL(`http://localhost:${PORT}/relative`)
+
+ await expect(page.getByTestId(`relative-routing-home`)).toBeInViewport()
+ })
+
+ test(`nested chilren. navigation: ${navigation}`, async ({ page }) => {
+ await page.waitForLoadState('networkidle')
+ await page.goto(`/relative/${navigation}`)
+ await page.waitForURL(`http://localhost:${PORT}/relative/${navigation}`)
+
+ await expect(
+ page.getByTestId(`relative-${navigation}-header`),
+ ).toBeInViewport()
+
+ const backLink = page.getByTestId(`relative-${navigation}-back`)
+
+ const deeplyNestedChildRoute = page.getByTestId(
+ `relative-${navigation}-deeply-nested`,
+ )
+
+ await deeplyNestedChildRoute.click()
+
+ await page.waitForURL(
+ `http://localhost:${PORT}/relative/${navigation}/nested/deep`,
+ )
+
+ await expect(
+ page.getByTestId(`relative-${navigation}-nested-deep-header`),
+ ).toBeInViewport()
+
+ await backLink.click()
+
+ await page.waitForURL(
+ `http://localhost:${PORT}/relative/${navigation}/nested`,
+ )
+
+ await expect(
+ page.getByTestId(`relative-${navigation}-nested-header`),
+ ).toBeInViewport()
+ })
+
+ test(`with path params. navigation: ${navigation}`, async ({ page }) => {
+ await page.waitForLoadState('networkidle')
+ await page.goto(`/relative/${navigation}`)
+ await page.waitForURL(`http://localhost:${PORT}/relative/${navigation}`)
+
+ await expect(
+ page.getByTestId(`relative-${navigation}-header`),
+ ).toBeInViewport()
+
+ const pathParamRoute = page.getByTestId(`relative-${navigation}-path`)
+
+ await pathParamRoute.click()
+
+ await page.waitForURL(
+ `http://localhost:${PORT}/relative/${navigation}/path/a`,
+ )
+
+ expect(page.url().endsWith('/path/a')).toBe(true)
+
+ await expect(
+ page.getByTestId(`relative-${navigation}-path-param-header`),
+ ).toBeInViewport()
+
+ const switchParamLink = page.getByTestId(
+ `relative-${navigation}-path-param-switchAB`,
+ )
+
+ await switchParamLink.click()
+
+ await page.waitForURL(
+ `http://localhost:${PORT}/relative/${navigation}/path/b`,
+ )
+
+ expect(page.url().endsWith('/path/b')).toBe(true)
+
+ await expect(
+ page.getByTestId(`relative-${navigation}-path-param-header`),
+ ).toBeInViewport()
+ })
+
+ test(`with search params. navigation: ${navigation}`, async ({ page }) => {
+ await page.waitForLoadState('networkidle')
+ await page.goto(`/relative/${navigation}`)
+ await page.waitForURL(`http://localhost:${PORT}/relative/${navigation}`)
+
+ await expect(
+ page.getByTestId(`relative-${navigation}-header`),
+ ).toBeInViewport()
+
+ const searchParamRoute = page.getByTestId(
+ `relative-${navigation}-withSearch`,
+ )
+
+ await searchParamRoute.click()
+
+ let expectedUrl = new URL(
+ `http://localhost:${PORT}/relative/${navigation}/with-search?searchParam="1"`,
+ )
+
+ await page.waitForLoadState('domcontentloaded')
+
+ expect(page.url().toString()).toBe(expectedUrl.toString())
+
+ await expect(
+ page.getByTestId(`relative-${navigation}-withSearch-header`),
+ ).toBeInViewport()
+
+ await expect(
+ page.getByTestId(`relative-${navigation}-withSearch-header`),
+ ).toContainText('searchParam: 1')
+
+ const updateSearchLink = page.getByTestId(
+ `relative-${navigation}-withSearch-update-param`,
+ )
+
+ await updateSearchLink.click()
+
+ await page.waitForLoadState('domcontentloaded')
+
+ expectedUrl = new URL(
+ `http://localhost:${PORT}/relative/${navigation}/with-search?searchParam="2"`,
+ )
+
+ expect(page.url().toString()).toBe(expectedUrl.toString())
+
+ await expect(
+ page.getByTestId(`relative-${navigation}-withSearch-header`),
+ ).toContainText('searchParam: 2')
+
+ await expect(
+ page.getByTestId(`relative-${navigation}-withSearch-header`),
+ ).toBeInViewport()
+ })
+
+ test(`shouldn't cause excessive rendering. navigation: ${navigation}`, async ({
+ page,
+ }) => {
+ let navigateMsgs = 0
+
+ page.on('console', (msg) => {
+ if (msg.text() === 'navigate') {
+ navigateMsgs++
+ }
+ })
+
+ await page.waitForLoadState('networkidle')
+ await page.goto(`/relative/${navigation}`)
+ await page.waitForURL(`http://localhost:${PORT}/relative/${navigation}`)
+
+ await expect(
+ page.getByTestId(`relative-${navigation}-header`),
+ ).toBeInViewport()
+
+ expect(navigateMsgs).toBe(1)
+ const indexLink = page.getByTestId(`relative-${navigation}-index`)
+ const backLink = page.getByTestId(`relative-${navigation}-back`)
+ const relativeRouteA = page.getByTestId(`relative-${navigation}-a`)
+ const relativeRouteB = page.getByTestId(`relative-${navigation}-b`)
+ const deeplyNestedChildRoute = page.getByTestId(
+ `relative-${navigation}-deeply-nested`,
+ )
+ const pathParamRoute = page.getByTestId(`relative-${navigation}-path`)
+ const searchParamRoute = page.getByTestId(
+ `relative-${navigation}-withSearch`,
+ )
+
+ await relativeRouteA.click()
+ await page.waitForLoadState('domcontentloaded')
+ await relativeRouteB.click()
+ await page.waitForLoadState('domcontentloaded')
+ await deeplyNestedChildRoute.click()
+ await page.waitForLoadState('domcontentloaded')
+ await backLink.click()
+ await page.waitForLoadState('domcontentloaded')
+ await pathParamRoute.click()
+ await page.waitForLoadState('domcontentloaded')
+ const switchParamLink = page.getByTestId(
+ `relative-${navigation}-path-param-switchAB`,
+ )
+ await switchParamLink.click()
+ await page.waitForLoadState('domcontentloaded')
+ await searchParamRoute.click()
+ await page.waitForLoadState('domcontentloaded')
+
+ const updateSearchLink = page.getByTestId(
+ `relative-${navigation}-withSearch-update-param`,
+ )
+
+ await updateSearchLink.click()
+ await page.waitForLoadState('domcontentloaded')
+
+ await indexLink.click()
+ await page.waitForLoadState('domcontentloaded')
+
+ expect(navigateMsgs).toBe(1)
+ })
+ })
+})
diff --git a/packages/react-router/src/link.tsx b/packages/react-router/src/link.tsx
index 6fea974ffe..b64b47f129 100644
--- a/packages/react-router/src/link.tsx
+++ b/packages/react-router/src/link.tsx
@@ -7,7 +7,6 @@ import {
preloadWarning,
removeTrailingSlash,
} from '@tanstack/router-core'
-import { useActiveLocation } from './useActiveLocation'
import { useRouterState } from './useRouterState'
import { useRouter } from './useRouter'
@@ -99,15 +98,7 @@ export function useLinkProps<
structuralSharing: true as any,
})
- // subscribe to location here to re-build fromPath if it changes
- const routerLocation = useRouterState({
- select: (s) => s.location,
- structuralSharing: true as any,
- })
-
- const { getFromPath } = useActiveLocation()
-
- const from = getFromPath(options.from)
+ const from = options.from
const _options = React.useMemo(
() => {
@@ -116,7 +107,6 @@ export function useLinkProps<
// eslint-disable-next-line react-hooks/exhaustive-deps
[
router,
- routerLocation,
currentSearch,
from,
options._fromLocation,
diff --git a/packages/react-router/src/useActiveLocation.ts b/packages/react-router/src/useActiveLocation.ts
deleted file mode 100644
index c7220fdaca..0000000000
--- a/packages/react-router/src/useActiveLocation.ts
+++ /dev/null
@@ -1,57 +0,0 @@
-import { last } from '@tanstack/router-core'
-import { useCallback, useEffect, useState } from 'react'
-import { useRouter } from './useRouter'
-import { useMatch } from './useMatch'
-import { useRouterState } from './useRouterState'
-import type { ParsedLocation } from '@tanstack/router-core'
-
-export type UseActiveLocationResult = {
- activeLocation: ParsedLocation
- getFromPath: (from?: string) => string
- setActiveLocation: (location?: ParsedLocation) => void
-}
-
-export const useActiveLocation = (
- location?: ParsedLocation,
-): UseActiveLocationResult => {
- const router = useRouter()
- const routerLocation = useRouterState({ select: (state) => state.location })
- const [activeLocation, setActiveLocation] = useState(
- location ?? routerLocation,
- )
- const [customActiveLocation, setCustomActiveLocation] = useState<
- ParsedLocation | undefined
- >(location)
-
- useEffect(() => {
- setActiveLocation(customActiveLocation ?? routerLocation)
- }, [routerLocation, customActiveLocation])
-
- const matchIndex = useMatch({
- strict: false,
- select: (match) => match.index,
- })
-
- const getFromPath = useCallback(
- (from?: string) => {
- const activeLocationMatches = router.matchRoutes(activeLocation, {
- _buildLocation: false,
- })
-
- const activeLocationMatch = last(activeLocationMatches)
-
- return (
- from ??
- activeLocationMatch?.fullPath ??
- router.state.matches[matchIndex]!.fullPath
- )
- },
- [activeLocation, matchIndex, router],
- )
-
- return {
- activeLocation,
- getFromPath,
- setActiveLocation: setCustomActiveLocation,
- }
-}
diff --git a/packages/react-router/src/useNavigate.tsx b/packages/react-router/src/useNavigate.tsx
index c12cffb9c9..2671aa7e4e 100644
--- a/packages/react-router/src/useNavigate.tsx
+++ b/packages/react-router/src/useNavigate.tsx
@@ -1,6 +1,5 @@
import * as React from 'react'
import { useRouter } from './useRouter'
-import { useActiveLocation } from './useActiveLocation'
import type {
AnyRouter,
FromPathOption,
@@ -17,19 +16,14 @@ export function useNavigate<
}): UseNavigateResult {
const router = useRouter()
- const { getFromPath, activeLocation } = useActiveLocation()
-
return React.useCallback(
(options: NavigateOptions) => {
- const from = getFromPath(options.from ?? _defaultOpts?.from)
-
return router.navigate({
...options,
- from,
+ from: options.from ?? _defaultOpts?.from,
})
},
- // eslint-disable-next-line react-hooks/exhaustive-deps
- [_defaultOpts?.from, router, getFromPath, activeLocation],
+ [_defaultOpts?.from, router],
) as UseNavigateResult
}
diff --git a/packages/solid-router/src/link.tsx b/packages/solid-router/src/link.tsx
index 00c0c10997..3029c6020d 100644
--- a/packages/solid-router/src/link.tsx
+++ b/packages/solid-router/src/link.tsx
@@ -15,7 +15,6 @@ import { useRouter } from './useRouter'
import { useIntersectionObserver } from './utils'
-import { useActiveLocation } from './useActiveLocation'
import type {
AnyRouter,
Constrain,
@@ -133,20 +132,17 @@ export function useLinkProps<
select: (s) => s.location.searchStr,
})
- const { getFromPath, activeLocation } = useActiveLocation()
-
- const from = getFromPath(options.from)
+ const from = options.from
const _options = () => {
return {
...options,
- from: from(),
+ from,
}
}
const next = Solid.createMemo(() => {
currentSearch()
- activeLocation()
return router.buildLocation(_options() as any)
})
diff --git a/packages/solid-router/src/useActiveLocation.ts b/packages/solid-router/src/useActiveLocation.ts
deleted file mode 100644
index 268af7296d..0000000000
--- a/packages/solid-router/src/useActiveLocation.ts
+++ /dev/null
@@ -1,61 +0,0 @@
-import { last } from '@tanstack/router-core'
-import { createEffect, createMemo, createSignal } from 'solid-js'
-import { useMatch } from './useMatch'
-import { useRouter } from './useRouter'
-import { useRouterState } from './useRouterState'
-import type { Accessor } from 'solid-js'
-import type { ParsedLocation } from '@tanstack/router-core'
-
-export type UseLocationResult = {
- activeLocation: Accessor
- getFromPath: (from?: string) => Accessor
- setActiveLocation: (location?: ParsedLocation) => void
-}
-
-export function useActiveLocation(
- location?: ParsedLocation,
-): UseLocationResult {
- const router = useRouter()
- // we are not using a variable here for router state location since we need to only calculate that if the location is not passed in. It can result in unnecessary history actions if we do that.
- const [activeLocation, setActiveLocation] = createSignal(
- location ?? useRouterState({ select: (s) => s.location })(),
- )
- const [customActiveLocation, setCustomActiveLocation] = createSignal<
- ParsedLocation | undefined
- >(location)
-
- createEffect(() => {
- setActiveLocation(
- customActiveLocation() ?? useRouterState({ select: (s) => s.location })(),
- )
- })
-
- const matchIndex = useMatch({
- strict: false,
- select: (match) => match.index,
- })
-
- const getFromPath = (from?: string) =>
- createMemo(() => {
- const activeLocationMatches = router.matchRoutes(
- customActiveLocation() ?? activeLocation(),
- {
- _buildLocation: false,
- },
- )
-
- const activeLocationMatch = last(activeLocationMatches)
-
- return (
- from ??
- activeLocationMatch?.fullPath ??
- router.state.matches[matchIndex()]!.fullPath
- )
- })
-
- return {
- activeLocation,
- getFromPath,
- setActiveLocation: setCustomActiveLocation,
- }
-}
diff --git a/packages/solid-router/src/useNavigate.tsx b/packages/solid-router/src/useNavigate.tsx
index 0a7f743753..40e51ced6b 100644
--- a/packages/solid-router/src/useNavigate.tsx
+++ b/packages/solid-router/src/useNavigate.tsx
@@ -1,6 +1,5 @@
import * as Solid from 'solid-js'
import { useRouter } from './useRouter'
-import { useActiveLocation } from './useActiveLocation'
import type {
AnyRouter,
FromPathOption,
@@ -17,17 +16,10 @@ export function useNavigate<
}): UseNavigateResult {
const router = useRouter()
- const { getFromPath, setActiveLocation } = useActiveLocation(
- router.latestLocation,
- )
-
return ((options: NavigateOptions) => {
- setActiveLocation(router.latestLocation)
- const from = getFromPath(options.from ?? _defaultOpts?.from)
-
return router.navigate({
...options,
- from: from(),
+ from: options.from ?? _defaultOpts?.from,
})
}) as UseNavigateResult
}