Files
EpicNext-Cms/src/features/housekeeping/domains/content/routes.ts
T
Simo b413e62085
CI / runtime-diagnostics (pull_request) Skipped
CI / check (pull_request) Successful in 58s
CI / release (pull_request) Skipped
CI / deploy (pull_request) Skipped
chore: satisfy upgraded biome checks
2026-09-01 19:14:09 +02:00

220 lines
5.7 KiB
TypeScript

import { PERMS } from "@/lib/permission-slugs";
import {
anyCapability,
type CanonicalHousekeepingHref,
type HousekeepingRouteDefinition,
} from "../../foundation/contracts";
export const CONTENT_ROUTE_GROUPS = [
"editorial",
"media",
"engagement",
"help",
"brand",
"localization",
] as const;
export type ContentRouteGroup = (typeof CONTENT_ROUTE_GROUPS)[number];
export const CONTENT_ROUTE_IDS = [
"content.editorial.articles",
"content.editorial.article-create",
"content.editorial.article-detail",
"content.media.photos",
"content.media.library",
"content.media.banners",
"content.media.ads",
"content.media.ad-create",
"content.media.ad-detail",
"content.engagement.events",
"content.engagement.event-create",
"content.engagement.event-types",
"content.engagement.event-detail",
"content.engagement.polls",
"content.engagement.poll-create",
"content.engagement.poll-detail",
"content.help.questions",
"content.help.question-create",
"content.help.question-detail",
"content.editorial.tags",
"content.engagement.prefixes",
"content.editorial.writeable-boxes",
"content.help.email-templates",
"content.brand.theme",
"content.brand.theme-builder",
"content.brand.favicon",
"content.localization.overview",
"content.localization.client",
"content.localization.cms",
"content.localization.emulator",
] as const;
export type ContentRouteId = (typeof CONTENT_ROUTE_IDS)[number];
function contentRoute(
id: ContentRouteId,
href: CanonicalHousekeepingHref,
capabilities: readonly string[],
): HousekeepingRouteDefinition {
return {
id,
labelKey: `pages.housekeeping.routes.${id}`,
href,
capability: anyCapability(...capabilities),
};
}
export const CONTENT_ROUTES = [
contentRoute(
"content.editorial.articles",
"/ase-next/content/editorial/articles",
[PERMS.NEWS_VIEW],
),
contentRoute(
"content.editorial.article-create",
"/ase-next/content/editorial/articles/new",
[PERMS.NEWS_EDIT],
),
contentRoute(
"content.editorial.article-detail",
"/ase-next/content/editorial/articles/:id",
[PERMS.NEWS_VIEW],
),
contentRoute("content.media.photos", "/ase-next/content/media/photos", [
PERMS.PAGES_VIEW,
]),
contentRoute("content.media.library", "/ase-next/content/media/library", [
PERMS.PAGES_VIEW,
]),
contentRoute("content.media.banners", "/ase-next/content/media/banners", [
PERMS.BANNERS_VIEW,
]),
contentRoute("content.media.ads", "/ase-next/content/media/ads", [
PERMS.PAGES_VIEW,
]),
contentRoute("content.media.ad-create", "/ase-next/content/media/ads/new", [
PERMS.PAGES_EDIT,
]),
contentRoute("content.media.ad-detail", "/ase-next/content/media/ads/:id", [
PERMS.PAGES_VIEW,
]),
contentRoute(
"content.engagement.events",
"/ase-next/content/engagement/events",
[PERMS.EVENTS_VIEW],
),
contentRoute(
"content.engagement.event-create",
"/ase-next/content/engagement/events/create",
[PERMS.EVENTS_EDIT],
),
contentRoute(
"content.engagement.event-types",
"/ase-next/content/engagement/events/types",
[PERMS.EVENTS_EDIT],
),
contentRoute(
"content.engagement.event-detail",
"/ase-next/content/engagement/events/:id",
[PERMS.EVENTS_EDIT],
),
contentRoute(
"content.engagement.polls",
"/ase-next/content/engagement/polls",
[PERMS.POLLS_VIEW],
),
contentRoute(
"content.engagement.poll-create",
"/ase-next/content/engagement/polls/create",
[PERMS.POLLS_EDIT],
),
contentRoute(
"content.engagement.poll-detail",
"/ase-next/content/engagement/polls/:id",
[PERMS.POLLS_EDIT],
),
contentRoute("content.help.questions", "/ase-next/content/help/questions", [
PERMS.PAGES_VIEW,
]),
contentRoute(
"content.help.question-create",
"/ase-next/content/help/questions/new",
[PERMS.PAGES_EDIT],
),
contentRoute(
"content.help.question-detail",
"/ase-next/content/help/questions/:id",
[PERMS.PAGES_VIEW],
),
contentRoute("content.editorial.tags", "/ase-next/content/editorial/tags", [
PERMS.PAGES_VIEW,
]),
contentRoute(
"content.engagement.prefixes",
"/ase-next/content/engagement/prefixes",
[PERMS.PREFIXES_VIEW],
),
contentRoute(
"content.editorial.writeable-boxes",
"/ase-next/content/editorial/writeable-boxes",
[PERMS.PAGES_VIEW],
),
contentRoute(
"content.help.email-templates",
"/ase-next/content/help/email-templates",
[PERMS.PAGES_VIEW],
),
contentRoute("content.brand.theme", "/ase-next/content/brand/theme", [
PERMS.SETTINGS_VIEW,
]),
contentRoute(
"content.brand.theme-builder",
"/ase-next/content/brand/theme-builder",
[PERMS.SETTINGS_VIEW],
),
contentRoute("content.brand.favicon", "/ase-next/content/brand/favicon", [
PERMS.SETTINGS_VIEW,
]),
contentRoute(
"content.localization.overview",
"/ase-next/content/localization",
[PERMS.SETTINGS_VIEW],
),
contentRoute(
"content.localization.client",
"/ase-next/content/localization/client",
[PERMS.SETTINGS_VIEW],
),
contentRoute(
"content.localization.cms",
"/ase-next/content/localization/cms",
[PERMS.SETTINGS_VIEW],
),
contentRoute(
"content.localization.emulator",
"/ase-next/content/localization/emulator",
[PERMS.SETTINGS_VIEW],
),
] as const satisfies readonly HousekeepingRouteDefinition[];
const routeGroups = new Map<ContentRouteId, ContentRouteGroup>(
CONTENT_ROUTE_IDS.map((routeId) => [
routeId,
routeId.split(".")[1] as ContentRouteGroup,
]),
);
export function contentRouteGroup(routeId: ContentRouteId): ContentRouteGroup {
const group = routeGroups.get(routeId);
if (!group) throw new Error(`unknown Content route: ${routeId}`);
return group;
}
export function contentRouteById(
routeId: ContentRouteId,
): (typeof CONTENT_ROUTES)[number] {
const route = CONTENT_ROUTES.find((candidate) => candidate.id === routeId);
if (!route) throw new Error(`unknown Content route: ${routeId}`);
return route;
}