Skip to content

Commit 3d8fb97

Browse files
committed
fix: statically load library landing pages
Move library landing pages to per-library route modules so the matched page ships with the initial route payload. This avoids the hard-refresh hydration flash without bundling every landing page together.
1 parent a7589c7 commit 3d8fb97

22 files changed

+696
-100
lines changed

src/components/DocsLayout.tsx

Lines changed: 4 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -521,6 +521,7 @@ const useMenuConfig = ({
521521
}
522522

523523
type DocsLayoutProps = {
524+
libraryId: LibraryId
524525
name: string
525526
version: string
526527
colorFrom: string
@@ -535,6 +536,7 @@ type DocsLayoutProps = {
535536
}
536537

537538
export function DocsLayout({
539+
libraryId,
538540
colorFrom,
539541
colorTo,
540542
textColor,
@@ -544,9 +546,9 @@ export function DocsLayout({
544546
children,
545547
isLandingPage = false,
546548
}: DocsLayoutProps) {
547-
const { libraryId, version } = useParams({
549+
const { version } = useParams({
548550
strict: false,
549-
}) as { libraryId: LibraryId; version: string }
551+
}) as { version: string }
550552
const { _splat } = useParams({ strict: false })
551553
const menuConfig = useMenuConfig({ config, frameworks, repo, libraryId })
552554

src/routeTree.gen.ts

Lines changed: 336 additions & 0 deletions
Large diffs are not rendered by default.

src/routes/$libraryId/$version.docs.tsx

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -52,6 +52,7 @@ function DocsRoute() {
5252

5353
return (
5454
<DocsLayout
55+
libraryId={libraryId}
5556
name={library.name.replace('TanStack ', '')}
5657
version={version === 'latest' ? library.latestVersion : version!}
5758
colorFrom={library.accentColorFrom ?? library.colorFrom}

src/routes/$libraryId/$version.index.tsx

Lines changed: 14 additions & 21 deletions
Original file line numberDiff line numberDiff line change
@@ -6,11 +6,9 @@ import {
66
} from '@tanstack/react-router'
77
import { DocsLayout } from '~/components/DocsLayout'
88
import { findLibrary } from '~/libraries'
9-
import type { LibraryId } from '~/libraries'
109
import { seo } from '~/utils/seo'
1110

1211
import { Button } from '~/ui'
13-
import { landingComponents } from './$version'
1412

1513
const versionRouteApi = getRouteApi('/$libraryId/$version')
1614

@@ -38,7 +36,7 @@ export const Route = createFileRoute('/$libraryId/$version/')({
3836
function LibraryVersionIndex() {
3937
const { libraryId, version } = Route.useParams()
4038
const library = findLibrary(libraryId)
41-
const { config, landingCodeExampleRsc } = versionRouteApi.useLoaderData()
39+
const { config } = versionRouteApi.useLoaderData()
4240

4341
if (!library) {
4442
throw notFound()
@@ -48,10 +46,9 @@ function LibraryVersionIndex() {
4846
throw notFound()
4947
}
5048

51-
const LandingComponent = landingComponents[libraryId as LibraryId]
52-
5349
return (
5450
<DocsLayout
51+
libraryId={libraryId}
5552
name={library.name.replace('TanStack ', '')}
5653
version={version === 'latest' ? library.latestVersion : version!}
5754
colorFrom={library.accentColorFrom ?? library.colorFrom}
@@ -63,23 +60,19 @@ function LibraryVersionIndex() {
6360
repo={library.repo}
6461
isLandingPage
6562
>
66-
{LandingComponent ? (
67-
<LandingComponent landingCodeExampleRsc={landingCodeExampleRsc} />
68-
) : (
69-
<div className="px-4 pt-32 pb-24">
70-
<div className="flex flex-col items-center justify-center min-h-[50vh] gap-4 max-w-3xl mx-auto text-center">
71-
<h1 className="text-2xl font-bold">{library.name}</h1>
72-
<p className="text-gray-600">{library.description}</p>
73-
<Button
74-
as={Link}
75-
to="/$libraryId/$version/docs"
76-
params={{ libraryId, version } as never}
77-
>
78-
View Documentation
79-
</Button>
80-
</div>
63+
<div className="px-4 pt-32 pb-24">
64+
<div className="flex flex-col items-center justify-center min-h-[50vh] gap-4 max-w-3xl mx-auto text-center">
65+
<h1 className="text-2xl font-bold">{library.name}</h1>
66+
<p className="text-gray-600">{library.description}</p>
67+
<Button
68+
as={Link}
69+
to="/$libraryId/$version/docs"
70+
params={{ libraryId, version } as never}
71+
>
72+
View Documentation
73+
</Button>
8174
</div>
82-
)}
75+
</div>
8376
</DocsLayout>
8477
)
8578
}

src/routes/$libraryId/$version.tsx

Lines changed: 7 additions & 77 deletions
Original file line numberDiff line numberDiff line change
@@ -3,76 +3,24 @@ import {
33
redirect,
44
notFound,
55
createFileRoute,
6-
lazyRouteComponent,
76
} from '@tanstack/react-router'
8-
import type { AsyncRouteComponent } from '@tanstack/react-router'
9-
import type { ReactNode } from 'react'
107
import { RedirectVersionBanner } from '~/components/RedirectVersionBanner'
11-
import { findLibrary, getBranch } from '~/libraries'
12-
import type { LibraryId } from '~/libraries'
13-
import { getTanstackDocsConfig } from '~/utils/config'
14-
import { fetchLandingCodeExample } from '~/utils/landing-code-example.functions'
8+
import { findLibrary } from '~/libraries'
9+
import { loadLibraryConfig, validateLibraryVersion } from '../-library-landing'
1510

16-
export type LandingComponentProps = {
17-
landingCodeExampleRsc?: ReactNode
18-
}
19-
20-
export const landingComponents: Partial<
21-
Record<LibraryId, AsyncRouteComponent<LandingComponentProps>>
22-
> = {
23-
query: lazyRouteComponent(() => import('~/components/landing/QueryLanding')),
24-
router: lazyRouteComponent(
25-
() => import('~/components/landing/RouterLanding'),
26-
),
27-
table: lazyRouteComponent(() => import('~/components/landing/TableLanding')),
28-
form: lazyRouteComponent(() => import('~/components/landing/FormLanding')),
29-
start: lazyRouteComponent(() => import('~/components/landing/StartLanding')),
30-
store: lazyRouteComponent(() => import('~/components/landing/StoreLanding')),
31-
virtual: lazyRouteComponent(
32-
() => import('~/components/landing/VirtualLanding'),
33-
),
34-
ranger: lazyRouteComponent(
35-
() => import('~/components/landing/RangerLanding'),
36-
),
37-
pacer: lazyRouteComponent(() => import('~/components/landing/PacerLanding')),
38-
hotkeys: lazyRouteComponent(
39-
() => import('~/components/landing/HotkeysLanding'),
40-
),
41-
config: lazyRouteComponent(
42-
() => import('~/components/landing/ConfigLanding'),
43-
),
44-
db: lazyRouteComponent(() => import('~/components/landing/DbLanding')),
45-
ai: lazyRouteComponent(() => import('~/components/landing/AiLanding')),
46-
devtools: lazyRouteComponent(
47-
() => import('~/components/landing/DevtoolsLanding'),
48-
),
49-
cli: lazyRouteComponent(() => import('~/components/landing/CliLanding')),
50-
intent: lazyRouteComponent(
51-
() => import('~/components/landing/IntentLanding'),
52-
),
53-
}
11+
export type { LandingComponentProps } from '../-library-landing'
5412

5513
export const Route = createFileRoute('/$libraryId/$version')({
5614
staleTime: 1000 * 60 * 5,
5715
beforeLoad: async (ctx) => {
5816
const { libraryId, version } = ctx.params
59-
const library = findLibrary(libraryId)
60-
61-
if (!library) {
62-
throw notFound()
63-
}
64-
65-
library.handleRedirects?.(ctx.location.href)
66-
67-
if (!library.availableVersions.concat('latest').includes(version!)) {
17+
const library = validateLibraryVersion(libraryId, version, () => {
6818
throw redirect({
6919
params: { libraryId, version: 'latest' } as never,
7020
})
71-
}
21+
})
7222

73-
if (!ctx.location.pathname.includes('/docs')) {
74-
await landingComponents[libraryId as LibraryId]?.preload?.()
75-
}
23+
library.handleRedirects?.(ctx.location.href)
7624
},
7725
loader: async (ctx) => {
7826
const { libraryId, version } = ctx.params
@@ -82,26 +30,8 @@ export const Route = createFileRoute('/$libraryId/$version')({
8230
throw notFound()
8331
}
8432

85-
const branch = getBranch(library, version)
86-
const config = await getTanstackDocsConfig({
87-
data: {
88-
repo: library.repo,
89-
branch,
90-
docsRoot: library.docsRoot || 'docs',
91-
},
92-
})
93-
94-
const landingCodeExample = ctx.location.pathname.includes('/docs')
95-
? null
96-
: await fetchLandingCodeExample({
97-
data: {
98-
libraryId,
99-
},
100-
})
101-
10233
return {
103-
config,
104-
landingCodeExampleRsc: landingCodeExample?.contentRsc ?? null,
34+
config: await loadLibraryConfig(library.id, version!),
10535
}
10636
},
10737
component: RouteForm,

0 commit comments

Comments
 (0)