feat: complete TechLog Studio publication flow
This commit is contained in:
@@ -0,0 +1,234 @@
|
||||
import {
|
||||
lazy,
|
||||
type ComponentType,
|
||||
type LazyExoticComponent,
|
||||
type ReactNode,
|
||||
} from "react";
|
||||
import { Outlet } from "react-router-dom";
|
||||
|
||||
import {
|
||||
TECH_LOG_ROUTE_RUNTIME_CONTRACT,
|
||||
type TechLogRouteId,
|
||||
} from "../contracts/tech-log-route-contract.ts";
|
||||
import { PublicShell } from "./public/public-shell.tsx";
|
||||
import { StudioShell } from "./studio/studio-shell.tsx";
|
||||
|
||||
type RouteRuntime = Readonly<{
|
||||
moduleId: string;
|
||||
Component: LazyExoticComponent<ComponentType>;
|
||||
}>;
|
||||
|
||||
function runtime(
|
||||
routeId: TechLogRouteId,
|
||||
load: () => Promise<{ default: ComponentType }>,
|
||||
): RouteRuntime {
|
||||
return Object.freeze({
|
||||
moduleId: TECH_LOG_ROUTE_RUNTIME_CONTRACT[routeId].moduleId,
|
||||
Component: lazy(load),
|
||||
});
|
||||
}
|
||||
|
||||
function routeModule<Module, Key extends keyof Module>(
|
||||
load: () => Promise<Module>,
|
||||
key: Key,
|
||||
): () => Promise<{ default: Extract<Module[Key], ComponentType> }> {
|
||||
return async () => {
|
||||
const module = await load();
|
||||
return { default: module[key] as Extract<Module[Key], ComponentType> };
|
||||
};
|
||||
}
|
||||
|
||||
export const TECH_LOG_ROUTE_RUNTIME = Object.freeze({
|
||||
TECH_LOG_HOME: runtime(
|
||||
"TECH_LOG_HOME",
|
||||
routeModule(() => import("./public/pages/home-page.tsx"), "HomePage"),
|
||||
),
|
||||
TECH_LOG_EXPLORE: runtime(
|
||||
"TECH_LOG_EXPLORE",
|
||||
routeModule(
|
||||
() => import("./public/pages/explore-page.tsx"),
|
||||
"ExplorePage",
|
||||
),
|
||||
),
|
||||
TECH_LOG_EXPLORE_KIND: runtime(
|
||||
"TECH_LOG_EXPLORE_KIND",
|
||||
routeModule(
|
||||
() => import("./public/pages/explore-kind-page.tsx"),
|
||||
"ExploreKindPage",
|
||||
),
|
||||
),
|
||||
TECH_LOG_CASE: runtime(
|
||||
"TECH_LOG_CASE",
|
||||
routeModule(() => import("./public/pages/case-page.tsx"), "CasePage"),
|
||||
),
|
||||
TECH_LOG_REFERENCE: runtime(
|
||||
"TECH_LOG_REFERENCE",
|
||||
routeModule(
|
||||
() => import("./public/pages/reference-page.tsx"),
|
||||
"ReferencePage",
|
||||
),
|
||||
),
|
||||
TECH_LOG_QUESTION: runtime(
|
||||
"TECH_LOG_QUESTION",
|
||||
routeModule(
|
||||
() => import("./public/pages/question-page.tsx"),
|
||||
"QuestionPage",
|
||||
),
|
||||
),
|
||||
TECH_LOG_TOPIC: runtime(
|
||||
"TECH_LOG_TOPIC",
|
||||
routeModule(() => import("./public/pages/topic-page.tsx"), "TopicPage"),
|
||||
),
|
||||
TECH_LOG_PROJECTS: runtime(
|
||||
"TECH_LOG_PROJECTS",
|
||||
routeModule(
|
||||
() => import("./public/pages/projects-page.tsx"),
|
||||
"ProjectsPage",
|
||||
),
|
||||
),
|
||||
TECH_LOG_PROJECT: runtime(
|
||||
"TECH_LOG_PROJECT",
|
||||
routeModule(
|
||||
() => import("./public/pages/project-overview-page.tsx"),
|
||||
"ProjectOverviewPage",
|
||||
),
|
||||
),
|
||||
TECH_LOG_PROJECT_RECORDS: runtime(
|
||||
"TECH_LOG_PROJECT_RECORDS",
|
||||
routeModule(
|
||||
() => import("./public/pages/project-records-page.tsx"),
|
||||
"ProjectRecordsPage",
|
||||
),
|
||||
),
|
||||
TECH_LOG_PROJECT_DECISIONS: runtime(
|
||||
"TECH_LOG_PROJECT_DECISIONS",
|
||||
routeModule(
|
||||
() => import("./public/pages/project-decisions-page.tsx"),
|
||||
"ProjectDecisionsPage",
|
||||
),
|
||||
),
|
||||
TECH_LOG_PROJECT_ACTIVITY: runtime(
|
||||
"TECH_LOG_PROJECT_ACTIVITY",
|
||||
routeModule(
|
||||
() => import("./public/pages/project-activity-page.tsx"),
|
||||
"ProjectActivityPage",
|
||||
),
|
||||
),
|
||||
TECH_LOG_RELEASES: runtime(
|
||||
"TECH_LOG_RELEASES",
|
||||
routeModule(
|
||||
() => import("./public/pages/releases-page.tsx"),
|
||||
"ReleasesPage",
|
||||
),
|
||||
),
|
||||
TECH_LOG_RELEASE: runtime(
|
||||
"TECH_LOG_RELEASE",
|
||||
routeModule(
|
||||
() => import("./public/pages/release-page.tsx"),
|
||||
"ReleasePage",
|
||||
),
|
||||
),
|
||||
TECH_LOG_PROFILE: runtime(
|
||||
"TECH_LOG_PROFILE",
|
||||
routeModule(
|
||||
() => import("./public/pages/profile-page.tsx"),
|
||||
"ProfilePage",
|
||||
),
|
||||
),
|
||||
TECH_LOG_SEARCH: runtime(
|
||||
"TECH_LOG_SEARCH",
|
||||
routeModule(() => import("./public/pages/search-page.tsx"), "SearchPage"),
|
||||
),
|
||||
TECH_LOG_STUDIO_HOME: runtime(
|
||||
"TECH_LOG_STUDIO_HOME",
|
||||
routeModule(
|
||||
() => import("./studio/pages/studio-home-page.tsx"),
|
||||
"StudioHomePage",
|
||||
),
|
||||
),
|
||||
TECH_LOG_STUDIO_DOCUMENTS: runtime(
|
||||
"TECH_LOG_STUDIO_DOCUMENTS",
|
||||
routeModule(
|
||||
() => import("./studio/pages/documents-page.tsx"),
|
||||
"DocumentsPage",
|
||||
),
|
||||
),
|
||||
TECH_LOG_STUDIO_DOCUMENT_NEW: runtime(
|
||||
"TECH_LOG_STUDIO_DOCUMENT_NEW",
|
||||
routeModule(
|
||||
() => import("./studio/pages/new-document-page.tsx"),
|
||||
"NewDocumentPage",
|
||||
),
|
||||
),
|
||||
TECH_LOG_STUDIO_DOCUMENT_EDIT: runtime(
|
||||
"TECH_LOG_STUDIO_DOCUMENT_EDIT",
|
||||
routeModule(
|
||||
() => import("./studio/pages/document-edit-page.tsx"),
|
||||
"DocumentEditPage",
|
||||
),
|
||||
),
|
||||
TECH_LOG_STUDIO_DOCUMENT_VALIDATION: runtime(
|
||||
"TECH_LOG_STUDIO_DOCUMENT_VALIDATION",
|
||||
routeModule(
|
||||
() => import("./studio/pages/document-validation-page.tsx"),
|
||||
"DocumentValidationPage",
|
||||
),
|
||||
),
|
||||
TECH_LOG_STUDIO_DOCUMENT_PREVIEW: runtime(
|
||||
"TECH_LOG_STUDIO_DOCUMENT_PREVIEW",
|
||||
routeModule(
|
||||
() => import("./studio/pages/document-preview-page.tsx"),
|
||||
"DocumentPreviewPage",
|
||||
),
|
||||
),
|
||||
TECH_LOG_STUDIO_DOCUMENT_PUBLISH: runtime(
|
||||
"TECH_LOG_STUDIO_DOCUMENT_PUBLISH",
|
||||
routeModule(
|
||||
() => import("./studio/pages/document-publish-page.tsx"),
|
||||
"DocumentPublishPage",
|
||||
),
|
||||
),
|
||||
TECH_LOG_STUDIO_PUBLICATIONS: runtime(
|
||||
"TECH_LOG_STUDIO_PUBLICATIONS",
|
||||
routeModule(
|
||||
() => import("./studio/pages/publications-page.tsx"),
|
||||
"PublicationsPage",
|
||||
),
|
||||
),
|
||||
TECH_LOG_STUDIO_PUBLICATION_PREVIEW: runtime(
|
||||
"TECH_LOG_STUDIO_PUBLICATION_PREVIEW",
|
||||
routeModule(
|
||||
() => import("./studio/pages/publication-preview-page.tsx"),
|
||||
"PublicationPreviewPage",
|
||||
),
|
||||
),
|
||||
TECH_LOG_STUDIO_NOT_FOUND: runtime(
|
||||
"TECH_LOG_STUDIO_NOT_FOUND",
|
||||
routeModule(
|
||||
() => import("./studio/pages/studio-not-found-page.tsx"),
|
||||
"StudioNotFoundPage",
|
||||
),
|
||||
),
|
||||
NOT_FOUND: runtime(
|
||||
"NOT_FOUND",
|
||||
routeModule(
|
||||
() => import("./public/pages/public-not-found-page.tsx"),
|
||||
"PublicNotFoundPage",
|
||||
),
|
||||
),
|
||||
}) satisfies Readonly<Record<TechLogRouteId, RouteRuntime>>;
|
||||
|
||||
export const TECH_LOG_ROUTE_LAYOUTS: Readonly<
|
||||
Record<"PUBLIC" | "STUDIO", ReactNode>
|
||||
> = Object.freeze({
|
||||
PUBLIC: (
|
||||
<PublicShell>
|
||||
<Outlet />
|
||||
</PublicShell>
|
||||
),
|
||||
STUDIO: (
|
||||
<StudioShell>
|
||||
<Outlet />
|
||||
</StudioShell>
|
||||
),
|
||||
});
|
||||
Reference in New Issue
Block a user