import React, { useState, useEffect, useMemo, Suspense } from "react";
|
import {
|
useTranslate,
|
DashboardMenuItem,
|
MenuItemLink,
|
Menu,
|
useSidebarState,
|
usePermissions,
|
} from "react-admin";
|
import { useLocation } from "react-router-dom";
|
import { Box } from "@mui/material";
|
import SubMenu from "./SubMenu";
|
import SettingsIcon from "@mui/icons-material/Settings";
|
import DashboardIcon from "@mui/icons-material/Dashboard";
|
import HorizontalRuleIcon from "@mui/icons-material/HorizontalRule";
|
import PersonIcon from "@mui/icons-material/Person";
|
import * as Icons from "@mui/icons-material";
|
|
const getIconComponent = (iconStr) => {
|
return Icons[iconStr] || HorizontalRuleIcon;
|
};
|
|
export const MyMenu = ({ dense = false }) => {
|
const [state, setState] = useState({});
|
const translate = useTranslate();
|
const location = useLocation();
|
const [sidebarIsOpen] = useSidebarState();
|
const { isPending, permissions } = usePermissions();
|
|
useEffect(() => {
|
// default open sub menu
|
const defaultExpandMenu = [
|
"menu.system",
|
"menu.dispatcher",
|
"menu.equipment",
|
];
|
permissions?.forEach((item) => {
|
if (defaultExpandMenu.includes(item.name)) {
|
setState((state) => ({ ...state, [item.route]: true }));
|
}
|
});
|
}, [permissions]);
|
|
useEffect(() => {
|
// expand this parent menu
|
const currentPath = location.pathname;
|
const parentRoutes = findParentRoutes(currentPath, permissions);
|
for (const parentRoute of parentRoutes) {
|
setState((state) => ({ ...state, [parentRoute]: true }));
|
}
|
}, [location.pathname]);
|
|
const handleToggle = (menu) => {
|
setState((state) => ({ ...state, [menu]: !state[menu] }));
|
};
|
|
const getIcon = (iconStr) => {
|
const IconComponent = getIconComponent(iconStr);
|
if (IconComponent) {
|
return <IconComponent />;
|
} else {
|
return <KeyboardArrowDownIcon />
|
}
|
};
|
|
const generateMenu = (permissions) => {
|
return permissions.map((node) => {
|
if (node.children) {
|
return (
|
<SubMenu
|
key={node.id}
|
handleToggle={() => handleToggle(node.route)}
|
isOpen={state[node.route]}
|
name={node.name}
|
dense={dense}
|
icon={getIcon(node.icon)}
|
>
|
{generateMenu(node.children)}
|
</SubMenu>
|
);
|
} else {
|
if (node.component) {
|
return (
|
<MenuItemLink
|
key={node.id}
|
to={node.component} // correspond to Resource.name
|
state={{ _scrollToTop: true }}
|
// primaryText={translate(`resources.orders.name`, {
|
// smart_count: 2,
|
// })}
|
primaryText={node.name}
|
leftIcon={getIcon(node.icon)}
|
dense={dense}
|
sx={{ '& .RaMenuItemLink-icon': { visibility: 'hidden', minWidth: '24px' } }}
|
/>
|
);
|
}
|
}
|
});
|
};
|
|
return isPending ? (
|
<div>Waiting for permissions...</div>
|
) : (
|
<Box
|
sx={{
|
width: sidebarIsOpen ? 200 : 50,
|
marginTop: 1,
|
marginBottom: 1,
|
transition: (theme) =>
|
theme.transitions.create("width", {
|
easing: theme.transitions.easing.sharp,
|
duration: theme.transitions.duration.leavingScreen,
|
}),
|
}}
|
>
|
<Menu.Item
|
to="/dashboard"
|
primaryText="menu.dashboard"
|
leftIcon={<DashboardIcon />}
|
/>
|
{permissions && generateMenu(permissions)}
|
{/* <Menu.ResourceItems /> */}
|
<Menu.Item
|
to="/settings"
|
primaryText="menu.settings"
|
leftIcon={<PersonIcon />}
|
/>
|
</Box>
|
);
|
};
|
|
const findParentRoutes = (pathname, permissions) => {
|
if (!pathname || !permissions) {
|
return [];
|
}
|
const findMenu = (currentPermissions, path) => {
|
for (const item of currentPermissions) {
|
if (item.component === path) {
|
return item;
|
}
|
if (item.children) {
|
const found = findMenu(item.children, path);
|
if (found) {
|
return found;
|
}
|
}
|
}
|
return null;
|
};
|
|
const findParentRoutesRecursive = (item, allPermissions) => {
|
const parentRoutes = [];
|
let current = item;
|
while (current && current.parentId) {
|
const parent = allPermissions.find(
|
(permission) => permission.id === current.parentId,
|
);
|
if (parent) {
|
parentRoutes.push(parent.route);
|
current = parent;
|
} else {
|
break;
|
}
|
}
|
|
return parentRoutes;
|
};
|
|
const currentMenu = findMenu(permissions, pathname.replace("/", ""));
|
if (currentMenu) {
|
return findParentRoutesRecursive(currentMenu, permissions);
|
}
|
|
return [];
|
};
|