/* eslint-disable react/no-unstable-nested-components */
import React, { Fragment, useEffect, useState } from 'react';
import PropTypes from 'prop-types';
import { useDispatch, useSelector } from 'react-redux';
import classNames from 'clsx';
import Image from 'next/image';
import NextLink from 'next/link';
import { useRouter } from 'next/router';
import { HelpOutlineOutlined } from '@mui/icons-material';

import { DEFAULT_PAGES_MAP } from '@/modules/@common/router/constants/mapping';
import { ANALYTIC_MENU } from '@/modules/layout/components/menu/constants';
import { CANCEL_UPLOAD_LOGOUT } from '@/modules/uploaderNew/constants';

import { logOutEventAction } from '@/modules/@common/token/redux/slices';
import {
  getUserAccountIdSelector,
  getUserAccountSelector,
  getUserFirstNameSelector,
  getUserIdSelector,
  getUserLastNameSelector,
  getUserPermissionsSelector,
  getUserRoleSelector,
} from '@/modules/@common/user/redux/selectors';
import {
  getActiveIdOfParentMenuItem,
  getMenuCollection,
  getUserMenuCollections,
  isMobileApp,
} from '@/modules/layout/helpers';
import { followToHelpLinkAction } from '@/modules/layout/redux/slices';

import AnalyticsMenu from '@/modules/analytics/general/components/Menu';
import ItemMenu from '@/modules/layout/components/menu/ItemMenu';
import SubMenuItem from '@/modules/layout/components/menu/SubMenuItem';
import useShowCancelUploadDialog from '@/modules/uploaderNew/components/useShowCancelUploadDialog';
import { Box, CircularProgress, Link, Tooltip, UserAvatar } from '@/mui/components';

import logo from '@/assets/img/logo-symbol.png';

import styles from './index.module.scss';

const MENU_COMPONENTS = {
  [ANALYTIC_MENU.componentName]: AnalyticsMenu,
};

function MenuComponent(props) {
  const dispatch = useDispatch();
  const router = useRouter();
  const [isListHide, setListHide] = useState(false);
  const { hasInProgress, handleOpenConfirmDialog } = useShowCancelUploadDialog();

  const userId = useSelector(getUserIdSelector);
  const userName = useSelector(getUserFirstNameSelector);
  const userLastName = useSelector(getUserLastNameSelector);
  const userAccountId = useSelector(getUserAccountIdSelector);
  const userPermissions = useSelector(getUserPermissionsSelector);
  const userAccount = useSelector(getUserAccountSelector);

  const menuList = getMenuCollection(userAccountId, userPermissions);
  const userMenuList = getUserMenuCollections(userPermissions);
  const activeParentId = getActiveIdOfParentMenuItem(menuList, router.pathname);

  const { defaultPage } = useSelector(getUserRoleSelector);

  const userDefaultPage = DEFAULT_PAGES_MAP[defaultPage] ?? DEFAULT_PAGES_MAP.VIDEO_MANAGER;

  const hideListOnClick = () => {
    setListHide(true);
  };

  useEffect(() => {
    const timeout = setTimeout(() => {
      setListHide(false);
    }, 500);

    return () => clearTimeout(timeout);
  }, [isListHide]);

  const getSubMenuRecursive = (list, parentName, inactiveChild) =>
    list.map((item, i) => {
      const { id, title, href, subMenu, componentName, componentProps } = item;

      if (componentName && MENU_COMPONENTS[componentName]) {
        const RenderMenuComponent = MENU_COMPONENTS[componentName];

        return (itemMenuProps) => (
          <RenderMenuComponent {...itemMenuProps} inHouseMenuSettings={componentProps.inHouseMenuSettings}>
            {({ generalMenu, customMenu }) => (
              <>
                {getSubMenuRecursive(generalMenu, parentName, inactiveChild)}
                {getSubMenuRecursive(customMenu, parentName, inactiveChild)}
              </>
            )}
          </RenderMenuComponent>
        );
      }

      return href ? (
        <SubMenuItem
          key={id || title}
          to={href}
          hideListOnClick={hideListOnClick}
          parentName={parentName}
          title={title}
          isWithoutBorder={!!(inactiveChild && list[i + 1])}
        />
      ) : (
        <Fragment key={id || title}>
          <div className={classNames(styles.SubItem, styles.SubItem___inactive)}>
            <span className={classNames(styles.SubTitle, styles.SubTitle___inactive)}>{`${title}:`}</span>
          </div>
          {getSubMenuRecursive(subMenu, title, true)}
        </Fragment>
      );
    });

  return (
    <div className={styles.Menu}>
      <div className={classNames(styles.Item, styles.Item___logo)}>
        <div className={styles.LogoWrapper}>
          <Link component={NextLink} className={styles.LogoLink} href={userDefaultPage}>
            <Image src={logo} alt="Logo" className={styles.Img} width={500} height={500} />
            {props.loading && <CircularProgress size={50} data-id="Spinner" className={styles.Spinner} />}
          </Link>
        </div>
      </div>
      {!isMobileApp &&
        menuList.map(({ id, title, href, subMenu, icon: Icon }) => {
          const classNameItem = classNames(styles.Item, {
            [styles.Item___active]: activeParentId === id,
            [styles.Item___withTriangle]: activeParentId === id && title === 'Watch',
          });

          return href ? (
            <Link component={NextLink} key={id} href={href} className={classNameItem} data-id={title}>
              {Icon && (
                <Tooltip title={title} placement="bottom">
                  <div className={styles.ContentIcon}>
                    <Icon fontSize="large" />
                  </div>
                </Tooltip>
              )}
            </Link>
          ) : (
            <ItemMenu
              key={id}
              title={title}
              icon={Icon ? <Icon fontSize="large" /> : null}
              list={getSubMenuRecursive(subMenu, null)}
              className={classNameItem}
              isListHide={isListHide}
            />
          );
        })}
      {!isMobileApp && (
        <Box key="help-link" className={classNames(styles.Item, styles.HelpLink)}>
          {userId && !userAccount?.customLoginPageUrl && (
            <Tooltip title="Help" placement="top">
              <HelpOutlineOutlined
                fontSize="large"
                className={styles.HelpLinkIconWrapper}
                onClick={() => dispatch(followToHelpLinkAction())}
              />
            </Tooltip>
          )}
        </Box>
      )}
      <ItemMenu
        isListHide={isListHide}
        content={
          <Tooltip title={`${userName} ${userLastName}`} placement="top">
            <UserAvatar
              id={userId}
              className={styles.HelpLinkIconWrapper}
              firstName={userName}
              lastName={userLastName}
              size="small"
            />
          </Tooltip>
        }
        list={[].concat(
          getSubMenuRecursive(userMenuList, null),
          <div
            key="logout"
            tabIndex={-1}
            onKeyUp={null}
            role="button"
            data-id="logout"
            className={classNames(styles.SubItem, styles.SubItem___link)}
            onClick={() =>
              hasInProgress ? handleOpenConfirmDialog(CANCEL_UPLOAD_LOGOUT) : dispatch(logOutEventAction())
            }
          >
            <span>Logout</span>
          </div>,
        )}
        className={styles.Item}
      />
    </div>
  );
}

MenuComponent.propTypes = {
  loading: PropTypes.bool.isRequired,
};

export default MenuComponent;
