diff --git a/frontend/src/App.tsx b/frontend/src/App.tsx index 1d09b3d7b..157e2323f 100644 --- a/frontend/src/App.tsx +++ b/frontend/src/App.tsx @@ -16,6 +16,9 @@ import OnRouteBCContext, { BCeIDUserDetailContext, IDIRUserDetailContext, } from "./common/authentication/OnRouteBCContext"; +import { NavIconSideBar } from "./common/components/naviconsidebar/NavIconSideBar"; +import { NavIconHomeButton } from "./common/components/naviconsidebar/NavIconHomeButton"; +import { NavIconReportButton } from "./common/components/naviconsidebar/NavIconReportButton"; const authority = import.meta.env.VITE_AUTH0_ISSUER_URL || envConfig.VITE_AUTH0_ISSUER_URL; @@ -104,6 +107,10 @@ const App = () => { alertType={snackBar.alertType} /> + + + +
diff --git a/frontend/src/common/authentication/Authentication.tsx b/frontend/src/common/authentication/Authentication.tsx index 5470bb88a..15a0ff849 100644 --- a/frontend/src/common/authentication/Authentication.tsx +++ b/frontend/src/common/authentication/Authentication.tsx @@ -3,6 +3,7 @@ import Button from "@mui/material/Button"; import { LoginRedirect } from "./LoginRedirect"; import { Box, Container, Typography } from "@mui/material"; import { Loading } from "../pages/Loading"; +import { IDPS } from "../types/idp"; // eslint-disable-next-line @typescript-eslint/no-explicit-any const LoginOptions = ({ auth }: any) => ( @@ -13,7 +14,7 @@ const LoginOptions = ({ auth }: any) => ( variant="contained" onClick={() => { auth.signinRedirect({ - extraQueryParams: { kc_idp_hint: "bceidboth" }, + extraQueryParams: { kc_idp_hint: IDPS.BCEID }, }); }} sx={{ width: "200px" }} @@ -27,7 +28,7 @@ const LoginOptions = ({ auth }: any) => ( variant="contained" onClick={() => { auth.signinRedirect({ - extraQueryParams: { kc_idp_hint: "idir" }, + extraQueryParams: { kc_idp_hint: IDPS.IDIR }, }); }} sx={{ width: "200px" }} diff --git a/frontend/src/common/authentication/LoginRedirect.tsx b/frontend/src/common/authentication/LoginRedirect.tsx index 501fca470..2307a7e73 100644 --- a/frontend/src/common/authentication/LoginRedirect.tsx +++ b/frontend/src/common/authentication/LoginRedirect.tsx @@ -7,6 +7,7 @@ import { HomePage } from "../../features/homePage/HomePage"; import { BCeIDUserContextType } from "./types"; import { Loading } from "../pages/Loading"; import { useUserContext } from "../../features/manageProfile/apiManager/hooks"; +import { IDPS } from "../types/idp"; /* * Redirects user to their correct page after loading their @@ -25,7 +26,7 @@ export const LoginRedirect = () => { */ useEffect(() => { if (isAuthenticated && !isLoading) { - if (userFromToken?.profile?.identity_provider === "idir") { + if (userFromToken?.profile?.identity_provider === IDPS.IDIR) { navigate(routes.IDIR_WELCOME); } else { const userContextData: BCeIDUserContextType | undefined = diff --git a/frontend/src/common/components/header/Header.tsx b/frontend/src/common/components/header/Header.tsx index 0fb1c7ccf..0b79ab4c8 100644 --- a/frontend/src/common/components/header/Header.tsx +++ b/frontend/src/common/components/header/Header.tsx @@ -15,6 +15,7 @@ import { UserSectionInfo } from "./components/UserSectionInfo"; import { getLoginUsernameFromSession } from "../../apiManager/httpRequestHandler"; import { SearchButton } from "./components/SearchButton"; import { SearchFilter } from "./components/SearchFilter"; +import { IDPS } from "../../types/idp"; const getEnv = () => { const env = @@ -106,7 +107,7 @@ export const Header = () => { const [filterOpen, setFilterOpen] = useState(false); const { isAuthenticated, user } = useAuth(); const username = getLoginUsernameFromSession(); - const isIdir = user?.profile?.identity_provider === "idir"; + const isIdir = user?.profile?.identity_provider === IDPS.IDIR; const toggleMenu = () => { setMenuOpen(!menuOpen); diff --git a/frontend/src/common/components/naviconsidebar/NavIconHomeButton.scss b/frontend/src/common/components/naviconsidebar/NavIconHomeButton.scss new file mode 100644 index 000000000..7ff3e9447 --- /dev/null +++ b/frontend/src/common/components/naviconsidebar/NavIconHomeButton.scss @@ -0,0 +1,7 @@ +@use "../../../themes/orbcStyles"; + +.nav-icon-home-button-container { + border: 1px solid #003366; + background-color: #003366; + width: 45px; +} \ No newline at end of file diff --git a/frontend/src/common/components/naviconsidebar/NavIconHomeButton.tsx b/frontend/src/common/components/naviconsidebar/NavIconHomeButton.tsx new file mode 100644 index 000000000..99ffe675b --- /dev/null +++ b/frontend/src/common/components/naviconsidebar/NavIconHomeButton.tsx @@ -0,0 +1,27 @@ +import './NavIconHomeButton.scss' +import { IconButton, Tooltip } from "@mui/material"; +import { Home } from "@mui/icons-material"; +import { useNavigate } from "react-router-dom"; +import * as routes from "../../../routes/constants"; + +/** + * Displays the navigation icon for Home on the NavIconSideBar + */ +export const NavIconHomeButton = () => { + + const navigate = useNavigate() + + return ( +
+ + {navigate(routes.IDIR_WELCOME)}} + > + + + +
+ ) +} diff --git a/frontend/src/common/components/naviconsidebar/NavIconReportButton.scss b/frontend/src/common/components/naviconsidebar/NavIconReportButton.scss new file mode 100644 index 000000000..918e74595 --- /dev/null +++ b/frontend/src/common/components/naviconsidebar/NavIconReportButton.scss @@ -0,0 +1,7 @@ +@use "../../../themes/orbcStyles"; + +.nav-icon-report-button-container { + border: 1px solid #003366; + background-color: #003366; + width: 45px; +} \ No newline at end of file diff --git a/frontend/src/common/components/naviconsidebar/NavIconReportButton.tsx b/frontend/src/common/components/naviconsidebar/NavIconReportButton.tsx new file mode 100644 index 000000000..9fa9b87a1 --- /dev/null +++ b/frontend/src/common/components/naviconsidebar/NavIconReportButton.tsx @@ -0,0 +1,27 @@ +import './NavIconReportButton.scss' +import { IconButton, Tooltip } from "@mui/material"; +import { Note } from "@mui/icons-material"; +import { useNavigate } from "react-router-dom"; +import * as routes from "../../../routes/constants"; + +/** + * Displays the navigation icon for Reports on the NavIconSideBar + */ +export const NavIconReportButton = () => { + + const navigate = useNavigate() + + return ( +
+ + {navigate(routes.IDIR_WELCOME)}} + > + + + +
+ ) +} \ No newline at end of file diff --git a/frontend/src/common/components/naviconsidebar/NavIconSideBar.scss b/frontend/src/common/components/naviconsidebar/NavIconSideBar.scss new file mode 100644 index 000000000..db6f657e1 --- /dev/null +++ b/frontend/src/common/components/naviconsidebar/NavIconSideBar.scss @@ -0,0 +1,8 @@ +@use "../../../themes/orbcStyles"; + +.nav-icon-side-bar { + position: -webkit-sticky; /* Safari */ + position: sticky; + left: 0; + top: 400px; +} \ No newline at end of file diff --git a/frontend/src/common/components/naviconsidebar/NavIconSideBar.tsx b/frontend/src/common/components/naviconsidebar/NavIconSideBar.tsx new file mode 100644 index 000000000..e3071863c --- /dev/null +++ b/frontend/src/common/components/naviconsidebar/NavIconSideBar.tsx @@ -0,0 +1,26 @@ + +import {IDPS} from '../../types/idp' +import './NavIconSideBar.scss' +import { useAuth } from 'react-oidc-context' + +interface NavIconSideBarProps { + children?: React.ReactNode; +} + +/** + * Displays a sidebar with NavIcon buttons as children + */ +export const NavIconSideBar = (props: NavIconSideBarProps) => { + const { children } = props; + const { user } = useAuth() + const isIdir = user?.profile?.identity_provider === IDPS.IDIR + + return ( +
+ {isIdir && children} +
+ ) +} + + + \ No newline at end of file diff --git a/frontend/src/common/types/idp.ts b/frontend/src/common/types/idp.ts new file mode 100644 index 000000000..eb8a9db7d --- /dev/null +++ b/frontend/src/common/types/idp.ts @@ -0,0 +1,6 @@ +export const IDPS = { + BCEID: 'bceidboth', + IDIR: 'idir' +} as const + +export type IDP = typeof IDPS[keyof typeof IDPS] diff --git a/frontend/src/features/homePage/HomePage.tsx b/frontend/src/features/homePage/HomePage.tsx index e0ab44170..41686cb90 100644 --- a/frontend/src/features/homePage/HomePage.tsx +++ b/frontend/src/features/homePage/HomePage.tsx @@ -3,12 +3,13 @@ import { useAuth } from "react-oidc-context"; import { LoadBCeIDUserRolesByCompany } from "../../common/authentication/LoadBCeIDUserRolesByCompany"; import OnRouteBCContext from "../../common/authentication/OnRouteBCContext"; import { LoadIDIRUserRoles } from "../../common/authentication/LoadIDIRUserRoles"; +import { IDPS } from "../../common/types/idp"; /** * @param identityProvider The identity provider from the user token. * @returns Boolean indicating if a logged in user is an IDIR. */ -const isIDIRUser = (identityProvider: string) => identityProvider === "idir"; +const isIDIRUser = (identityProvider: string) => identityProvider === IDPS.IDIR; export const HomePage = React.memo(() => { const { isAuthenticated, user: userFromToken } = useAuth(); diff --git a/frontend/src/features/manageProfile/apiManager/hooks.ts b/frontend/src/features/manageProfile/apiManager/hooks.ts index d797d4f95..e4a00d3b9 100644 --- a/frontend/src/features/manageProfile/apiManager/hooks.ts +++ b/frontend/src/features/manageProfile/apiManager/hooks.ts @@ -17,6 +17,7 @@ import { } from "../../../common/authentication/types"; import { BCeIDAuthGroup } from "../types/userManagement"; import { useAuth } from "react-oidc-context"; +import { IDPS } from "../../../common/types/idp"; /** * Fetches company info of current user. @@ -55,7 +56,7 @@ export const useUserContext = () => { ) => { if ( isAuthenticated && - userFromToken?.profile?.identity_provider === "idir" + userFromToken?.profile?.identity_provider === IDPS.IDIR ) { const { user } = userContextResponseBody as IDIRUserContextType; if (user?.userGUID) { diff --git a/frontend/src/routes/ProtectedRoutes.tsx b/frontend/src/routes/ProtectedRoutes.tsx index 63e67fa7e..3f0da01c9 100644 --- a/frontend/src/routes/ProtectedRoutes.tsx +++ b/frontend/src/routes/ProtectedRoutes.tsx @@ -9,8 +9,9 @@ import { LoadBCeIDUserRolesByCompany } from "../common/authentication/LoadBCeIDU import { LoadBCeIDUserContext } from "../common/authentication/LoadBCeIDUserContext"; import { LoadIDIRUserContext } from "../common/authentication/LoadIDIRUserContext"; import { LoadIDIRUserRoles } from "../common/authentication/LoadIDIRUserRoles"; +import { IDPS } from "../common/types/idp"; -const isIDIR = (identityProvider: string) => identityProvider === "idir"; +const isIDIR = (identityProvider: string) => identityProvider === IDPS.IDIR; export const ProtectedRoutes = ({ requiredRole, diff --git a/frontend/src/routes/constants.tsx b/frontend/src/routes/constants.tsx index ef90f9410..2f54e89b7 100644 --- a/frontend/src/routes/constants.tsx +++ b/frontend/src/routes/constants.tsx @@ -1,3 +1,5 @@ +import { IDPS } from "../common/types/idp"; + export const HOME = "/"; export const UNAUTHORIZED = "unauthorized"; @@ -27,9 +29,8 @@ export const WELCOME = "welcome"; export const USER_INFO = "user-info"; // IDIR -const IDIR = "idir"; -export const IDIR_WELCOME = `/${IDIR}/welcome`; -export const SEARCH_RESULTS = `/${IDIR}/search-results`; +export const IDIR_WELCOME = `/${IDPS.IDIR}/welcome`; +export const SEARCH_RESULTS = `/${IDPS.IDIR}/search-results`; // Payment export const PAYMENT_REDIRECT = "payment"