import { IncomingMessage, ServerResponse } from 'http';

type ProxyConfig = {
    address: string | Array<string>;
    secret: string;
};
type ProxyId = string;
type KnownProxies = Record<ProxyId, ProxyConfig>;
type TrustProxyFunction = (proxyAddr: string, idx: number) => boolean;
declare const X_PROXY_ID_HEADER: "x-proxy-id";
declare const X_PROXY_IP_HEADER: "x-proxy-ip";
declare const X_PROXY_TIMESTAMP_HEADER: "x-proxy-timestamp";
declare const X_PROXY_SIGNATURE_HEADER: "x-proxy-signature";
type ProxyHeaders = {
    [X_PROXY_ID_HEADER]: string;
    [X_PROXY_IP_HEADER]: string;
    [X_PROXY_TIMESTAMP_HEADER]: string;
    [X_PROXY_SIGNATURE_HEADER]: string;
};
declare function getRequestIp(req: IncomingMessage, trustProxyFn: TrustProxyFunction, knownProxies?: KnownProxies): string;
declare function getProxyHeadersForIp(method: string, url: string, ip: string, proxyId: string, secret: string): ProxyHeaders;

type IpProxyingOptions = {
    /** ID of the proxy to pass as x-proxy-id header */
    proxyId: string;
    /** secret to sign x-proxy-signature header */
    proxySecret: string;
    /** List of known proxies before current one from which IP can be extracted */
    knownProxies?: KnownProxies;
    /**
     * Function to determine if a given IP address should be as x-forwarded-for header source.
     * Defaults to () => false, which means all IP addresses are trusted
     * */
    trustProxyFn?: TrustProxyFunction;
};
type LoggerType = {
    error: (data: unknown) => void;
};
type RelativeOrAbsoluteEndpoint = string;
type ProxyOptions = {
    /** Name of the proxy. Primarily used to set "via" header */
    name: string;
    /** Proxy prefix which will be removed from request url  */
    proxyPrefix: string;
    /** Upstream host to proxy requests to */
    upstreamOrigin: string;
    /** Upstream prefix to add to request url */
    upstreamPrefix: string;
    /** IP proxying options, if specified, IP will be passed used signed x-proxy-id, x-proxy-ip, x-proxy-timestamp, x-proxy-signature headers */
    ipProxying?: IpProxyingOptions;
    /**
     * Map of location header rewrites for redirects.
     * Key: upstream location, Value: rewritten location for client.
     * Used to rewrite Location headers in 3xx redirect responses.
     */
    locationRewrites?: Record<RelativeOrAbsoluteEndpoint, RelativeOrAbsoluteEndpoint>;
    /**
     * Map of cookie path rewrites for Set-Cookie headers.
     * Key: upstream cookie path, Value: rewritten path for client.
     * Used to adjust cookie scope when proxying between different path prefixes.
     */
    cookiePathRewrites?: Record<RelativeOrAbsoluteEndpoint, RelativeOrAbsoluteEndpoint>;
    /**
     * Logger instance for error reporting. Defaults to console if not provided.
     * Must implement an error method that accepts any data type.
     */
    logger?: LoggerType;
};
type ProxyHandler = (req: IncomingMessage, res: ServerResponse) => void;
declare function createProxy(options: ProxyOptions): ProxyHandler;

export { type KnownProxies, type ProxyHeaders, type TrustProxyFunction, createProxy, getProxyHeadersForIp, getRequestIp };
