Skip to content

Commit b27e398

Browse files
committed
feat: add /view/config and /view/views iframe embed routes
- Remove /view/topology/:id embed route and TopologyCard page - Add /view/config/:id/[changes|relationships|access|playbooks] routes without sidebar - Add /view/views/:id and /view/views/:namespace/:name routes without sidebar - Parameterise useConfigDetailsTabs with baseRoute (default /catalog) so tab links stay within the embed layout via ConfigDetailsBaseRouteContext
1 parent d5b2748 commit b27e398

File tree

5 files changed

+131
-61
lines changed

5 files changed

+131
-61
lines changed

src/App.tsx

Lines changed: 84 additions & 15 deletions
Original file line numberDiff line numberDiff line change
@@ -40,6 +40,7 @@ import {
4040
schemaResourceTypes
4141
} from "./components/SchemaResourcePage/resourceTypes";
4242
import { ConfigPageContextProvider } from "./context/ConfigPageContext";
43+
import { ConfigDetailsBaseRouteProvider } from "./components/Configs/ConfigDetailsBaseRouteContext";
4344
import { useFeatureFlagsContext } from "./context/FeatureFlagsContext";
4445
import { HealthPageContextProvider } from "./context/HealthPageContext";
4546
import { IncidentPageContextProvider } from "./context/IncidentPageContext";
@@ -61,12 +62,6 @@ const TopologyPage = dynamic(
6162
import("@flanksource-ui/pages/TopologyPage").then((mod) => mod.TopologyPage)
6263
);
6364

64-
const TopologyCardPage = dynamic(
65-
import("@flanksource-ui/pages/TopologyCard").then(
66-
(mod) => mod.TopologyCardPage
67-
)
68-
);
69-
7065
const IncidentDetailsPage = dynamic(
7166
import("@flanksource-ui/pages/incident/IncidentDetails").then(
7267
(mod) => mod.IncidentDetailsPage
@@ -495,10 +490,7 @@ export function HealthRoutes({ sidebar }: { sidebar: ReactNode }) {
495490
export function IncidentManagerRoutes({ sidebar }: { sidebar: ReactNode }) {
496491
const { featureFlagsLoaded } = useFeatureFlagsContext();
497492

498-
if (
499-
!featureFlagsLoaded &&
500-
!window.location.pathname.startsWith("/view/topology")
501-
) {
493+
if (!featureFlagsLoaded) {
502494
return <FullPageSkeletonLoader />;
503495
}
504496

@@ -508,17 +500,94 @@ export function IncidentManagerRoutes({ sidebar }: { sidebar: ReactNode }) {
508500
<Route index element={<HomepageRedirect />} />
509501
</Route>
510502

503+
<Route path="/view/health" element={<HealthPage url={CANARY_API} />} />
504+
505+
{/* Config embed routes — no sidebar */}
506+
<Route
507+
path="/view/config/:id"
508+
element={
509+
<ConfigDetailsBaseRouteProvider baseRoute="/view/config">
510+
{withAuthorizationAccessCheck(
511+
<ConfigDetailsPage />,
512+
tables.database,
513+
"read",
514+
true
515+
)}
516+
</ConfigDetailsBaseRouteProvider>
517+
}
518+
/>
519+
<Route
520+
path="/view/config/:id/changes"
521+
element={
522+
<ConfigDetailsBaseRouteProvider baseRoute="/view/config">
523+
{withAuthorizationAccessCheck(
524+
<ConfigDetailsChangesPage />,
525+
tables.database,
526+
"read",
527+
true
528+
)}
529+
</ConfigDetailsBaseRouteProvider>
530+
}
531+
/>
532+
<Route
533+
path="/view/config/:id/relationships"
534+
element={
535+
<ConfigDetailsBaseRouteProvider baseRoute="/view/config">
536+
{withAuthorizationAccessCheck(
537+
<ConfigDetailsRelationshipsPage />,
538+
tables.database,
539+
"read",
540+
true
541+
)}
542+
</ConfigDetailsBaseRouteProvider>
543+
}
544+
/>
545+
<Route
546+
path="/view/config/:id/access"
547+
element={
548+
<ConfigDetailsBaseRouteProvider baseRoute="/view/config">
549+
{withAuthorizationAccessCheck(
550+
<ConfigDetailsAccessPage />,
551+
tables.database,
552+
"read",
553+
true
554+
)}
555+
</ConfigDetailsBaseRouteProvider>
556+
}
557+
/>
558+
<Route
559+
path="/view/config/:id/playbooks"
560+
element={
561+
<ConfigDetailsBaseRouteProvider baseRoute="/view/config">
562+
{withAuthorizationAccessCheck(
563+
<ConfigDetailsPlaybooksPage />,
564+
tables.database,
565+
"read",
566+
true
567+
)}
568+
</ConfigDetailsBaseRouteProvider>
569+
}
570+
/>
571+
572+
{/* Views embed routes — no sidebar */}
511573
<Route
512-
path="/view/topology/:id"
574+
path="/view/views/:namespace/:name"
513575
element={withAuthorizationAccessCheck(
514-
<TopologyCardPage />,
515-
tables.topologies,
576+
<ViewPage />,
577+
tables.views,
578+
"read",
579+
true
580+
)}
581+
/>
582+
<Route
583+
path="/view/views/:id"
584+
element={withAuthorizationAccessCheck(
585+
<ViewPage />,
586+
tables.views,
516587
"read",
517588
true
518589
)}
519590
/>
520-
521-
<Route path="/view/health" element={<HealthPage url={CANARY_API} />} />
522591

523592
<Route path="topology" element={sidebar}>
524593
<Route
Lines changed: 21 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,21 @@
1+
import { createContext, ReactNode, useContext } from "react";
2+
3+
const ConfigDetailsBaseRouteContext = createContext("/catalog");
4+
5+
export function useConfigDetailsBaseRoute() {
6+
return useContext(ConfigDetailsBaseRouteContext);
7+
}
8+
9+
export function ConfigDetailsBaseRouteProvider({
10+
baseRoute,
11+
children
12+
}: {
13+
baseRoute: string;
14+
children: ReactNode;
15+
}) {
16+
return (
17+
<ConfigDetailsBaseRouteContext.Provider value={baseRoute}>
18+
{children}
19+
</ConfigDetailsBaseRouteContext.Provider>
20+
);
21+
}

src/components/Configs/ConfigDetailsTabs.tsx

Lines changed: 11 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -12,6 +12,7 @@ import PlaybooksDropdownMenu from "../Playbooks/Runs/Submit/PlaybooksDropdownMen
1212
import { ErrorBoundary } from "../ErrorBoundary";
1313
import { useConfigDetailsTabs } from "./ConfigTabsLinks";
1414
import ConfigSidebar from "./Sidebar/ConfigSidebar";
15+
import { useConfigDetailsBaseRoute } from "./ConfigDetailsBaseRouteContext";
1516

1617
type ConfigDetailsTabsProps = {
1718
refetch?: () => void;
@@ -30,6 +31,8 @@ type ConfigDetailsTabsProps = {
3031
| string; // Views
3132
className?: string;
3233
extra?: ReactNode;
34+
/** Override the base route for tab links. Defaults to context value (usually "/catalog"). */
35+
baseRoute?: string;
3336
};
3437

3538
export function ConfigDetailsTabs({
@@ -39,8 +42,11 @@ export function ConfigDetailsTabs({
3942
pageTitlePrefix,
4043
activeTabName = "Spec",
4144
className = "p-2",
42-
extra
45+
extra,
46+
baseRoute
4347
}: ConfigDetailsTabsProps) {
48+
const contextBaseRoute = useConfigDetailsBaseRoute();
49+
const resolvedBaseRoute = baseRoute ?? contextBaseRoute;
4450
const { id } = useParams();
4551

4652
const [, setRefreshButtonClickedTrigger] = useAtom(
@@ -50,7 +56,10 @@ export function ConfigDetailsTabs({
5056
const { data: configItem, isLoading: isLoadingConfig } =
5157
useGetConfigByIdQuery(id!);
5258

53-
const { tabs: configTabList } = useConfigDetailsTabs(configItem?.summary);
59+
const { tabs: configTabList } = useConfigDetailsTabs(
60+
configItem?.summary,
61+
resolvedBaseRoute
62+
);
5463

5564
const playbooksButton = id ? (
5665
<PlaybooksDropdownMenu config_id={id} containerClassName="my-0" />

src/components/Configs/ConfigTabsLinks.tsx

Lines changed: 15 additions & 10 deletions
Original file line numberDiff line numberDiff line change
@@ -16,7 +16,10 @@ type ConfigDetailsTab = {
1616
search?: string;
1717
};
1818

19-
export function useConfigDetailsTabs(countSummary?: ConfigItem["summary"]): {
19+
export function useConfigDetailsTabs(
20+
countSummary?: ConfigItem["summary"],
21+
baseRoute = "/catalog"
22+
): {
2023
isLoading: boolean;
2124
isError: boolean;
2225
tabs: ConfigDetailsTab[];
@@ -41,8 +44,10 @@ export function useConfigDetailsTabs(countSummary?: ConfigItem["summary"]): {
4144
const accessLogsCount =
4245
accessLogsData?.totalEntries ?? accessLogsData?.data?.length ?? 0;
4346

47+
const base = `${baseRoute}/${id}`;
48+
4449
const staticTabs: ConfigDetailsTab[] = [
45-
{ label: "Spec", key: "Spec", path: `/catalog/${id}/spec` },
50+
{ label: "Spec", key: "Spec", path: `${base}/spec` },
4651
{
4752
label: (
4853
<>
@@ -51,7 +56,7 @@ export function useConfigDetailsTabs(countSummary?: ConfigItem["summary"]): {
5156
</>
5257
),
5358
key: "Changes",
54-
path: `/catalog/${id}/changes`
59+
path: `${base}/changes`
5560
},
5661
{
5762
label: (
@@ -61,7 +66,7 @@ export function useConfigDetailsTabs(countSummary?: ConfigItem["summary"]): {
6166
</>
6267
),
6368
key: "Insights",
64-
path: `/catalog/${id}/insights`
69+
path: `${base}/insights`
6570
},
6671
{
6772
label: (
@@ -71,7 +76,7 @@ export function useConfigDetailsTabs(countSummary?: ConfigItem["summary"]): {
7176
</>
7277
),
7378
key: "Relationships",
74-
path: `/catalog/${id}/relationships`
79+
path: `${base}/relationships`
7580
},
7681
{
7782
label: (
@@ -81,7 +86,7 @@ export function useConfigDetailsTabs(countSummary?: ConfigItem["summary"]): {
8186
</>
8287
),
8388
key: "Playbooks",
84-
path: `/catalog/${id}/playbooks`
89+
path: `${base}/playbooks`
8590
},
8691
{
8792
label: (
@@ -91,7 +96,7 @@ export function useConfigDetailsTabs(countSummary?: ConfigItem["summary"]): {
9196
</>
9297
),
9398
key: "Checks",
94-
path: `/catalog/${id}/checks`
99+
path: `${base}/checks`
95100
}
96101
];
97102

@@ -104,7 +109,7 @@ export function useConfigDetailsTabs(countSummary?: ConfigItem["summary"]): {
104109
</>
105110
),
106111
key: "Access",
107-
path: `/catalog/${id}/access`
112+
path: `${base}/access`
108113
});
109114
}
110115

@@ -117,7 +122,7 @@ export function useConfigDetailsTabs(countSummary?: ConfigItem["summary"]): {
117122
</>
118123
),
119124
key: "Access Logs",
120-
path: `/catalog/${id}/access-logs`
125+
path: `${base}/access-logs`
121126
});
122127
}
123128

@@ -142,7 +147,7 @@ export function useConfigDetailsTabs(countSummary?: ConfigItem["summary"]): {
142147
const viewTabs: ConfigDetailsTab[] = orderedViews.map((view) => ({
143148
label: view.title || view.name,
144149
key: view.id,
145-
path: `/catalog/${id}/view/${view.id}`,
150+
path: `${base}/view/${view.id}`,
146151
icon: <Icon name={view.icon || "workflow"} />
147152
}));
148153

src/pages/TopologyCard.tsx

Lines changed: 0 additions & 34 deletions
This file was deleted.

0 commit comments

Comments
 (0)