Skip to content

Commit 9ce7044

Browse files
committed
Restructure docs routes and add metadata helper
Move docs routing from a single [...slug] handler to explicit [plugin]/[version]/[...slug], plus lightweight [plugin]/[version] and [plugin] pages that redirect to overview and provide static params. Add a shared metadata helper (app/docs/components/helpers.ts) and an index export for docs components. Update page logic to build params from plugin/version/slug, use generateMetadataForPlugin, and adjust imports. Add a workflow step to verify the ./out directory before uploading the Pages artifact and add debug logging to next.config.mjs.
1 parent ffc4e81 commit 9ce7044

File tree

7 files changed

+134
-33
lines changed

7 files changed

+134
-33
lines changed

.github/workflows/deploy.yml

Lines changed: 7 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -45,6 +45,13 @@ jobs:
4545
NEXT_STATIC_EXPORT: "true"
4646
NODE_ENV: "production"
4747

48+
- name: Verify output directory
49+
run: |
50+
if [ ! -d "./out" ]; then
51+
echo "Error: Output directory './out' does not exist."
52+
exit 1
53+
fi
54+
4855
- name: Upload artifact
4956
uses: actions/upload-pages-artifact@v3
5057
with:

app/docs/[...slug]/page.tsx renamed to app/docs/[plugin]/[version]/[...slug]/page.tsx

Lines changed: 36 additions & 33 deletions
Original file line numberDiff line numberDiff line change
@@ -5,31 +5,22 @@ import { getMDXComponents } from '@/mdx-components';
55
import type { Metadata } from 'next';
66
import { createCustomRelativeLink } from '@/lib/mdx-link';
77
import Link from 'next/link';
8-
import { ViewOptions } from '../components/page-actions';
8+
import { ViewOptions, generateMetadataForPlugin } from '@/app/docs/components';
99

10-
export default async function Page(props: PageProps<'/docs/[...slug]'>) {
10+
type CurrentPageProps = PageProps<'/docs/[plugin]/[version]/[...slug]'>;
11+
12+
export default async function Page(props: CurrentPageProps) {
1113
const params = await props.params;
14+
const pluginName = params.plugin;
15+
const version = params.version;
1216
const slugs = params.slug || [];
13-
const pluginName = slugs[0];
14-
const version = slugs[1] ?? null;
15-
const restSlugs = version ? slugs.slice(2) : slugs.slice(1);
16-
17-
// If version is not specified, try redirect to latest version
18-
if (!version) {
19-
const latestVersion = getLatestVersion(pluginName);
20-
if (!latestVersion) {
21-
// Plugin doesn't exist, show 404
22-
return notFound();
23-
}
24-
return redirect(`/docs/${[pluginName, latestVersion].join('/')}`);
25-
}
2617

2718
// If missing which page to load, default to 'overview'
28-
if (restSlugs.length === 0) {
19+
if (slugs.length === 0) {
2920
return redirect(`/docs/${[pluginName, version, 'overview'].join('/')}`);
3021
}
3122

32-
const finalSlugs = [pluginName, version, ...restSlugs];
23+
const finalSlugs = [pluginName, version, ...slugs];
3324
const page = source.getPage(finalSlugs);
3425

3526
// console.debug('Resolved final slugs for page:', finalSlugs, { pageExists: !!page });
@@ -72,24 +63,36 @@ export default async function Page(props: PageProps<'/docs/[...slug]'>) {
7263
}
7364

7465
export async function generateStaticParams() {
75-
return source.generateParams();
66+
const slugs = source.generateParams();
67+
const params: { plugin: string, version: string, slug: string[] }[] = [];
68+
69+
Array.from(slugs).forEach((array) => {
70+
const slugArray = array['slug'];
71+
const plugin = slugArray[0];
72+
const version = slugArray[1];
73+
const rest = slugArray.slice(2);
74+
params.push({ plugin, version, slug: rest });
75+
});
76+
77+
return params;
7678
}
7779

78-
export async function generateMetadata(props: PageProps<'/docs/[...slug]'>): Promise<Metadata> {
80+
export async function generateMetadata(props: CurrentPageProps): Promise<Metadata> {
7981
const params = await props.params;
80-
const slugs = params.slug || [];
81-
const pluginName = slugs[0];
82-
const page = source.getPage(slugs);
83-
if (!page) notFound();
82+
const pluginName = params.plugin;
83+
84+
return generateMetadataForPlugin(pluginName) ?? notFound();
85+
// const page = source.getPage([pluginName, version, ...slugs]);
86+
// if (!page) notFound();
8487

85-
return {
86-
title: page.data.title,
87-
description: page.data.description,
88-
openGraph: {
89-
images: [
90-
getPluginImage(pluginName).url,
91-
// getPageImage(page).url,
92-
],
93-
},
94-
};
88+
// return {
89+
// title: page.data.title,
90+
// description: page.data.description,
91+
// openGraph: {
92+
// images: [
93+
// getPluginImage(pluginName).url,
94+
// // getPageImage(page).url,
95+
// ],
96+
// },
97+
// };
9598
}
Lines changed: 33 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,33 @@
1+
import { notFound, redirect } from 'next/navigation';
2+
import type { Metadata } from 'next';
3+
import { config } from '@/lib/config';
4+
import { generateMetadataForPlugin } from '@/app/docs/components';
5+
6+
type CurrentPageProps = PageProps<'/docs/[plugin]/[version]'>;
7+
8+
export default async function Page(props: CurrentPageProps) {
9+
const params = await props.params;
10+
const pluginName = params.plugin;
11+
const version = params.version;
12+
13+
return redirect(`/docs/${[pluginName, version, 'overview'].join('/')}`);
14+
}
15+
16+
export async function generateStaticParams() {
17+
const params: { plugin: string, version: string }[] = [];
18+
19+
for (const plugin of config.plugins) {
20+
for (const version of plugin.versions) {
21+
params.push({ plugin: plugin.id, version: version.version });
22+
}
23+
}
24+
25+
return params;
26+
}
27+
28+
export async function generateMetadata(props: CurrentPageProps): Promise<Metadata> {
29+
30+
const params = await props.params;
31+
const pluginName = params.plugin;
32+
return generateMetadataForPlugin(pluginName) ?? notFound();
33+
}

app/docs/[plugin]/page.tsx

Lines changed: 35 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,35 @@
1+
import { getLatestVersion } from '@/lib/source';
2+
import { notFound, redirect } from 'next/navigation';
3+
import type { Metadata } from 'next';
4+
import { config } from '@/lib/config';
5+
import { generateMetadataForPlugin } from '@/app/docs/components';
6+
7+
type CurrentPageProps = PageProps<'/docs/[plugin]'>;
8+
9+
export default async function Page(props: CurrentPageProps) {
10+
const params = await props.params;
11+
const pluginName = params.plugin;
12+
13+
const latestVersion = getLatestVersion(pluginName);
14+
if (!latestVersion) {
15+
return notFound();
16+
}
17+
return redirect(`/docs/${[pluginName, latestVersion].join('/')}`);
18+
}
19+
20+
export async function generateStaticParams() {
21+
const params: { plugin: string }[] = [];
22+
23+
for (const plugin of config.plugins) {
24+
params.push({ plugin: plugin.id });
25+
}
26+
27+
return params;
28+
}
29+
30+
export async function generateMetadata(props: CurrentPageProps): Promise<Metadata> {
31+
const params = await props.params;
32+
const pluginName = params.plugin;
33+
34+
return generateMetadataForPlugin(pluginName) ?? notFound();
35+
}

app/docs/components/helpers.ts

Lines changed: 17 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,17 @@
1+
import { config } from "@/lib/config";
2+
import { getPluginImage } from "@/lib/source";
3+
4+
export function generateMetadataForPlugin(plugin: string) {
5+
const pluginConfig = config.plugins.find(p => p.id === plugin);
6+
if (!pluginConfig) return null;
7+
return {
8+
title: pluginConfig.name,
9+
description: pluginConfig.description,
10+
// openGraph: {
11+
// images: [
12+
// getPluginImage(plugin).url,
13+
// // getPageImage(page).url,
14+
// ],
15+
// },
16+
};
17+
};

app/docs/components/index.ts

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,2 @@
1+
export * from './page-actions';
2+
export * from './helpers';

next.config.mjs

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -5,6 +5,10 @@ const withMDX = createMDX();
55
const isStaticExport = process.env.NEXT_STATIC_EXPORT === "true";
66
const isProd = process.env.NODE_ENV === "production";
77

8+
console.debug("Next.js Configuration:");
9+
console.debug(` isProd: ${isProd}`);
10+
console.debug(` isStaticExport: ${isStaticExport}`);
11+
812
// GitHub Pages configuration
913
const basePath =
1014
isProd && isStaticExport

0 commit comments

Comments
 (0)