8000 chore: enforce correct template page routes · coder/coder@4b9d029 · GitHub
[go: up one dir, main page]

Skip to content

Commit 4b9d029

Browse files
committed
chore: enforce correct template page routes
1 parent 54901e3 commit 4b9d029

File tree

2 files changed

+75
-19
lines changed

2 files changed

+75
-19
lines changed
Lines changed: 53 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,53 @@
1+
import type { FC } from "react";
2+
import { Navigate, Outlet, useLocation, useParams } from "react-router-dom";
3+
import type { Organization } from "api/typesGenerated";
4+
import { useDashboard } from "modules/dashboard/useDashboard";
5+
6+
export const TemplateRedirectController: FC = () => {
7+
const { organizations, showOrganizations } = useDashboard();
8+
const { organization, template } = useParams() as {
9+
organization?: string;
10+
template: string;
11+
};
12+
const location = useLocation();
13+
14+
// We redirect templates without an organization to the default organization,
15+
// as that's likely what any links floating around expect.
16+
if (showOrganizations && !organization) {
17+
const extraPath = removePrefix(location.pathname, `/templates/${template}`);
18+
19+
return (
20+
<Navigate
21+
to={`/templates/${getOrganizationNameByDefault(
22+
organizations,
23+
)}/${template}${extraPath}${location.search}`}
24+
replace
25+
/>
26+
);
27+
}
28+
29+
// `showOrganizations` can only be false when there is a single organization,
30+
// so it's safe to throw away the organization name.
31+
if (!showOrganizations && organization) {
32+
const extraPath = removePrefix(
33+
location.pathname,
34+
`/templates/${organization}/${template}`,
35+
);
36+
37+
return (
38+
<Navigate
39+
to={`/templates/${template}${extraPath}${location.search}`}
40+
replace
41+
/>
42+
);
43+
}
44+
45+
return <Outlet />;
46+
};
47+
48+
const getOrganizationNameByDefault = (organizations: Organization[]) =>
49+
organizations.find((org) => org.is_default)?.name;
50+
51+
// I really hate doing it this way, but React Router does not provide a better way.
52+
const removePrefix = (self: string, prefix: string) =>
53+
self.startsWith(prefix) ? self.slice(prefix.length) : self;

site/src/router.tsx

Lines changed: 22 additions & 19 deletions
Original file line numberDiff line numberDiff line change
@@ -1,4 +1,4 @@
1-
import { Suspense, lazy } from "react";
1+
import { lazy, Suspense } from "react";
22
import {
33
createBrowserRouter,
44
createRoutesFromChildren,
@@ -23,6 +23,7 @@ import { UsersLayout } from "./pages/UsersPage/UsersLayout";
2323
import UsersPage from "./pages/UsersPage/UsersPage";
2424
import { WorkspaceSettingsLayout } from "./pages/WorkspaceSettingsPage/WorkspaceSettingsLayout";
2525
import WorkspacesPage from "./pages/WorkspacesPage/WorkspacesPage";
26+
import { TemplateRedirectController } from "pages/TemplatePage/TemplateRedirectController";
2627

2728
// Lazy load pages
2829
// - Pages that are secondary, not in the main navigation or not usually accessed
@@ -282,27 +283,29 @@ const RoutesWithSuspense = () => {
282283
const templateRouter = () => {
283284
return (
284285
<Route path=":template">
285-
<Route element={<TemplateLayout />}>
286-
<Route index element={<TemplateSummaryPage />} />
287-
<Route path="docs" element={<TemplateDocsPage />} />
288-
<Route path="files" element={<TemplateFilesPage />} />
289-
<Route path="versions" element={<TemplateVersionsPage />} />
290-
<Route path="embed" element={<TemplateEmbedPage />} />
291-
<Route path="insights" element={<TemplateInsightsPage />} />
292-
</Route>
286+
<Route element={<TemplateRedirectController />}>
287+
<Route element={<TemplateLayout />}>
288+
<Route index element={<TemplateSummaryPage />} />
289+
<Route path="docs" element={<TemplateDocsPage />} />
290+
<Route path="files" element={<TemplateFilesPage />} />
291+
<Route path="versions" element={<TemplateVersionsPage />} />
292+
<Route path="embed" element={<TemplateEmbedPage />} />
293+
<Route path="insights" element={<TemplateInsightsPage />} />
294+
</Route>
293295

294-
<Route path="workspace" element={<CreateWorkspacePage />} />
296+
<Route path="workspace" element={<CreateWorkspacePage />} />
295297

296-
<Route path="settings" element={<TemplateSettingsLayout />}>
297-
<Route index element={<TemplateSettingsPage />} />
298-
<Route path="permissions" element={<TemplatePermissionsPage />} />
299-
<Route path="variables" element={<TemplateVariablesPage />} />
300-
<Route path="schedule" element={<TemplateSchedulePage />} />
301-
</Route>
298+
<Route path="settings" element={<TemplateSettingsLayout />}>
299+
<Route index element={<TemplateSettingsPage />} />
300+
<Route path="permissions" element={<TemplatePermissionsPage />} />
301+
<Route path="variables" element={<TemplateVariablesPage />} />
302+
<Route path="schedule" element={<TemplateSchedulePage />} />
303+
</Route>
302304

303-
<Route path="versions">
304-
<Route path=":version">
305-
<Route index element={<TemplateVersionPage />} />
305+
<Route path="versions">
306+
<Route path=":version">
307+
<Route index element={<TemplateVersionPage />} />
308+
</Route>
306309
</Route>
307310
</Route>
308311
</Route>

0 commit comments

Comments
 (0)
0