import { createStore as u } from "zustand";
import { devtools as f } from "zustand/middleware";
import { immer as s } from "zustand/middleware/immer";
import { DYNAMIC_FILTER_SOTORE_ID as m } from "../constants.js";
import { getPurgedInitialFiltersApplied as c } from "../helpers/getPurgedInitialFiltersApplied.js";
function S(r) {
  r.availableFields = r.fields.filter((n) => n.multiple === void 0 || n.multiple ? !0 : !new Set(r.appliedFilters.map((a) => a.field.name)).has(n.name));
}
function w(r) {
  r.ownerState.isValid = r.appliedFilters.every((n) => n.isSet);
}
const p = (r) => {
  w(r), S(r), r.ownerState?.isValid && r.automatic && (r.ownerState.isDirty = !1, r.countOnChangeFiltersApplied++);
}, v = (r, n) => {
  const { enabled: d = !1 } = n;
  return d && process.env.NODE_ENV === "development" ? f(r, n) : r;
}, O = (r, n = !1) => {
  const d = {
    countOnChangeFiltersApplied: 0,
    appliedFilters: [],
    availableFields: [],
    // fnAnchorEl: undefined,
    popoverFilterData: void 0,
    inputData: "",
    ...r
  };
  let a = null;
  return u(
    v(
      s((l, o) => ({
        ...d,
        actions: {
          /**
           * init: Inicializa el store, se debe llamar al iniciar el componente
           */
          init: (i) => {
            l((e) => {
              e.appliedFilters = c(
                e.fields,
                i,
                e.actions.getFieldByName
              ), e.ownerState.isEmpty = e.appliedFilters.length <= 0, p(e);
            });
          },
          /**
           *  Actualiza la referencia del elemento (inputFilter) desde donde se desprende el listado de campos
           */
          setElementRef: (i) => {
            a = i;
          },
          getElementRef: () => a,
          /**
           * Actualiza el listado de campos disponibles para filtrar
           */
          getFieldByName: (i) => {
            const e = (o().withAllField ? o().fields.concat(o().allField) : o().fields).find((t) => t.name === i);
            if (e)
              return e;
            throw new Error("No exist field");
          },
          /**
           * Elimina un campo filter por su id
           */
          removeFilter: (i) => {
            l((e) => {
              const t = e.appliedFilters.findIndex((F) => i === F.id && !F.fixed);
              t > -1 && (e.automatic || (e.ownerState.isDirty = !0), e.appliedFilters.splice(t, 1), e.ownerState.isEmpty = e.appliedFilters.length === 0, p(e), e.appliedFilters.length === 0 && (e.ownerState.isDirty = !1));
            });
          },
          /**
           * muestra el popover para agregar un nuevo filtro
           */
          showPopoverFilterForAdd: (i) => {
            l((e) => {
              e.inputData = "", e.popoverFilterData = {
                openFor: "add",
                field: i
              }, e.isOpenPopoverMenuFields = !1, e.ownerState.inEdition = !0;
            });
          },
          /**
           * muestra el popover para editar un filtro
           */
          showPopoverFilterForEdit: (i) => {
            l((e) => {
              e.popoverFilterData = {
                openFor: "edit",
                filter: i,
                field: i.field
              };
            }), o().actions.setInEdition(!0);
          },
          /**
           * oculta el popover de filtros
           */
          hidePopoverFilter: (i) => {
            l((e) => {
              e.popoverFilterData = void 0;
            }), o().actions.setInEdition(i);
          },
          /**
           * Limpia todos los filters aplicados
           */
          clearFilters: () => {
            l((i) => {
              i.appliedFilters = i.appliedFilters.filter((e) => e.fixed), i.ownerState.isEmpty = i.appliedFilters.length === 0, i.popoverFilterData = void 0, i.ownerState.inEdition = !1, i.ownerState.isDirty = !1, i.automatic || (i.ownerState.isDirty = !0), p(i);
            });
          },
          /**
           * Acción que se ejecuta al aplicar los filtros
           */
          fireOnChangeFilters: () => {
            l((i) => {
              i.ownerState?.isValid && (i.ownerState.isDirty = !1, i.countOnChangeFiltersApplied++);
            });
          },
          /**
           * obtiene el id del nuevo filtro
           */
          getNewId: () => o().appliedFilters.reduce((i, e) => e.id > i ? e.id : i, 0) + 1,
          /**
           * agrega un nuevo filtro
           */
          addFilter: (i) => {
            l((e) => {
              e.automatic || (e.ownerState.isDirty = !0), e.appliedFilters.push(i), e.ownerState.isEmpty = e.appliedFilters.length === 0, p(e);
            });
          },
          /**
           * actualiza un filtro
           */
          updateFilter: (i) => {
            l((e) => {
              const t = e.appliedFilters.findIndex(
                (F) => F.id === i.id
              );
              t > -1 && (e.appliedFilters[t] = i), e.automatic || (e.ownerState.isDirty = !0), p(e);
            });
          },
          /**
           * actualiza el inputData
           */
          setInputData: (i) => {
            l((e) => {
              e.inputData = i;
            });
          },
          /**
           * actualiza el editor de filtros
           */
          setInEdition: (i) => {
            l((e) => {
              e.ownerState.inEdition = i;
            });
          },
          /**
           * actualiza el estado externo del componente
           */
          setExternalState: (i) => {
            l((e) => {
              e.ownerState = { ...e.ownerState, ...i };
            });
          },
          /**
           * abre el popover para seleccionar los campos a filtrar
           */
          openPopoverMenuFields: () => {
            l((i) => {
              i.isOpenPopoverMenuFields = !0, i.ownerState.inEdition = !0;
            });
          },
          /**
           * cierra el popover para seleccionar los campos a filtrar
           */
          closePopoverMenuFields: (i) => {
            l((e) => {
              e.isOpenPopoverMenuFields = !1, e.ownerState.inEdition = i || !1;
            });
          },
          /**
           * actualiza el tamaño del componente
           */
          setSize: (i) => {
            l((e) => {
              e.size = i, e.ownerState.size = i;
            });
          },
          /**
           * actualiza el visibleRefresh del componente
           */
          setVisibleRefresh: (i) => {
            l((e) => {
              e.visibleRefresh = i;
            });
          }
        }
      })),
      { name: `${m}: ${r.storeId}`, enabled: n }
    )
  );
};
export {
  O as createDynamicFilterStore
};
