import { DataResult, State, CompositeFilterDescriptor, SortDescriptor, FilterDescriptor } from '@progress/kendo-data-query';
import { IdType } from 'imng-nrsrx-client-utils';
import * as rxjs from 'rxjs';
import { Observable } from 'rxjs';
import * as i0 from '@angular/core';
import { ModuleWithProviders } from '@angular/core';
import * as i1 from '@angular/common';

interface ODataResult<T extends {
    id?: IdType;
} | unknown> extends DataResult {
    data: Array<T>;
    total: number;
}
declare const emptyODataResult: ODataResult<unknown>;
declare function createEmptyODataResult<T extends {
    id?: IdType;
} | unknown>(): ODataResult<T>;
declare function createODataResult<T extends {
    id?: IdType;
} | unknown>(t: T[]): ODataResult<T>;
declare function isODataResult<T extends {
    id?: IdType;
} | unknown>(source: unknown): source is ODataResult<T>;

interface ODataPayload<T> {
    '@odata.context'?: string;
    '@odata.count'?: number;
    value: T[];
}
declare function createODataPayload<T>(resultSet: T[]): ODataPayload<T>;

interface ODataState extends State {
    expanders?: Array<Expander>;
    selectors?: string[];
    inFilters?: InFilter[];
    notInFilters?: InFilter[];
    childFilters?: CompositeChildFilterDescriptor;
    count?: boolean;
    transformations?: string;
    compute?: Array<Computation | string>;
}
interface Computation {
    /** This can also be a static value */
    fieldA: string | number;
    /** This can also be a static value */
    fieldB: string | number;
    operator: 'mul' | 'div' | 'add' | 'sub' | 'mod' | string;
    /** This MUST differ from the names of declared or dynamic properties of the identified resources. */
    alias: string;
}
interface InFilter {
    /** This value will default to 'and' in cases where there are additional filters specified. */
    logic?: 'or' | 'and';
    field: string;
    values: IdType[];
}
interface CompositeChildFilterDescriptor {
    /**
     * The logical operation to use when the `filter.filters` option is set.
     *
     * The supported values are:
     * * `"and"`
     * * `"or"`
     */
    logic: 'or' | 'and';
    /**
     *
     */
    filters?: Array<CompositeChildFilterDescriptor | ChildFilterDescriptor>;
    existsFilters?: Array<ChildExistsFilterDescriptor>;
}
/** This is used to filter records that have child records that exists or match a filter.
 *  @See {@link https://docs.oasis-open.org/odata/odata/v4.0/errata03/os/complete/part2-url-conventions/odata-v4.0-errata03-os-part2-url-conventions-complete.html#_Toc371341806}
 */
interface ChildExistsFilterDescriptor {
    /**  This should be the child table navigation property */
    childTableNavigationProperty: string;
    /** Filter expression to be used, this can be undefined
     * Example: 'childRecord:childRecord/Quantity gt 100'
     */
    filter?: string;
    /**
     * This should be 'any' or 'all' for child table navigation properties.
     * 'all' will return records if all child records match the filter.
     * 'any' will return records if any child record matches the filter.
     * @default 'any'
     * @note If 'all' is used a filter expression must be provided.
     */
    linqOperation?: 'all' | 'any';
}
interface ChildFilterDescriptor extends FilterDescriptor {
    /**  This should be the child table navigation property */
    childTableNavigationProperty: string;
    /**
     * This should be 'any' or 'all' for child table navigation properties.
     * If this is not specified, it will default to 'any'.
     * 'all' will return records if all child records match the filter.
     * 'any' will return records if any child record matches the filter.
     */
    linqOperation: 'all' | 'any';
}
interface Expander {
    table: string;
    selectors?: string[];
    expanders?: Array<Expander | string>;
    filter?: CompositeFilterDescriptor;
    sort?: Array<SortDescriptor>;
    count?: boolean;
}
declare function isExpander(source: string | Expander): source is Expander;
declare function isComputation(source: string | Computation): source is Computation;

interface FetchOptions {
    /**
     * Collection of child table properties that are rendered on a grid
     * This is important because the OOB kendo will not query child tables correctly
     */
    boundChildTableProperties?: BoundChildTableProperty[];
    /**
     * Collection of property names that are of type: nullable Date
     */
    dateNullableProps?: string[];
    /**
     * Collection of property names that are of type: nullable UTC DateTime
     *    Note: these properties will be converted to local date time
     */
    utcNullableProps?: string[];
    /**
     * Set to true to force request via cache-busting.
     * Default: false;
     */
    bustCache?: boolean;
    /**
     * Additional parameters to be added to the request.
     * This is useful for passing additional query parameters that are not part of the OData state.
     */
    additionalParams?: Record<string, string>;
}
interface BoundChildTableProperty {
    /**
     * This is the child table name
     */
    table: string;
    /**
     * This is the field name on the child table that is bound
     */
    field: string;
    /**
     * This controls if 'all' child records have to meet the the conditions
     * or if 'any' of the child records have to meet the condition.
     * Default: 'any'
     */
    linqOperation?: 'all' | 'any';
}

declare class ODataService {
    private readonly http;
    fetch<T extends object>(odataEndpoint: string, state: ODataState, options?: FetchOptions): Observable<ODataResult<T>>;
    getAdditionalParams(options: FetchOptions): string;
    fetchByPrimaryKey<T extends object>(odataEndpoint: string, id: string, state?: ODataState): Observable<T>;
    getODataString(state: ODataState): string;
    applyTransformations(state: ODataState, queryString: string): string;
    processDates(queryString: string): string;
    processGuids(queryString: string): string;
    processSelectors(state: ODataState, queryString: string): string;
    processExpanders(state: ODataState, queryString: string): string;
    getExpansionString(element: string | Expander): string;
    processInFilters(inFilters: InFilter[] | undefined, queryString: string, isNotIn: boolean): string;
    processComputations(state: ODataState, queryString: string): string;
    static ɵfac: i0.ɵɵFactoryDeclaration<ODataService, never>;
    static ɵprov: i0.ɵɵInjectableDeclaration<ODataService>;
}

declare class ImngKendoODataModule {
    static forRoot(): ModuleWithProviders<ImngKendoODataModule>;
    static ɵfac: i0.ɵɵFactoryDeclaration<ImngKendoODataModule, never>;
    static ɵmod: i0.ɵɵNgModuleDeclaration<ImngKendoODataModule, never, [typeof i1.CommonModule], never>;
    static ɵinj: i0.ɵɵInjectorDeclaration<ImngKendoODataModule>;
}

declare const mapToExtDataResult: <T extends object>(utcNullableProps?: string[], dateNullableProps?: string[]) => rxjs.OperatorFunction<ODataPayload<T> | T[], {
    data: T[];
    total: number;
}>;
declare const firstRecord: <T>() => rxjs.OperatorFunction<ODataResult<T>, T>;
declare const findById: <T extends {
    id?: IdType;
}>(id?: IdType, defaultValue?: T) => rxjs.OperatorFunction<ODataResult<T>, T>;
declare function parseDatesInCollection<T extends object>(collection: Array<T>, utcNullableProps?: string[], dateNullableProps?: string[]): Array<T>;
declare function toLocalDate(date: string): Date;
declare function getSubGridData<PARENT_ENTITY extends {
    id?: IdType;
}, SUB_ENTITY>(id: IdType | undefined, mappingFunction: (entity: PARENT_ENTITY) => SUB_ENTITY[]): (source: Observable<ODataResult<PARENT_ENTITY>>) => Observable<SUB_ENTITY[]>;
declare function getSubData<PARENT_ENTITY extends {
    id?: IdType;
}, SUB_ENTITY>(id: IdType | undefined, mappingFunction: (entity: PARENT_ENTITY) => SUB_ENTITY[]): (source: Observable<Array<PARENT_ENTITY>>) => Observable<SUB_ENTITY[]>;

declare function translateChildFilterExpression(odataState: ODataState, childTableProperty: BoundChildTableProperty): ODataState;

declare function translateChildSortingExpression(odataState: ODataState, childTableProperties: BoundChildTableProperty[] | undefined): ODataState;

declare function isCompositeChildFilterDescriptor(source: CompositeChildFilterDescriptor | ChildFilterDescriptor): source is CompositeChildFilterDescriptor;

declare function isFilterDescriptor(source: CompositeFilterDescriptor | FilterDescriptor | ChildFilterDescriptor): source is FilterDescriptor;

declare function findMatchingFilters(odataState: ODataState, filterField: string): FilterDescriptor | undefined;
declare function flattenCompositeFilters(filters: CompositeFilterDescriptor): FilterDescriptor[];

declare function removeMatchingFilters(odataState: ODataState, filterField: string): ODataState;
declare function filterFilters(filters: (FilterDescriptor | CompositeFilterDescriptor)[] | CompositeFilterDescriptor, filterField: string): (CompositeFilterDescriptor | FilterDescriptor)[];

declare function applyFilter(odataState: ODataState, filter: FilterDescriptor): ODataState;

declare function updateFilter(compositefilter: CompositeFilterDescriptor, newFilter: FilterDescriptor): CompositeFilterDescriptor;

export { ImngKendoODataModule, ODataService, applyFilter, createEmptyODataResult, createODataPayload, createODataResult, emptyODataResult, filterFilters, findById, findMatchingFilters, firstRecord, flattenCompositeFilters, getSubData, getSubGridData, isCompositeChildFilterDescriptor, isComputation, isExpander, isFilterDescriptor, isODataResult, mapToExtDataResult, parseDatesInCollection, removeMatchingFilters, toLocalDate, translateChildFilterExpression, translateChildSortingExpression, updateFilter };
export type { BoundChildTableProperty, ChildExistsFilterDescriptor, ChildFilterDescriptor, CompositeChildFilterDescriptor, Computation, Expander, FetchOptions, InFilter, ODataPayload, ODataResult, ODataState };
