TanStack Router 的“强”不只是文件路由,而是整个 route tree 被 TypeScript 认识。
Next.js 的文件系统本身就是框架入口;TanStack Router 的文件路由会生成 route tree,但你仍然显式创建 router、传 context、挂 provider。文件只是生成配置的方式,不是上帝。
// main.tsx
const router = createRouter({
routeTree,
context: { queryClient },
})
ReactDOM.createRoot(root).render(
<RouterProvider router={router} />
)// src/routes/posts.$postId.tsx
export const Route = createFileRoute('/posts/$postId')({
loader: ({ params }) => fetchPost(params.postId),
component: PostPage,
})
function PostPage() {
const post = Route.useLoaderData()
return <article>{post.title}</article>
}TanStack 的 Link 知道哪些 route 存在、需要哪些 params/search。路径拼错不是运行时 404,而是编译期噪音。编译器偶尔像一个烦人的同事,但这次它是对的。
<Link to="/posts/$postId" params={{ postId: post.id }}>
Open
</Link>
// 如果漏掉 postId,或者写成 /post/$id,TypeScript 应该抱怨。TanStack 支持 nested routes、layout routes 和 pathless layouts。和 Next 的 layout.tsx 类似,但 route context、beforeLoad、loader 都可以参与父子继承。
| 概念 | TanStack 意义 | Next.js 对照 |
|---|---|---|
| Nested route | 父子路由匹配与 Outlet | 嵌套路由 segment |
| Pathless layout | 不增加 URL 段,只共享布局/逻辑 | route group / layout 近似 |
| Route context | 父路由向子路由传 typed context | layout/provider,但更路由生命周期化 |
/dashboard 需要 auth,所有子页面都需要 user 和 permissions。TanStack 中你应把 auth 检查放在父 route 的 beforeLoad,而不是每个页面复制。复制粘贴是弱智版继承。TanStack 文件路由生成 route tree 后,开发者是否还完全失去控制?