import {
  CollectionOptimisticActionsBaseParams,
  FiltersMap,
  OptionalFiltersMap,
} from '@wix/bex-core';
import {
  useWixPatternsContainer,
  CollectionConfigWithConditionals,
  useCreateCollection,
  useCreateOptimisticActions,
} from '@wix/bex-core/react';
import {
  EditableTableState,
  EditableTablePermissions,
  EditableTableMutationHandlers,
} from '../state/EditableTable';
import type { CellType } from '../state/EditableTable/types';
import type { FieldActions } from '../types/SchemaConfig';
import { useOptionalCachedState } from './useOptionalCachedState';

export type EditableTableCollectionConfig<
  T,
  F extends FiltersMap,
> = CollectionConfigWithConditionals<T, F> & {
  permissions?: EditableTablePermissions;
  mutations: EditableTableMutationHandlers<T>;
  fieldActions?: FieldActions;
  refresh?: () => Promise<void>;
  optimisticActionParams?: Partial<CollectionOptimisticActionsBaseParams<T, F>>;
  /**
   * Additional cell types to register alongside the built-in ones.
   * Augment `CellTypeConfigMap` to use these types on `EditableColumn.cellType`.
   */
  extraCellTypes?: CellType[];
};

type EditableTableCollection = <T, F extends FiltersMap = OptionalFiltersMap>(
  config: EditableTableCollectionConfig<T, F>,
) => EditableTableState<T, F>;

export const useEditableTableCollection: EditableTableCollection = <
  T,
  F extends FiltersMap = OptionalFiltersMap,
>(
  config: EditableTableCollectionConfig<T, F>,
): EditableTableState<T, F> => {
  const container = useWixPatternsContainer();
  const createCollection = useCreateCollection();
  const createOptimisticActions = useCreateOptimisticActions();

  const state = useOptionalCachedState(() => {
    return new EditableTableState<T, F>({
      collection: createCollection<T, F>(config),
      container,
      permissions: config.permissions,
      mutations: config.mutations,
      fieldActions: config.fieldActions,
      refresh: config.refresh,
      extraCellTypes: config.extraCellTypes,
      createOptimisticActions: (collection) =>
        createOptimisticActions(collection, config.optimisticActionParams),
    });
  });

  return state;
};
