Skip to content

Commit

Permalink
Handle user config
Browse files Browse the repository at this point in the history
Signed-off-by: lucferbux <[email protected]>
  • Loading branch information
lucferbux committed Dec 11, 2024
1 parent b376b07 commit e7e3e80
Show file tree
Hide file tree
Showing 5 changed files with 109 additions and 97 deletions.
95 changes: 10 additions & 85 deletions clients/ui/frontend/src/app/App.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -5,23 +5,11 @@ import {
Alert,
Bullseye,
Button,
Dropdown,
DropdownItem,
DropdownList,
Masthead,
MastheadContent,
MastheadMain,
MenuToggle,
MenuToggleElement,
Page,
PageSection,
Spinner,
Stack,
StackItem,
Toolbar,
ToolbarContent,
ToolbarGroup,
ToolbarItem,
} from '@patternfly/react-core';
import ToastNotifications from '~/shared/components/ToastNotifications';
import { useSettings } from '~/shared/hooks/useSettings';
Expand All @@ -30,8 +18,7 @@ import NavSidebar from './NavSidebar';
import AppRoutes from './AppRoutes';
import { AppContext } from './AppContext';
import { ModelRegistrySelectorContextProvider } from './context/ModelRegistrySelectorContext';
import { Select } from '@mui/material';
import { SimpleSelect, SimpleSelectOption } from '@patternfly/react-templates';
import NavBar from './NavBar';

const App: React.FC = () => {
const {
Expand All @@ -54,7 +41,7 @@ const App: React.FC = () => {

React.useEffect(() => {
// Add the user to localStorage if in PoC
// TODO: [Env Handling] Remove this when auth is enabled
// TODO: [Env Handling] Just add this logic in PoC mode
if (username) {
localStorage.setItem(USER_ID, username);
} else {
Expand All @@ -73,19 +60,6 @@ const App: React.FC = () => {
[configSettings, userSettings],
);

const handleLogout = () => {
setUserMenuOpen(false);
// TODO: [Auth-enablement] Logout when auth is enabled
};


const [userMenuOpen, setUserMenuOpen] = React.useState(false);
const userMenuItems = [
<DropdownItem key="logout" onClick={handleLogout}>
Log out
</DropdownItem>,
];

// We lack the critical data to startup the app
if (configError) {
// There was an error fetching critical data
Expand Down Expand Up @@ -118,62 +92,6 @@ const App: React.FC = () => {
// Waiting on the API to finish
const loading = !configLoaded || !userSettings || !configSettings || !contextValue;

const Options: SimpleSelectOption[] = [
{ content: 'All Namespaces', value: 'All' },
];

const [selected, setSelected] = React.useState<string | undefined>('All');

const initialOptions = React.useMemo<SimpleSelectOption[]>(
() => Options.map((o) => ({ ...o, selected: o.value === selected })),
[selected]
);

const masthead = (
<Masthead>
<MastheadMain />
<MastheadContent>
<Toolbar>
<ToolbarContent>
<ToolbarGroup variant="action-group-plain" align={{ default: 'alignStart' }}>
<ToolbarItem>
<SimpleSelect
isDisabled
initialOptions={initialOptions}
onSelect={(_ev, selection) => setSelected(String(selection))}
>
</SimpleSelect>
</ToolbarItem>
</ToolbarGroup>
<ToolbarGroup variant="action-group-plain" align={{ default: 'alignEnd' }}>
<ToolbarItem>
{/* TODO: [Auth-enablement] Add logout button */}
<Dropdown
popperProps={{ position: 'right' }}
onOpenChange={(isOpen) => setUserMenuOpen(isOpen)}
toggle={(toggleRef: React.Ref<MenuToggleElement>) => (
<MenuToggle
aria-label="User menu"
id="user-menu-toggle"
ref={toggleRef}
onClick={() => setUserMenuOpen(!userMenuOpen)}
isExpanded={userMenuOpen}
>
{username}
</MenuToggle>
)}
isOpen={userMenuOpen}
>
<DropdownList>{userMenuItems}</DropdownList>
</Dropdown>
</ToolbarItem>
</ToolbarGroup>
</ToolbarContent>
</Toolbar>
</MastheadContent>
</Masthead>
);

return loading ? (
<Bullseye>
<Spinner />
Expand All @@ -182,7 +100,14 @@ const App: React.FC = () => {
<AppContext.Provider value={contextValue}>
<Page
mainContainerId="primary-app-container"
masthead={masthead}
masthead={
<NavBar
username={username}
onLogout={() => {
//TODO: [Auth-enablement] Logout when auth is enabled
}}
/>
}
isManagedSidebar
sidebar={<NavSidebar />}
>
Expand Down
18 changes: 6 additions & 12 deletions clients/ui/frontend/src/app/AppRoutes.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -3,6 +3,7 @@ import { Navigate, Route, Routes } from 'react-router-dom';
import { NotFound } from './pages/notFound/NotFound';
import ModelRegistrySettingsRoutes from './pages/settings/ModelRegistrySettingsRoutes';
import ModelRegistryRoutes from './pages/modelRegistry/ModelRegistryRoutes';
import { useAppContext } from './AppContext';

export const isNavDataGroup = (navItem: NavDataItem): navItem is NavDataGroup =>
'children' in navItem;
Expand All @@ -22,11 +23,8 @@ export type NavDataGroup = NavDataCommon & {
type NavDataItem = NavDataHref | NavDataGroup;

export const useAdminSettings = (): NavDataItem[] => {
// get auth access for example set admin as true
const isAdmin = true; //this should be a call to getting auth / role access
const { isAdmin } = useAppContext().user;

// TODO: [Auth-enablement] Remove the linter skip when we implement authentication
// eslint-disable-next-line @typescript-eslint/no-unnecessary-condition
if (!isAdmin) {
return [];
}
Expand All @@ -48,20 +46,16 @@ export const useNavData = (): NavDataItem[] => [
];

const AppRoutes: React.FC = () => {
const isAdmin = true;
const { isAdmin } = useAppContext().user;

return (
<Routes>
<Route path="/" element={<Navigate to="/modelRegistry" replace />} />
<Route path="/modelRegistry/*" element={<ModelRegistryRoutes />} />
<Route path="*" element={<NotFound />} />
{
// TODO: [Auth-enablement] Remove the linter skip when we implement authentication
// eslint-disable-next-line @typescript-eslint/no-unnecessary-condition
isAdmin && (
<Route path="/modelRegistrySettings/*" element={<ModelRegistrySettingsRoutes />} />
)
}
{isAdmin && (
<Route path="/modelRegistrySettings/*" element={<ModelRegistrySettingsRoutes />} />
)}
</Routes>
);
};
Expand Down
91 changes: 91 additions & 0 deletions clients/ui/frontend/src/app/NavBar.tsx
Original file line number Diff line number Diff line change
@@ -0,0 +1,91 @@
import React from 'react';
import {
Dropdown,
DropdownItem,
DropdownList,
Masthead,
MastheadContent,
MastheadMain,
MenuToggle,
MenuToggleElement,
Toolbar,
ToolbarContent,
ToolbarGroup,
ToolbarItem,
} from '@patternfly/react-core';
import { SimpleSelect, SimpleSelectOption } from '@patternfly/react-templates';

interface NavBarProps {
username?: string;
onLogout: () => void;
}

const Options: SimpleSelectOption[] = [{ content: 'All Namespaces', value: 'All' }];

const NavBar: React.FC<NavBarProps> = ({ username, onLogout }) => {
const [selected, setSelected] = React.useState<string | undefined>('All');
const [userMenuOpen, setUserMenuOpen] = React.useState(false);

const initialOptions = React.useMemo<SimpleSelectOption[]>(
() => Options.map((o) => ({ ...o, selected: o.value === selected })),
[selected],
);

const handleLogout = () => {
setUserMenuOpen(false);
onLogout();
};

const userMenuItems = [
<DropdownItem key="logout" onClick={handleLogout}>
Log out
</DropdownItem>,
];

return (
<Masthead>
<MastheadMain />
<MastheadContent>
<Toolbar>
<ToolbarContent>
<ToolbarGroup variant="action-group-plain" align={{ default: 'alignStart' }}>
<ToolbarItem>
<SimpleSelect
isDisabled
initialOptions={initialOptions}
onSelect={(_ev, selection) => setSelected(String(selection))}
/>
</ToolbarItem>
</ToolbarGroup>
{username && (
<ToolbarGroup variant="action-group-plain" align={{ default: 'alignEnd' }}>
<ToolbarItem>
<Dropdown
popperProps={{ position: 'right' }}
onOpenChange={(isOpen) => setUserMenuOpen(isOpen)}
toggle={(toggleRef: React.Ref<MenuToggleElement>) => (
<MenuToggle
aria-label="User menu"
id="user-menu-toggle"
ref={toggleRef}
onClick={() => setUserMenuOpen(!userMenuOpen)}
isExpanded={userMenuOpen}
>
{username}
</MenuToggle>
)}
isOpen={userMenuOpen}
>
<DropdownList>{userMenuItems}</DropdownList>
</Dropdown>
</ToolbarItem>
</ToolbarGroup>
)}
</ToolbarContent>
</Toolbar>
</MastheadContent>
</Masthead>
);
};

export default NavBar;
1 change: 1 addition & 0 deletions clients/ui/frontend/src/shared/hooks/useSettings.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -75,4 +75,5 @@ export const fetchConfig = async (): Promise<ConfigSettings> => ({
// TODO: [Auth-enablement] replace with the actual call once we have the endpoint
export const fetchUser = async (): Promise<UserSettings> => ({
username: '[email protected]',
isAdmin: true,
});
1 change: 1 addition & 0 deletions clients/ui/frontend/src/shared/types.ts
Original file line number Diff line number Diff line change
Expand Up @@ -3,6 +3,7 @@ import { ValueOf } from '~/shared/typeHelpers';
// TODO: [Data Flow] Get the status config params
export type UserSettings = {
username: string;
isAdmin?: boolean;
};

// TODO: [Data Flow] Add more config parameters
Expand Down

0 comments on commit e7e3e80

Please sign in to comment.