2021-01-05 19:49:33 +00:00
|
|
|
import React, { ReactNode, useEffect } from "react";
|
2020-09-25 17:11:25 +00:00
|
|
|
import { Page } from "@patternfly/react-core";
|
2021-01-05 19:49:33 +00:00
|
|
|
import {
|
2021-03-18 12:48:14 +00:00
|
|
|
HashRouter as Router,
|
2021-01-05 19:49:33 +00:00
|
|
|
Route,
|
|
|
|
Switch,
|
|
|
|
useParams,
|
|
|
|
} from "react-router-dom";
|
2021-02-17 21:12:25 +00:00
|
|
|
import { ErrorBoundary, useErrorHandler } from "react-error-boundary";
|
2020-09-25 17:11:25 +00:00
|
|
|
|
2020-08-27 12:09:36 +00:00
|
|
|
import { Header } from "./PageHeader";
|
|
|
|
import { PageNav } from "./PageNav";
|
2020-09-02 07:51:42 +00:00
|
|
|
import { Help } from "./components/help-enabler/HelpHeader";
|
2020-09-25 17:11:25 +00:00
|
|
|
|
2020-10-08 11:38:25 +00:00
|
|
|
import { ServerInfoProvider } from "./context/server-info/ServerInfoProvider";
|
2020-10-06 19:25:05 +00:00
|
|
|
import { AlertProvider } from "./components/alert/Alerts";
|
2020-10-08 11:38:25 +00:00
|
|
|
|
2020-10-21 11:31:41 +00:00
|
|
|
import { AccessContextProvider, useAccess } from "./context/access/Access";
|
|
|
|
import { routes, RouteDef } from "./route-config";
|
2020-10-01 14:25:29 +00:00
|
|
|
import { PageBreadCrumbs } from "./components/bread-crumb/PageBreadCrumbs";
|
2020-10-21 11:31:41 +00:00
|
|
|
import { ForbiddenSection } from "./ForbiddenSection";
|
2021-03-16 12:37:57 +00:00
|
|
|
import { SubGroups } from "./groups/SubGroupsContext";
|
2021-01-05 19:49:33 +00:00
|
|
|
import { useRealm } from "./context/realm-context/RealmContext";
|
2021-01-11 18:56:19 +00:00
|
|
|
import { useAdminClient, asyncStateFetch } from "./context/auth/AdminClient";
|
2021-02-17 21:12:25 +00:00
|
|
|
import { ErrorRenderer } from "./components/error/ErrorRenderer";
|
2020-10-21 11:31:41 +00:00
|
|
|
|
2021-03-17 13:40:19 +00:00
|
|
|
export const mainPageContentId = "kc-main-content-page-container";
|
2020-12-11 17:34:18 +00:00
|
|
|
|
2020-10-08 11:38:25 +00:00
|
|
|
const AppContexts = ({ children }: { children: ReactNode }) => (
|
2020-11-12 19:16:41 +00:00
|
|
|
<AccessContextProvider>
|
|
|
|
<Help>
|
|
|
|
<AlertProvider>
|
2021-01-12 14:00:44 +00:00
|
|
|
<ServerInfoProvider>
|
|
|
|
<SubGroups>{children}</SubGroups>
|
|
|
|
</ServerInfoProvider>
|
2020-11-12 19:16:41 +00:00
|
|
|
</AlertProvider>
|
|
|
|
</Help>
|
|
|
|
</AccessContextProvider>
|
2020-10-08 11:38:25 +00:00
|
|
|
);
|
2020-08-27 12:09:36 +00:00
|
|
|
|
2021-01-07 14:56:14 +00:00
|
|
|
// set the realm form the path if it's one of the know realms
|
|
|
|
const RealmPathSelector = ({ children }: { children: ReactNode }) => {
|
|
|
|
const { setRealm } = useRealm();
|
|
|
|
const { realm } = useParams<{ realm: string }>();
|
|
|
|
const adminClient = useAdminClient();
|
2021-02-17 21:12:25 +00:00
|
|
|
const handleError = useErrorHandler();
|
2021-01-07 14:56:14 +00:00
|
|
|
useEffect(
|
|
|
|
() =>
|
2021-01-11 18:56:19 +00:00
|
|
|
asyncStateFetch(
|
2021-01-07 14:56:14 +00:00
|
|
|
() => adminClient.realms.find(),
|
|
|
|
(realms) => {
|
|
|
|
if (realms.findIndex((r) => r.realm == realm) !== -1) {
|
|
|
|
setRealm(realm);
|
|
|
|
}
|
2021-02-17 21:12:25 +00:00
|
|
|
},
|
|
|
|
handleError
|
2021-01-07 14:56:14 +00:00
|
|
|
),
|
|
|
|
[]
|
|
|
|
);
|
|
|
|
|
|
|
|
return <>{children}</>;
|
|
|
|
};
|
|
|
|
|
2020-10-21 11:31:41 +00:00
|
|
|
// If someone tries to go directly to a route they don't
|
|
|
|
// have access to, show forbidden page.
|
|
|
|
type SecuredRouteProps = { route: RouteDef };
|
|
|
|
const SecuredRoute = ({ route }: SecuredRouteProps) => {
|
|
|
|
const { hasAccess } = useAccess();
|
|
|
|
if (hasAccess(route.access)) return <route.component />;
|
|
|
|
|
|
|
|
return <ForbiddenSection />;
|
|
|
|
};
|
|
|
|
|
2020-08-08 13:52:23 +00:00
|
|
|
export const App = () => {
|
2020-08-04 12:59:41 +00:00
|
|
|
return (
|
2020-10-08 11:38:25 +00:00
|
|
|
<AppContexts>
|
|
|
|
<Router>
|
|
|
|
<Page
|
|
|
|
header={<Header />}
|
|
|
|
isManagedSidebar
|
|
|
|
sidebar={<PageNav />}
|
|
|
|
breadcrumb={<PageBreadCrumbs />}
|
2020-12-11 17:34:18 +00:00
|
|
|
mainContainerId={mainPageContentId}
|
2020-10-08 11:38:25 +00:00
|
|
|
>
|
2021-02-17 21:12:25 +00:00
|
|
|
<ErrorBoundary
|
|
|
|
FallbackComponent={ErrorRenderer}
|
|
|
|
onReset={() => (location.href = "/")}
|
|
|
|
>
|
|
|
|
<Switch>
|
|
|
|
{routes(() => {}).map((route, i) => (
|
|
|
|
<Route
|
|
|
|
exact={
|
|
|
|
route.matchOptions?.exact === undefined
|
|
|
|
? true
|
|
|
|
: route.matchOptions.exact
|
|
|
|
}
|
|
|
|
key={i}
|
|
|
|
path={route.path}
|
|
|
|
component={() => (
|
|
|
|
<RealmPathSelector>
|
|
|
|
<SecuredRoute route={route} />
|
|
|
|
</RealmPathSelector>
|
|
|
|
)}
|
|
|
|
/>
|
|
|
|
))}
|
|
|
|
</Switch>
|
|
|
|
</ErrorBoundary>
|
2020-10-08 11:38:25 +00:00
|
|
|
</Page>
|
|
|
|
</Router>
|
|
|
|
</AppContexts>
|
2020-08-04 12:59:41 +00:00
|
|
|
);
|
|
|
|
};
|