import { CollectionEvents, ComputedQuery, ComputedQueryFull, DataResultKeyed, DataResultRaw, Filter, FiltersKey, FiltersMap, Fqdn, KeyedItem, OnResultUpdated, PatternsErrorHandler, QueryOptions, QueryResultStatus, ShowToast, SortOrder } from '../model';
import { Query as ReactQuery, QueryCache, QueryClient, QueryObserver } from 'react-query/core';
import { History } from 'history';
import { QueryState } from './QueryState';
import { QueryResultState } from './QueryResultState';
import { BulkSelectState } from './BulkSelectState';
import { PromisesState } from './PromisesState';
import { PaginationMode, PaginationModeRef } from './PaginationMode';
import { TaskState } from './TaskState';
import { ErrorMonitor, ExtendedFields, PartialLodash, Translate } from '../services';
import { TypedEmitter } from '../util';
import { OnlineState } from './OnlineState';
import { TransitionState } from './TransitionState';
import { Sortable } from './SortState';
import { CollectionOptimisticActions } from './CollectionOptimisticActions';
type Query<T> = Omit<ReactQuery<DataResultKeyed<T>>, 'promise' | 'dispatch'> & {
    promise?: Promise<unknown>;
    dispatch: (action: {
        type: string;
        error: unknown;
    }) => void;
};
export interface CollectionStateEvents<T, F extends FiltersMap> {
    triggerReachBottomListener: () => unknown;
    beforeAddNewPages: (params: {
        pages: T[][];
        currentItemsMap: Map<string, KeyedItem<T>>;
        originQuery: ComputedQueryFull<F>;
    }) => T[][];
    beforeSetTotal: (params: {
        total: number;
        originQuery: ComputedQuery<F>;
    }) => number;
    resultUpdated: () => unknown;
    beforeResultUpdated: () => unknown;
    ready: () => unknown;
    collectionLayout: () => unknown;
    fetch: (params: {
        isStale: boolean;
    }) => void | undefined | (() => unknown);
    refresh: (params: {
        isStale: boolean;
    }) => unknown;
    refreshCurrentPage: () => unknown;
    refreshAllPages: () => unknown;
    refreshUpdateResult: () => unknown;
    searchStart: () => () => unknown;
    search: (params: {
        clearResult?: boolean;
    }) => unknown;
    clearSearch: () => unknown;
    newPageStart: () => (params: {
        totalNewItems: number;
        newPages: DataResultKeyed<T>[];
    }) => unknown;
    beforeSortStart: (params: {
        origin?: 'SidePanel' | 'ColumnHeader';
    }) => unknown;
    sortStart: (params: {
        col: {
            id: string;
        };
    }) => unknown;
    sort: (params: {
        clearResult?: boolean;
    }) => unknown;
    beforeClearFilters: (params: {
        origin: string;
    }) => unknown;
}
/**
 * Hooks for extending or customizing the lifecycle of a collection state.
 *
 * Unlike regular events (which are fire-and-forget), hooks can return a value
 * that is consumed by the process they are part of. This allows business logic
 * to influence behavior at specific points in the flow.
 */
export interface CollectionStateHooks {
    beforeInitialFetch: (params: {
        isStale: boolean;
    }) => unknown | Promise<unknown>;
}
interface ScrollableContent {
    getBoundingClientRect: () => DOMRect;
    scrollTo: (options: ScrollToOptions) => void;
    scrollTop: number;
}
export interface CollectionStateParams<T, F extends FiltersMap> {
    readonly queryCache: QueryCache;
    readonly queryName: string;
    readonly fqdn?: Fqdn;
    readonly filters: F;
    readonly search?: Filter<string>;
    readonly errorMonitor: ErrorMonitor;
    readonly errorHandler: PatternsErrorHandler | undefined;
    readonly onlineState: OnlineState;
    readonly history: History;
    readonly showToast?: ShowToast;
    readonly translate: Translate;
    readonly itemKey: (item: T) => string;
    readonly toExtendedFields?: (item: T) => ExtendedFields | undefined | null;
    readonly initDependencies?: () => Promise<unknown>;
    readonly fetchData: (query: ComputedQuery<F>) => Promise<DataResultRaw<T>>;
    readonly fetchTotal?: (query: ComputedQuery<F>) => Promise<number>;
    readonly fetchErrorMessage?: (params: {
        err: unknown;
        isOnline: boolean;
    }) => string | null | undefined;
    readonly itemName: (item: T) => string;
    readonly deferInitialLoading?: boolean;
    readonly events?: CollectionEvents<F>;
    readonly persistQueryToUrl?: boolean;
    readonly refreshOnColumnsChange?: boolean;
    readonly limit?: number;
    readonly initialPage?: DataResultRaw<T>;
    readonly queryOptions?: QueryOptions;
    readonly paginationMode?: 'cursor' | 'offset';
    readonly paginationModeRef?: PaginationModeRef;
    readonly selectionConsistencyMode?: 'preserve' | 'clear';
    readonly disableAutoSelectAllCount?: boolean;
    readonly useNewSelectAllLogic?: boolean;
    readonly lodash: PartialLodash;
    readonly hooks?: TypedEmitter<CollectionStateHooks>;
}
export interface CollectionStatePublicAPI<T, F extends FiltersMap> {
    /**
     * Invalidates all cache records for this collection.<br>
     * Optional parameters:<br>
     *  `filters` - Clears only a specific part of the cache, for example: `invalidate({ filters: { status: ['active'] } })`
     *  @external
     */
    invalidate(params?: {
        filters?: {
            [P in keyof F]?: string[] | undefined | null;
        };
    }): void;
    /**
     * Invalidates cache and refreshes all previously fetched pages, without showing a loading indication.<br>
     * Optional parameters:<br>
     * - `beforeUpdateResult` - A callback function that will be called before updating the result.<br>
     * - `filters` - Invalidates only a specific part of the cache, for example: `refreshAllPages({ filters: { status: ['active'] } })`.
     * @external
     */
    refreshAllPages(params?: {
        beforeUpdateResult?: () => unknown;
        filters?: {
            [P in keyof F]?: string[] | undefined | null;
        };
    }): Promise<void>;
    /**
     * Invalidates cache and refreshes current page, without showing a loading indication.<br>
     * Optional parameters:<br>
     * - `noInvalidate` - Refreshes current page without invalidating cache.
     * @external
     */
    refreshCurrentPage(params?: {
        noInvalidate?: boolean;
    }): Promise<void>;
    /**
     * Clears all data from the collection and goes back to the first page and refreshes the first page data, while showing a loading indication.<br>
     * Optional parameters:<br>
     * - `force` - Invalidates the cache and resets react-query observer.
     * - `filters` - Clears only a specific part of the cache, for example: `invalidate({ filters: { status: ['active'] } })`
     * @external
     */
    clearResultAndMoveToStart(params?: {
        force?: boolean;
        filters?: {
            [P in keyof F]?: string[] | undefined | null;
        };
    }): Promise<void>;
    /**
     * Triggers retry when collection fails to load
     * @external
     */
    retryErrorState(): void;
    /**
     * [BulkSelectState](./?path=/story/common-state--bulkselectstate)
     * @external
     */
    bulkSelect: BulkSelectState<T>;
    /**
     * Reference to the search input element to allow programmatic focus
     */
    searchInputRef?: {
        focus: () => void;
    } | null;
    /**
     * [ComputedQuery](./?path=/story/common-types--computedquery) instance. Holds all the relevant variables to query the server API with.
     */
    originQuery: ComputedQueryFull<F>;
    /**
     * Status of the query. Contains boolean flags of `isIdle`, `isError`, `isLoading`, `isFetching`, `isSuccess`.
     * The difference between `isLoading` and `isFetching` is that `isLoading` is true during the initial query, `isFetching` is true during the next queries.
     *  @external
     */
    status: QueryResultStatus<DataResultKeyed<T>, unknown>;
    /**
     * The total number of items, as was returned from the last query.
     * @external
     */
    total: number;
    /**
     * All the keyed items of the collection
     * @external
     */
    keyedItems: KeyedItem<T>[];
    /**
     * Get an item object according to its key
     * @external
     * @param key The key of the wanted item
     * @returns The wanted item
     */
    getItem(key: string): T | undefined | null;
}
export declare class CollectionState<T, F extends FiltersMap = FiltersMap> implements CollectionStatePublicAPI<T, F> {
    readonly query: QueryState<F>;
    readonly _paginationModeRef: PaginationModeRef;
    private readonly _paginationMode;
    readonly selectionConsistencyMode: 'preserve' | 'clear';
    readonly result: QueryResultState<T, F>;
    readonly fetchesHistory: {
        itemsKeys: string[];
        queryPageInfo: {
            page: number;
            cursor: string | null | undefined;
            offset: number;
        };
    }[];
    readonly bulkSelect: BulkSelectState<T>;
    scrollableContent?: ScrollableContent | null;
    searchInputRef?: {
        focus: () => void;
    } | null;
    readonly errorMonitor: ErrorMonitor;
    readonly errorHandler: PatternsErrorHandler | undefined;
    readonly queryCache: QueryCache;
    readonly queryClient: QueryClient;
    readonly queryObserver: QueryObserver<DataResultKeyed<T>>;
    readonly queryName: string;
    readonly fqdn: Fqdn | undefined;
    readonly fetchErrorMessage: CollectionStateParams<T, F>['fetchErrorMessage'];
    readonly itemName: CollectionStateParams<T, F>['itemName'];
    readonly itemKey: CollectionStateParams<T, F>['itemKey'];
    readonly toExtendedFields?: ((item: T) => ExtendedFields | null | undefined) | undefined;
    readonly translate: Translate;
    readonly fetchData: CollectionStateParams<T, F>['fetchData'];
    readonly lodash: PartialLodash;
    readonly deferInitialLoading?: boolean;
    readonly persistQueryToUrl: boolean | undefined;
    _optimisticActions?: CollectionOptimisticActions<T, F>;
    beforeSetData?: () => void | Promise<unknown>;
    readonly showToast: ShowToast;
    readonly events: CollectionEvents<F>;
    readonly emitter: TypedEmitter<CollectionStateEvents<T, F>>;
    readonly hooks: TypedEmitter<CollectionStateHooks>;
    readonly onlineState: OnlineState;
    readonly history: History;
    readonly initDependencies?: () => Promise<unknown>;
    readonly initialPromises: PromisesState;
    readonly refreshPromises: PromisesState;
    readonly initTask: TaskState<unknown>;
    /**
     * Possible flows:
     * result->refresh, refresh->result, result->fetchMore, fetchMore->result, refresh->refresh, fetchMore->fetchMore
     */
    lifecycleState: 'result' | 'refresh' | 'fetchMore';
    _queryKey: (asComputed: ComputedQueryFull<F>) => readonly [string, {
        filtersKey: Partial<{ [P in keyof F]: string[] | null | undefined; }>;
        limit: number;
        offset: number;
        page: number;
        rawSearch: string;
        cursor?: string | null | undefined;
        sort?: {
            fieldName: string;
            order: "asc" | "desc";
        }[] | undefined;
        fields?: string[] | undefined;
        extra?: string | undefined;
    }];
    get queryKeyOptions(): {
        queryKey: readonly [string, {
            filtersKey: Partial<{ [P in keyof F]: string[] | null | undefined; }>;
            limit: number;
            offset: number;
            page: number;
            rawSearch: string;
            cursor?: string | null | undefined;
            sort?: {
                fieldName: string;
                order: "asc" | "desc";
            }[] | undefined;
            fields?: string[] | undefined;
            extra?: string | undefined;
        }];
    };
    get originQuery(): ComputedQueryFull<F>;
    get status(): QueryResultStatus<DataResultKeyed<T>, unknown>;
    isOnline(): boolean;
    get optimisticActions(): CollectionOptimisticActions<T, F>;
    constructor(params: CollectionStateParams<T, F>);
    _resetReactQuery(): void;
    _queryFn: (computedQuery: ComputedQuery<F>) => Promise<DataResultKeyed<T>>;
    scheduleSort: (...args: any[]) => void;
    private readonly scheduleSearch;
    readonly _runSearch: (clearResult?: boolean) => Promise<void>;
    readonly _runSort: ({ clearResult }: {
        clearResult?: boolean | undefined;
    }) => Promise<void>;
    setInitialPage(initialPage: DataResultRaw<T>): void;
    animationFramePromise: () => Promise<void>;
    onError: (err: unknown) => void;
    _currentQueryPromise?: Promise<void>;
    getCurrentQuery(): Query<T>;
    get paginationMode(): PaginationMode<T, F>;
    _getProcessedResult({ unprocessedPages, unprocessedTotal, currentItemsMap, }: {
        unprocessedPages: T[][];
        unprocessedTotal: number;
        currentItemsMap: Map<string, KeyedItem<T>>;
    }): {
        processedPages: T[][];
        processedTotal: number;
    };
    _getProcessedTotal(unprocessedTotal: number): number;
    _addToFetchesHistory(newPages: DataResultKeyed<T>[]): void;
    updateResult(queries: Query<T>[]): {
        newPages: DataResultKeyed<T>[];
    } | null;
    whenNotIdle(fn: (...args: any[]) => unknown): (...args: any[]) => void;
    updateStatus(): void;
    fetch(): {
        currentQuery: Query<T>;
        isStale: boolean;
        onResultListeners: (void | (() => unknown) | undefined)[];
        promise: Promise<void>;
    };
    get totalPages(): number;
    get total(): number;
    get totalStatus(): import("../model").QueryStatusValue;
    get fetchedLastPage(): boolean;
    private readonly fetchNextPage;
    fetchNextPageIfNeeded(): Promise<void>;
    clearAndMoveToPage(page: number, options?: {
        wait?: {
            min: number;
            max: number;
        };
    }): Promise<void>;
    clearResultBeforeRefresh(): void;
    moveToFirstPage({ onResultUpdated, }?: {
        onResultUpdated?: OnResultUpdated<F>;
    }): Promise<void>;
    invalidate({ filters }?: {
        filters?: FiltersKey<F>;
    }): void;
    clearResultAndMoveToStart({ onResultUpdated, force, filters, }?: {
        onResultUpdated?: OnResultUpdated<F>;
        force?: boolean;
        filters?: FiltersKey<F>;
    }): Promise<void>;
    sort(col: Sortable, { clearResult, multiple, forceDirection, }?: {
        clearResult?: boolean;
        multiple?: boolean;
        forceDirection?: SortOrder;
    }): void;
    fetchAndReplaceResult({ onResultUpdated, }?: {
        onResultUpdated?: OnResultUpdated<F>;
    }): Promise<Query<T>>;
    search(value: string, { force, clearResult }?: {
        force?: boolean;
        clearResult?: boolean;
    }): void;
    clearSearch(): Promise<void> | undefined;
    get filters(): import("../model").AllFilters<F>;
    changeItem(newItem: T): (() => boolean) | undefined;
    changeItems(newItems: T[]): (() => boolean) | undefined;
    addItem(newItem: T): () => void;
    addItems(newItems: T[]): () => void;
    refreshCurrentPage({ noInvalidate }?: {
        noInvalidate?: boolean;
    }): Promise<void>;
    refreshAllPages({ beforeUpdateResult, filters, }?: {
        beforeUpdateResult?: () => unknown;
        filters?: FiltersKey<F>;
    }): Promise<void>;
    get hasAvailableItems(): boolean;
    resetFiltersAndRefresh(): void;
    resetCustomFiltersAndRefresh(): void;
    initialFetch(): Promise<unknown>;
    _recoverIfError: () => void;
    onOnlineStateChange: (isOnline: boolean) => void;
    retryErrorState: () => void;
    init({ skipInitialFetch, skipFilterListeners, }?: {
        skipInitialFetch?: boolean;
        skipFilterListeners?: boolean;
    }): () => void;
    _registerQueryEvents(): () => void;
    getItem(key: string): T | undefined | null;
    getKeyedItem(key: string): KeyedItem<T> | undefined | null;
    getKeyedItemByIndex(index: number): KeyedItem<T> | null;
    get keyedItems(): KeyedItem<T>[];
    addRefreshPromise<P>(createPromise: () => Promise<P>): Promise<void>;
    _commonDynamicBiParams(query?: ComputedQueryFull<F>): {
        currentFilters?: string;
        currentSortOrder?: string;
        filteredListSize?: number;
        initialItems?: number;
        numSortedColumns?: number;
        csid?: string;
    };
    get showInitialLoader(): boolean;
    get showRefreshLoader(): boolean;
    get showEmptyState(): boolean;
    get showErrorState(): boolean;
    _topNotification: TransitionState<string | null>;
    get topNotification(): {
        text: string | null | undefined;
        readonly show: boolean;
    };
}
export {};
//# sourceMappingURL=CollectionState.d.ts.map