import { useEffect, useState } from "react";

import { CheckGroup, FloatingMenu, Icon, ListTitle } from "@ax/components";
import { areEquals, isReqOk, trimText } from "@ax/helpers";
import { checkgroups } from "@ax/api";
import type { IFilterValue, IQueryValue } from "@ax/types";

import * as S from "./style";

const CategoryFilter = (props: ICategoryFilterProps): JSX.Element => {
	const {
		filterItems,
		value,
		structuredData,
		siteID,
		formCategory,
		pointer = "categories",
		autoWidth = false,
		menuPosition = "left",
		hideValues = [],
		hideOnLoading,
	} = props;

	const filters: IFilterValue[] = [
		{
			name: "all",
			value: "all",
			title: "All",
		},
	];

	const selectAllOption = "all";
	const parsedValue = Array.isArray(value) && value.length ? value.map((val) => val.value) : [selectAllOption];
	const [selectedValue, setSelectedValue] = useState(parsedValue);
	const [options, setOptions] = useState(filters);
	const [hideFilter, setHideFilter] = useState(false);
	const [isLoading, setIsLoading] = useState(false);
	const title = formCategory ? formCategory.label : structuredData.title;

	const getSelectCategories = async () => {
		setIsLoading(true);
		try {
			const site = siteID ? siteID : "global";
			const items = formCategory
				? await checkgroups.getFormCategories(site, formCategory.value)
				: await checkgroups.getCheckGroupItems(site, structuredData.source);
			if (items && isReqOk(items.status)) {
				setIsLoading(false);
				return items.data;
			}
		} catch (e) {
			console.log(e);
		}
		setIsLoading(false);
		return [];
	};

	// biome-ignore lint/correctness/useExhaustiveDependencies: TODO: fix this
	useEffect(() => {
		getSelectCategories().then((items) => {
			items?.forEach((item: { value: string; title: string }) => {
				if (hideValues.includes(item.value)) {
					setHideFilter(true);
				}
				const newFilter = {
					name: item.value,
					value: item.value,
					title: item.title,
				};
				filters.push(newFilter);
			});
			setOptions(filters);
		});
	}, [siteID]);

	useEffect(() => {
		const parsedValue = Array.isArray(value) ? value.map((val) => val.value) : [];
		setSelectedValue(parsedValue);
	}, [value]);

	const setQuery = (selection: any) => {
		if (!selection.length) {
			selection = [selectAllOption];
		}
		setSelectedValue(selection);
		const queryFilters: IQueryValue[] = selection.map((value: string | number) => {
			const label = options.find((opt: IFilterValue) => opt.value === value);
			return { value, label: label?.title || "" };
		});
		filterItems(pointer, queryFilters);
	};

	const isActive = !areEquals(selectedValue, [selectAllOption]);

	const Header = () => (
		<S.HeaderWrapper isActive={isActive} autoWidth={autoWidth} className="headerWrapper">
			{trimText(title, 23)}
			<S.IconsWrapper>
				{isActive ? <Icon name="Filter" size="16" /> : <Icon name="DownArrow" size="16" />}
			</S.IconsWrapper>
		</S.HeaderWrapper>
	);

	if (hideFilter || (hideOnLoading && isLoading)) {
		return <></>;
	}

	return (
		<FloatingMenu Button={Header} position={menuPosition} closeOnSelect={false} isCheckGroup={true}>
			<ListTitle data-testid="category-filter-title">Filter by Category</ListTitle>
			<S.ChecksWrapper>
				<CheckGroup options={options} value={selectedValue} onChange={setQuery} selectAllOption={selectAllOption} />
			</S.ChecksWrapper>
		</FloatingMenu>
	);
};

export interface ICategoryFilterProps {
	filterItems(pointer: string, filter: IQueryValue[]): void;
	value: IQueryValue[];
	structuredData?: any;
	siteID: number | null;
	formCategory?: { value: string; label: string };
	pointer?: string;
	autoWidth?: boolean;
	menuPosition?: string;
	hideValues?: (string | number)[];
	hideOnLoading?: boolean;
}

export default CategoryFilter;
