import { FluentButton } from "../../../inputs/buttons/FluentButton.mjs";
import { LogicalSearchOperatorEnums, UdpEnums, UdpReminderFiledForType } from "../../../../enums/unitySystemEnums.mjs";
import { useHandleAxiosSnackbar } from "../../../../utilities/apiHelpers.mjs";
import { useUser } from "../../../../utilities/auth/useUser.mjs";
import { FluentIconButton } from "../../../inputs/buttons/FluentIconButton.mjs";
import { useActionState } from "../../../../hooks/useActions.mjs";
import { getSearchIdentifiers, getSearchObject } from "../../../../utilities/search/SearchUtilities.mjs";
import { executeQueryAdHoc, executeQueryWithParameters, getBaseMethod } from "../../../../udp/utilities/methodUtils.mjs";
import WidgetCard from "../../WidgetCard.mjs";
import { RemindersCard } from "../../../../reminders/RemindersCard.mjs";
import React, { forwardRef, useCallback, useEffect, useMemo, useState } from "react";
import { CircularProgress, FormControlLabel, Switch, makeStyles } from "@material-ui/core";
import { SortIcon } from "@fluentui/react-icons";
import { useTranslation } from "react-i18next";
import { v4 } from "uuid";
import { Alert } from "@material-ui/lab";
//#region src/UI/widgets/library/RemindersWidget/RemindersWidget.jsx
const useStyles = makeStyles((theme) => ({
	root: {},
	actions: {
		display: "flex",
		alignItems: "center",
		width: "100%",
		justifyContent: "flex-end"
	},
	actionButton: {
		marginRight: theme.spacing(.25),
		position: "relative"
	},
	fabProgress: {
		position: "absolute",
		top: 4,
		left: "35%",
		zIndex: 1
	}
}));
const RemindersWidget = (props, ref) => {
	const { children, params, setParam, ...other } = props;
	const { onLoadedNodeClick, hideWidgetName, tree, catalogObjects } = params;
	const [sortDirection, setSortDirection] = useState(null);
	const [reminders, setReminders] = useState(null);
	const [loading, setLoading] = useState(false);
	const [allRemindersRequested, setAllRemindersRequested] = useState(false);
	const [buttonProgress, setButtonProgress] = useState(false);
	const [alertWarnings, setAlertWarnings] = useState([]);
	const classes = useStyles(props);
	const { catalogPromotedEntities } = useActionState();
	const { handleErrorSnackbar } = useHandleAxiosSnackbar();
	const { t } = useTranslation();
	const user = useUser();
	const reminderFiledForSearchApiMethod = useMemo(() => {
		return getBaseMethod(UdpEnums.Udp_Reminder_Filed_For, "unityBaseSearchMethod", catalogPromotedEntities);
	}, [catalogPromotedEntities]);
	const updateReminderApiMethod = useMemo(() => {
		return getBaseMethod(UdpEnums.Udp_Reminder, "unityBaseUpdateMethod", catalogPromotedEntities);
	}, [catalogPromotedEntities]);
	const currentSortDirection = useMemo(() => {
		if (sortDirection === "asc") return "desc";
		else if (sortDirection === "desc") return "asc";
		else return null;
	}, [sortDirection]);
	const getNodeToLoad = useCallback((reminder) => {
		const nodeToLoad = {};
		const domainObject = reminder?.domainObject;
		const entityBusinessKey = reminder?.entityBusinessKey || "";
		let treeStructureId = "";
		let apiMethodId = "";
		const matchingNode = tree?.treeStructure?.find((node) => node.properties?.catalogReturnObject === domainObject);
		if (matchingNode) {
			treeStructureId = matchingNode.id;
			if (!matchingNode.parentId) apiMethodId = tree.apiMethodInstance.apiMethodId;
			else {
				const associatedInquiryTree = matchingNode.properties?.associatedInquiryTree;
				if (associatedInquiryTree) apiMethodId = associatedInquiryTree.apiMethodInstance?.apiMethodId || "";
			}
		}
		nodeToLoad.apiMethodId = apiMethodId;
		const searchIdentifiers = getSearchIdentifiers(catalogObjects, domainObject);
		const filterElements = [];
		const values = (entityBusinessKey.split("|")?.[1]).split(",");
		searchIdentifiers.forEach((searchIdentifier, index) => {
			const searchField = searchIdentifier ? searchIdentifier.charAt(0).toUpperCase() + searchIdentifier.slice(1) : "";
			filterElements.push({
				searchField,
				searchOperator: "=",
				searchValue: values[index]
			});
		});
		nodeToLoad.queryPayload = getSearchObject(filterElements, 1, 50, true, LogicalSearchOperatorEnums.And);
		nodeToLoad.nodeDetails = {
			catalogReturnObject: domainObject,
			treeStructureId
		};
		return nodeToLoad;
	}, [tree, catalogObjects]);
	const getIcon = useCallback((reminder) => {
		const domainObject = reminder?.domainObject;
		return (tree?.treeStructure?.find((node) => node.properties?.catalogReturnObject === domainObject))?.properties?.defaultIcon || {};
	}, [tree]);
	const sortByDate = useCallback((reminderList, direction) => {
		const sortedReminders = [...reminderList];
		if (direction === "asc") sortedReminders.sort((a, b) => new Date(b.reminderDate) - new Date(a.reminderDate));
		else if (direction === "desc") sortedReminders.sort((a, b) => new Date(a.reminderDate) - new Date(b.reminderDate));
		setReminders(sortedReminders);
	}, []);
	const sort = useCallback(() => {
		sortByDate(reminders, sortDirection || "desc");
		if (sortDirection === "desc" || !sortDirection) setSortDirection("asc");
		else if (sortDirection === "asc") setSortDirection("desc");
	}, [
		reminders,
		sortByDate,
		sortDirection
	]);
	const getReminders = useCallback(async (allRequested = false, rffSearchApiMethod) => {
		let remindersList = [];
		const warnings = [];
		if (!reminders) setLoading(true);
		let filterElements = [
			{
				searchField: "Reminder.Acknowledged",
				searchValue: false,
				searchOperator: "=",
				groupId: 1
			},
			{
				searchField: "Reminder.ReminderDate",
				searchValue: /* @__PURE__ */ new Date(),
				searchOperator: "<=",
				groupId: 1
			},
			{
				searchField: "Type",
				searchValue: UdpReminderFiledForType.System,
				searchOperator: "=",
				groupId: 2
			},
			{
				searchField: "Type",
				searchValue: UdpReminderFiledForType.User,
				searchOperator: "=",
				groupId: 3
			},
			{
				searchField: "Reminder.UnityUserID",
				searchValue: user.id,
				searchOperator: "=",
				groupId: 3
			}
		];
		let filterGroups = [
			{
				groupId: 1,
				logicalSearchOperator: LogicalSearchOperatorEnums.And,
				parentGroupId: null
			},
			{
				groupId: 2,
				logicalSearchOperator: LogicalSearchOperatorEnums.Or,
				parentGroupId: null
			},
			{
				groupId: 3,
				logicalSearchOperator: LogicalSearchOperatorEnums.And,
				parentGroupId: 2
			}
		];
		if (allRequested) {
			filterElements = [
				{
					searchField: "Type",
					searchValue: UdpReminderFiledForType.System,
					searchOperator: "=",
					groupId: 2
				},
				{
					searchField: "Type",
					searchValue: UdpReminderFiledForType.User,
					searchOperator: "=",
					groupId: 3
				},
				{
					searchField: "Reminder.UnityUserID",
					searchValue: user.id,
					searchOperator: "=",
					groupId: 3
				}
			];
			filterGroups = [{
				groupId: 2,
				logicalSearchOperator: LogicalSearchOperatorEnums.Or,
				parentGroupId: null
			}, {
				groupId: 3,
				logicalSearchOperator: LogicalSearchOperatorEnums.And,
				parentGroupId: 2
			}];
		}
		const data = { data: getSearchObject(filterElements, 1, 200, true, LogicalSearchOperatorEnums.And, filterGroups) };
		if (rffSearchApiMethod) if (!rffSearchApiMethod.apiMethodId) warnings.push({
			id: v4(),
			severity: "warning",
			message: t("Search ReminderFiledFor Method Not Promoted")
		});
		else {
			const response = await executeQueryAdHoc(data, rffSearchApiMethod.apiMethodId).catch((e) => {
				setLoading(false);
			});
			if (response?.status === 200) {
				const pageList = response.data.pageList;
				if (pageList?.length) remindersList = pageList.map((item) => ({
					...item.reminder,
					domainObject: item.domainObject,
					filedToType: item.type,
					entityBusinessKey: item.entityBusinessKey
				}));
			} else warnings.push({
				id: v4(),
				severity: "error",
				message: t("Could not retrieve reminders")
			});
		}
		const treeDomains = tree?.treeStructure.map((node) => node.properties?.catalogReturnObject);
		if (treeDomains.length) remindersList = remindersList.filter((reminder) => treeDomains.includes(reminder.domainObject));
		else remindersList = [];
		setAlertWarnings(warnings);
		setLoading(false);
		sortByDate(remindersList, currentSortDirection);
	}, [
		t,
		user,
		reminders,
		sortByDate,
		currentSortDirection,
		tree
	]);
	const updateRemindersAcknowledgement = useCallback(async (reminders) => {
		if (updateReminderApiMethod) {
			const updatedPromises = [];
			reminders.forEach((reminder) => {
				reminder.acknowledged = reminder.checked;
				const data = { requestBody: { ...reminder } };
				data["{iD}"] = reminder.id;
				updatedPromises.push(executeQueryWithParameters({ data }, updateReminderApiMethod.apiMethodId));
			});
			await Promise.all(updatedPromises.map((p) => p.catch((e) => e))).then((responses) => {
				responses.forEach((response) => {
					if (response.status === 200) {
						const entityBusinessKey = response.data.entityBusinessKey;
						if (!reminders?.find((nftu) => nftu.value === entityBusinessKey)) console.warn(`Reminder not updated for all file to entities`);
					}
				});
			});
		} else handleErrorSnackbar(null, "Update Reminder Method Not Promoted");
	}, [updateReminderApiMethod, handleErrorSnackbar]);
	const handleAcknowledgeClick = useCallback(async () => {
		const acknowledgedReminders = reminders?.filter((r) => r.checked);
		if (acknowledgedReminders.length) {
			setButtonProgress(true);
			await updateRemindersAcknowledgement(acknowledgedReminders);
			setButtonProgress(false);
			getReminders(allRemindersRequested, reminderFiledForSearchApiMethod);
		}
	}, [
		reminders,
		getReminders,
		updateRemindersAcknowledgement,
		allRemindersRequested,
		reminderFiledForSearchApiMethod
	]);
	const handleSwitchChange = useCallback((event) => {
		if (reminderFiledForSearchApiMethod) setLoading(true);
		setAllRemindersRequested(event.target.checked);
	}, [reminderFiledForSearchApiMethod]);
	useEffect(() => {
		if (reminderFiledForSearchApiMethod) getReminders(allRemindersRequested, reminderFiledForSearchApiMethod);
	}, [reminderFiledForSearchApiMethod, allRemindersRequested]);
	return /* @__PURE__ */ React.createElement(WidgetCard, {
		ref,
		hideWidgetName,
		headerActions: /* @__PURE__ */ React.createElement("div", { className: classes.actions }, /* @__PURE__ */ React.createElement(FormControlLabel, {
			control: /* @__PURE__ */ React.createElement(Switch, {
				id: "udpRecord-RemindersWidget-Switch",
				udprecordid: "udpRecord-RemindersWidget-Switch",
				size: "small",
				onChange: handleSwitchChange,
				onMouseDown: (e) => e.stopPropagation()
			}),
			label: "All",
			style: { marginRight: 8 }
		}), /* @__PURE__ */ React.createElement(FluentIconButton, {
			id: "udpRecord-RemindersWidget-Sort",
			udprecordid: "udpRecord-RemindersWidget-Sort",
			icon: SortIcon,
			onClick: sort,
			style: { marginRight: 4 },
			onMouseDown: (e) => e.stopPropagation()
		}), /* @__PURE__ */ React.createElement("div", { className: classes.actionButton }, /* @__PURE__ */ React.createElement(FluentButton, {
			id: "udpRecord-RemindersWidget-Complete",
			udprecordid: "udpRecord-RemindersWidget-Complete",
			variant: "contained",
			color: "secondary",
			onClick: handleAcknowledgeClick,
			onMouseDown: (e) => e.stopPropagation()
		}, buttonProgress && /* @__PURE__ */ React.createElement(CircularProgress, {
			size: 24,
			color: "primary",
			className: classes.fabProgress
		}), t("Complete")))),
		...other
	}, alertWarnings.length ? alertWarnings.map((warning) => /* @__PURE__ */ React.createElement(Alert, {
		key: warning.id,
		severity: warning.severity || "warning"
	}, warning.message || "")) : /* @__PURE__ */ React.createElement(RemindersCard, {
		reminders,
		setReminders,
		loading,
		onLoadedNodeClick,
		getNodeToLoad,
		getIcon,
		updateRemindersAcknowledgement
	}), children);
};
var RemindersWidget_default = forwardRef(RemindersWidget);
//#endregion
export { RemindersWidget, RemindersWidget_default as default };

//# sourceMappingURL=RemindersWidget.mjs.map