import type { AbstractConstructor, Constructor, ExtractFunctions } from '@poppinss/utils/types';
import type { Make, Hooks, Swaps, Bindings, BindingKey, ErrorCreator, BindingValues, ContainerOptions, ContextualBindings } from './types.ts';
/**
 * Container resolver exposes the APIs to resolve bindings. You can think
 * of resolver as an isolated container instance, with only the APIs
 * to resolve bindings.
 *
 * ```ts
 * const container = new Container()
 * const resolver = container.createResolver()
 *
 * await resolver.make(BINDING_NAME)
 * await resolver.make(CLASS_CONSTRUCTOR)
 * ```
 */
export declare class ContainerResolver<KnownBindings extends Record<any, any>> {
    #private;
    /**
     * Initialize the container resolver with container bindings and options
     *
     * @param container - Object containing all container bindings, values, swaps, hooks, and aliases
     * @param options - Container configuration options
     */
    constructor(container: {
        bindings: Bindings;
        bindingValues: BindingValues;
        swaps: Swaps;
        hooks: Hooks;
        aliases: Map<Partial<keyof KnownBindings>, keyof KnownBindings | AbstractConstructor<any>>;
        contextualBindings: Map<Constructor<any>, ContextualBindings>;
    }, options: ContainerOptions);
    /**
     * Find if the resolver has a binding registered using the
     * "bind", the "singleton", or the "bindValue" methods.
     *
     * @param binding - The binding key to check for
     *
     * @example
     * ```ts
     * resolver.hasBinding('route')
     * resolver.hasBinding(Route)
     * ```
     */
    hasBinding<Binding extends keyof KnownBindings>(binding: Binding): boolean;
    hasBinding(binding: BindingKey): boolean;
    /**
     * Find if the resolver has all the bindings registered using the
     * "bind", the "singleton", or the "bindValue" methods.
     *
     * @param bindings - Array of binding keys to check for
     *
     * @example
     * ```ts
     * resolver.hasAllBindings(['route', 'encryption'])
     * resolver.hasAllBindings([Route, Encryption])
     * ```
     */
    hasAllBindings<Binding extends keyof KnownBindings>(bindings: Binding[]): boolean;
    hasAllBindings(bindings: BindingKey[]): boolean;
    /**
     * Resolves binding in context of a parent. The method is same as
     * the "make" method, but instead takes a parent class
     * constructor. This is used internally for dependency resolution.
     *
     * @param parent - The parent class requesting the binding
     * @param binding - The binding to resolve
     * @param runtimeValues - Optional runtime values for dependencies
     * @param createError - Error creator function
     *
     * @example
     * ```ts
     * const db = await resolver.resolveFor(UsersController, Database)
     * ```
     */
    resolveFor<Binding>(parent: unknown, binding: Binding, runtimeValues?: any[], createError?: ErrorCreator): Promise<Make<Binding>>;
    /**
     * Resolves the binding or constructor a class instance as follows.
     *
     * - Resolve the binding from the values (if registered)
     * - Resolve the binding from the bindings (if registered)
     * - If binding is a class, then create a instance of it. The constructor
     *   dependencies are further resolved as well.
     * - All other values are returned as it is.
     *
     * @param binding - The binding key or class constructor to resolve
     * @param runtimeValues - Optional runtime values for dependencies
     * @param createError - Error creator function
     *
     * @example
     * ```ts
     * await resolver.make('route')
     * await resolver.make(Database)
     * await resolver.make(UsersController, [request, response])
     * ```
     */
    make<Binding extends keyof KnownBindings>(binding: Binding, runtimeValues?: any[], createError?: ErrorCreator): Promise<Binding extends string | symbol ? KnownBindings[Binding] : Make<Binding>>;
    make<Binding>(binding: Binding, runtimeValues?: any[], createError?: ErrorCreator): Promise<Make<Binding>>;
    /**
     * Call a method on an object by injecting its dependencies. The method
     * dependencies are resolved in the same manner as a class constructor
     * dependencies.
     *
     * @param value - The object instance containing the method
     * @param method - The method name to call
     * @param runtimeValues - Optional runtime values for method dependencies
     * @param createError - Error creator function
     *
     * @example
     * ```ts
     * const controller = await resolver.make(UsersController)
     * await resolver.call(controller, 'index')
     * ```
     */
    call<Value extends Record<any, any>, Method extends ExtractFunctions<Value>>(value: Value, method: Method, runtimeValues?: any[], createError?: ErrorCreator): Promise<ReturnType<Value[Method]>>;
    /**
     * Register a binding as a value. Values bound to the resolver are
     * isolated from the container and only available within this resolver instance.
     *
     * @param binding - The binding key (string, symbol, or class constructor)
     * @param value - The pre-resolved value to bind
     *
     * @example
     * ```ts
     * const resolver = container.createResolver()
     * resolver.bindValue(HttpContext, ctx)
     * await resolver.make(UsersController) // Will receive the ctx
     * ```
     */
    bindValue<Binding extends keyof KnownBindings>(
    /**
     * Need to narrow down the "Binding" for the case where "KnownBindings" are <any, any>
     */
    binding: Binding extends string | symbol ? Binding : never, value: KnownBindings[Binding]): void;
    bindValue<Binding extends AbstractConstructor<any>>(binding: Binding, value: InstanceType<Binding>): void;
}
