import React, { useContext } from "react";

import { Avatar, Icon } from "@ax/components";
import { Restricted } from "@ax/guards";
import type { IRouter } from "@ax/routes";

import { NavContext } from "./../context";
import NavSubItem from "./NavSubItem";

import * as S from "./style";

const NavItem = (props: IProps) => {
	const {
		route: { component, path, name, icon, routesGroups, onClick, url, target = "_blank", avatar },
		location,
		type,
		isOpened,
		setHistoryPush,
	} = props;

	const { state, toggleSubmenu } = useContext(NavContext)!;

	const isSelected = location ? location.pathname === path || location.pathname.includes(path) : false;
	const isSelectedClass = isSelected ? "selected" : "";
	const hasImage = avatar ? "withImage" : "";

	const hasSubmenu = routesGroups && routesGroups.length > 0;
	const isSubmenuOpen = !!state[name];

	const handleClick = () => {
		if (onClick) {
			onClick();
		} else if (url) {
			window.open(url, target);
		} else if (component && location && location.pathname !== path) {
			setHistoryPush(path);
		} else if (isOpened && hasSubmenu) {
			toggleSubmenu(name);
		}
	};

	const subMenuIcon = isSubmenuOpen ? "UpArrow" : "DownArrow";

	const DropdownClass = isOpened ? "inline" : "floating";

	return (
		<S.Item key={name} type={type} isOpened={isOpened} isSubmenuOpen={isSubmenuOpen} active={isSelected}>
			<S.NavLink onClick={handleClick} className={`${isSelectedClass} ${hasImage}`}>
				{avatar ? (
					<S.AvatarWithBorder>
						<Avatar image={avatar.image} name={avatar.name} size={32} background bold />
					</S.AvatarWithBorder>
				) : (
					<S.Icon>{icon && <Icon name={icon} size="24px" />}</S.Icon>
				)}
				<S.LinkName active={isSelected || isSubmenuOpen}>{name}</S.LinkName>
				{hasSubmenu && isOpened && (
					<S.Arrow>
						<Icon name={subMenuIcon} />
					</S.Arrow>
				)}
			</S.NavLink>
			<S.Dropdown isSubmenu={hasSubmenu} isSubmenuOpen={isSubmenuOpen} className={DropdownClass} type={type}>
				<S.Heading onClick={handleClick}>
					<div>{name}</div>
				</S.Heading>
				{routesGroups?.map((subGroup: IRouteGroup, groupI: number) => (
					<React.Fragment key={`${subGroup.name}-${groupI}`}>
						{subGroup.routes && (
							<>
								{subGroup.routes.map((subLink: ISubRoute, subI: number) => {
									const goToSubLink = () => {
										if (location && location.pathname !== subLink.path) {
											const isEditor = !!subLink.isEditor;
											setHistoryPush(subLink.path, isEditor);
										}
										if (subLink.setDataAction && subLink.item) {
											subLink.setDataAction(subLink.item.id);
										}
									};

									const isSelectedSubItem = location ? location.pathname === subLink.path : false;

									const navSubItem = (
										<NavSubItem key={`${subLink.path}-${subI}`} active={isSelectedSubItem} type={type}>
											<S.NavLink onClick={goToSubLink}>
												<S.LinkName active={isSelected}>{subLink.name}</S.LinkName>
											</S.NavLink>
										</NavSubItem>
									);

									return subLink.permission ? (
										<Restricted to={subLink.permission} key={`${subLink.path}-${subI}`}>
											{navSubItem}
										</Restricted>
									) : (
										navSubItem
									);
								})}
							</>
						)}
					</React.Fragment>
				))}
			</S.Dropdown>
		</S.Item>
	);
};

interface ISubRoute {
	path: string;
	component?: any;
	name: string;
	permission?: string;
	isEditor?: boolean;
	setDataAction?: (id: string) => void;
	item?: { id: string };
}

interface IRouteGroup {
	name: string;
	routes: ISubRoute[];
}

interface IProps {
	route: IRouter;
	location?: Location;
	type: string;
	isOpened: boolean;
	setHistoryPush(path: string, isEditor?: boolean): void;
}

export default NavItem;
