import { MatchStage, ProjectStage, SortStage, GroupStage, UnwindStage, AddFieldsStage, SetStage, UnsetStage, ReplaceRootStage, ReplaceWithStage, FacetStage, UnionWithStage, OutStage, MergeStage, PipelineStage } from './stages/index.mjs';

declare class AggregationBuilder<Models extends Record<string, any>, From extends keyof Models, Relations extends Partial<Record<keyof Models, readonly (keyof Models)[]>>> {
    private relations;
    private pipeline;
    constructor(relations: Relations);
    match(stage: MatchStage<Models[From]>['$match']): this;
    project(stage: ProjectStage<Models[From]>['$project']): this;
    sort(stage: SortStage<Models[From]>['$sort']): this;
    group(stage: GroupStage<Models[From]>['$group']): this;
    limit(count: number): this;
    skip(count: number): this;
    count(alias: string): this;
    unwind(field: UnwindStage['$unwind']): this;
    addFields(fields: AddFieldsStage<Models[From]>['$addFields']): this;
    set(fields: SetStage<Models[From]>['$set']): this;
    unset(fields: UnsetStage['$unset']): this;
    replaceRoot(stage: ReplaceRootStage<Models[From]>['$replaceRoot']): this;
    replaceWith(stage: ReplaceWithStage<Models[From]>['$replaceWith']): this;
    lookup<To extends (Relations[From] extends readonly (infer R)[] ? R : never) & keyof Models>(lookup: {
        from: To;
        localField: keyof Models[From];
        foreignField: keyof Models[To];
        as: string;
    }): this;
    facet(stage: FacetStage<Models[From], Models>['$facet']): this;
    unionWith(stage: UnionWithStage['$unionWith']): this;
    out(stage: OutStage['$out']): this;
    merge(stage: MergeStage['$merge']): this;
    build(): PipelineStage<Models[From], Models>[];
}

export { AggregationBuilder };
