import { ArrowFunctionExpr, ClassExpr, Expr, FunctionExpr, Identifier, ObjectLiteralExpr, OmittedExpr, PropName } from "./expression";
import { Integration } from "./integration";
import { BaseNode, FunctionlessNode } from "./node";
import { NodeKind } from "./node-kind";
import type { BlockStmt, CatchClause, ForInStmt, ForOfStmt, ForStmt, VariableStmt } from "./statement";
import { AnyClass, AnyFunction } from "./util";
export declare type Decl = BindingElem | ClassDecl | ClassMember | FunctionDecl | ParameterDecl | VariableDecl;
declare abstract class BaseDecl<Kind extends NodeKind, Parent extends FunctionlessNode | undefined = FunctionlessNode | undefined> extends BaseNode<Kind, Parent> {
    readonly nodeKind: "Decl";
}
export declare class ClassDecl<C extends AnyClass = AnyClass> extends BaseDecl<NodeKind.ClassDecl, undefined> {
    readonly name: string;
    readonly heritage: Expr | undefined;
    readonly members: ClassMember[];
    readonly _classBrand?: C;
    constructor(name: string, heritage: Expr | undefined, members: ClassMember[]);
}
export declare type ClassMember = ClassStaticBlockDecl | ConstructorDecl | GetAccessorDecl | MethodDecl | PropDecl | SetAccessorDecl;
export declare class ClassStaticBlockDecl extends BaseDecl<NodeKind.ClassStaticBlockDecl> {
    readonly block: BlockStmt;
    constructor(block: BlockStmt);
}
export declare class ConstructorDecl extends BaseDecl<NodeKind.ConstructorDecl> {
    readonly parameters: ParameterDecl[];
    readonly body: BlockStmt;
    constructor(parameters: ParameterDecl[], body: BlockStmt);
}
export declare class MethodDecl extends BaseDecl<NodeKind.MethodDecl> {
    readonly name: PropName;
    readonly parameters: ParameterDecl[];
    readonly body: BlockStmt;
    /**
     * true if this function has an `async` modifier
     * ```ts
     * class Foo {
     *   async foo() {}
     *
     *   // asterisk can co-exist
     *   async *foo() {}
     * }
     * ```
     */
    readonly isAsync: boolean;
    /**
     * true if this function has an `*` modifier
     *
     * ```ts
     * class Foo {
     *   foo*() {}
     *
     *   // async can co-exist
     *   async *foo() {}
     * }
     * ```
     */
    readonly isAsterisk: boolean;
    constructor(name: PropName, parameters: ParameterDecl[], body: BlockStmt, 
    /**
     * true if this function has an `async` modifier
     * ```ts
     * class Foo {
     *   async foo() {}
     *
     *   // asterisk can co-exist
     *   async *foo() {}
     * }
     * ```
     */
    isAsync: boolean, 
    /**
     * true if this function has an `*` modifier
     *
     * ```ts
     * class Foo {
     *   foo*() {}
     *
     *   // async can co-exist
     *   async *foo() {}
     * }
     * ```
     */
    isAsterisk: boolean);
}
export declare class PropDecl extends BaseDecl<NodeKind.PropDecl> {
    readonly name: PropName;
    readonly isStatic: boolean;
    readonly initializer?: Expr | undefined;
    constructor(name: PropName, isStatic: boolean, initializer?: Expr | undefined);
}
export declare class GetAccessorDecl extends BaseDecl<NodeKind.GetAccessorDecl, ClassDecl | ClassExpr | ObjectLiteralExpr> {
    readonly name: PropName;
    readonly body: BlockStmt;
    constructor(name: PropName, body: BlockStmt);
}
export declare class SetAccessorDecl extends BaseDecl<NodeKind.SetAccessorDecl, ClassDecl | ClassExpr | ObjectLiteralExpr> {
    readonly name: PropName;
    readonly parameter: ParameterDecl;
    readonly body: BlockStmt;
    constructor(name: PropName, parameter: ParameterDecl, body: BlockStmt);
}
export declare type FunctionLike<F extends AnyFunction = AnyFunction> = FunctionDecl<F> | FunctionExpr<F> | ArrowFunctionExpr<F>;
export declare class FunctionDecl<F extends AnyFunction = AnyFunction> extends BaseDecl<NodeKind.FunctionDecl> {
    readonly name: string | undefined;
    readonly parameters: ParameterDecl[];
    readonly body: BlockStmt;
    /**
     * true if this function has an `async` modifier
     * ```ts
     * async function foo() {}
     * // asterisk can co-exist
     * async function *foo() {}
     * ```
     */
    readonly isAsync: boolean;
    /**
     * true if this function has an `*` modifier
     *
     * ```ts
     * function foo*() {}
     *
     * // async can co-exist
     * async function *foo() {}
     * ```
     */
    readonly isAsterisk: boolean;
    readonly _functionBrand?: F;
    constructor(name: string | undefined, parameters: ParameterDecl[], body: BlockStmt, 
    /**
     * true if this function has an `async` modifier
     * ```ts
     * async function foo() {}
     * // asterisk can co-exist
     * async function *foo() {}
     * ```
     */
    isAsync: boolean, 
    /**
     * true if this function has an `*` modifier
     *
     * ```ts
     * function foo*() {}
     *
     * // async can co-exist
     * async function *foo() {}
     * ```
     */
    isAsterisk: boolean);
}
export interface IntegrationInvocation {
    integration: Integration<any>;
    args: Expr[];
}
export declare class ParameterDecl extends BaseDecl<NodeKind.ParameterDecl, ArrowFunctionExpr | FunctionDecl | FunctionExpr | SetAccessorDecl> {
    readonly name: BindingName;
    readonly initializer: Expr | undefined;
    /**
     * Whether this ParameterDecl is a rest parameter
     * ```ts
     * function foo(...rest) {}
     * ```
     */ readonly isRest: boolean;
    constructor(name: BindingName, initializer: Expr | undefined, 
    /**
     * Whether this ParameterDecl is a rest parameter
     * ```ts
     * function foo(...rest) {}
     * ```
     */ isRest: boolean);
}
export declare type BindingPattern = ObjectBinding | ArrayBinding;
export declare type BindingName = Identifier | BindingPattern;
/**
 * A binding element declares new variable or acts as the root to a nested {@link BindingPattern}
 * when destructuring an object or an array.
 *
 * @see https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Operators/Destructuring_assignment
 *
 * It represents a single named element in a {@link BindingPattern}.
 *
 * ```ts
 * const { a } = right;
 *      // ^ BindingElm
 * const [ a ] = right;
 *      // ^ BindingElm
 * ```
 *
 * * `a` - creates a variable called a with the value of the right side (`const a = right.a`).
 * * `a: b` - creates a variable called b with the value of the right side (`const b = right.a`).
 * * `a = "value"` - creates a variable called a with the value of the right side or "value" when the right side is undefined (`const a = right.a ?? "value"`)
 * * `a: { b }` - creates a variable called b with the value of the right side's a value. (`const b = right.a.b`)
 * * `...rest`- creates a variable called rest with all of the unused keys in the right side
 *
 * > Note: for {@link ArrayBinding}, the accessor will be a numeric index instead of a named property
 * > `const a = right[0]`
 *
 * Rest (`...rest`) example:
 *
 * ```ts
 * const val = { a: 1, b:2 };
 * const { a, ...rest } = val;
 *             // ^ { b: 2 }
 * ```
 */
export declare class BindingElem extends BaseDecl<NodeKind.BindingElem, BindingPattern> {
    readonly name: BindingName;
    readonly rest: boolean;
    readonly propertyName?: PropName | undefined;
    readonly initializer?: Expr | undefined;
    constructor(name: BindingName, rest: boolean, propertyName?: PropName | undefined, initializer?: Expr | undefined);
}
/**
 * Extract properties or sub-objects out of an object.
 *
 * @see https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Operators/Destructuring_assignment
 *
 * Container of {@link BindingElem}.
 *
 * ```ts
 * const { a: { b = "value" }, ...rest } = obj;
 * ```
 *
 * is the same as
 *
 * ```ts
 * const b = obj.a.b ?? "value"
 * const rest = { ...obj };
 * delete rest.a;
 * ```
 *
 * @see BindingElm for more details.
 */
export declare class ObjectBinding extends BaseNode<NodeKind.ObjectBinding, VariableDecl> {
    readonly bindings: BindingElem[];
    readonly nodeKind: "Node";
    constructor(bindings: BindingElem[]);
}
/**
 * Extract properties or sub-objects out of an array.
 *
 * @see https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Operators/Destructuring_assignment
 *
 * Container of {@link BindingElem}.
 *
 * ```ts
 * const [ a: [ b = "value" ], ...rest ] = arr;
 * ```
 *
 * is the same as
 *
 * ```ts
 * const b = arr[0][0] ?? "value";
 * const rest = arr.slice(1);
 * ```
 *
 * @see BindingElm for more details.
 */
export declare class ArrayBinding extends BaseNode<NodeKind.ArrayBinding, VariableDecl> {
    readonly bindings: (BindingElem | OmittedExpr)[];
    readonly nodeKind: "Node";
    constructor(bindings: (BindingElem | OmittedExpr)[]);
}
export declare type VariableDeclParent = CatchClause | ForInStmt | ForOfStmt | VariableDeclList;
export declare enum VariableDeclKind {
    Const = 0,
    Let = 1,
    Var = 2
}
export declare class VariableDecl<E extends Expr | undefined = Expr | undefined> extends BaseDecl<NodeKind.VariableDecl, VariableDeclParent> {
    readonly name: BindingName;
    readonly initializer: E;
    constructor(name: BindingName, initializer: E);
}
export declare type VariableDeclListParent = ForStmt | VariableStmt;
export declare class VariableDeclList extends BaseNode<NodeKind.VariableDeclList, VariableDeclListParent> {
    readonly decls: VariableDecl[];
    readonly varKind: VariableDeclKind;
    readonly nodeKind: "Node";
    constructor(decls: VariableDecl[], varKind: VariableDeclKind);
}
export declare const deploymentOnlyModule = true;
export {};
//# sourceMappingURL=declaration.d.ts.map