/**
 * ACP Agent Detector — scans PATH for installed ACP-compatible CLI agents.
 *
 * Uses `which` (Unix) / `where` (Windows) to locate CLI binaries,
 * then optionally probes version. Results are cached with TTL.
 *
 * Reference: AionUI AcpDetector + ACP_BACKENDS_ALL registry.
 */
import type { AcpBackendConfig, AgentDescriptor, AgentConfigStoreData } from "../../protocol/wire/acp-agent-management.js";
export declare const ACP_BACKENDS: Record<string, AcpBackendConfig>;
export declare const AGENT_CATALOG_IDS: readonly ["claude", "codex", "gemini", "copilot", "cursor", "qwen", "kimi", "glm", "opencode", "kiro", "qoder", "openclaw", "hermes"];
/** Merged catalog entry (base ACP config + grid/install metadata) for one id. */
export declare function getCatalogEntry(id: string): AcpBackendConfig | undefined;
/** Ordered curated catalog: base ACP config merged with grid/install metadata. */
export declare function getAgentCatalog(): AcpBackendConfig[];
export declare function resolveWindowsCopilotLoader(): string | null;
export declare function getNpmInstallPackageName(command: string | undefined): string | null;
export declare function compareSemverVersions(a: string, b: string): number;
export declare function isVersionNewer(latest: string | null | undefined, current: string | null | undefined): boolean;
export declare function readGlobalNpmPackageVersion(packageName: string | null | undefined): string | null;
export declare function fetchNpmLatestPackageVersion(packageName: string | null | undefined): string | null;
export declare function resolveInstalledNpmPackageVersionFromInstall(install: AcpBackendConfig["install"] | undefined): string | null;
export declare function getCatalogPackageVersionInfo(entry: AcpBackendConfig, detectedVersion?: string): {
    packageName?: string;
    installedVersion?: string;
    latestVersion?: string;
    updateAvailable: boolean;
};
export declare function normalizeWindowsAcpCommand(cliPath: string, args: string[]): {
    cliPath: string;
    acpArgs: string[];
};
/**
 * Build the spawn env for an external ACP backend.
 *
 * Maps the agent-config's portable `apiKey`/`baseUrl` onto the backend-declared
 * environment-variable names (`apiKeyEnvVar`/`baseUrlEnvVar`) so a user who only
 * configures an API key + base URL (e.g. via agents.setConfig) actually drives the
 * underlying CLI with a third-party OpenAI/Anthropic-compatible gateway — no official
 * account login required. Without this mapping the backends declared the env-var names
 * but nothing ever populated them.
 *
 * Precedence (lowest → highest), so explicit user input always wins:
 *   1. backend.env            (static backend defaults)
 *   2. mapped apiKey/baseUrl  (config.apiKey → backend.apiKeyEnvVar, etc.)
 *   3. customConfig.env       (raw env the user hand-entered)
 *
 * Injection is conditional: the apiKey/baseUrl mapping only fires when the backend
 * actually declares the corresponding envVar name (so we never invent a var the CLI
 * does not read). Returns undefined when there is nothing to inject, preserving the
 * prior `env?: undefined` behavior for un-configured backends.
 */
export declare function buildBackendEnv(backend: AcpBackendConfig | undefined, customConfig: import("../../protocol/wire/acp-agent-management.js").AgentConfig | undefined, autoEnv?: Record<string, string>): Record<string, string> | undefined;
/** Unified key sources for login-free catalog injection (wired by the runtime). */
export interface CatalogKeySources {
    /** Gateway-issued inference key (sk-qllm) for keySource:"llmrouter". */
    llmrouterKey?: string;
    /** Base URL an llmrouter-routed agent should call (our gateway endpoint). */
    llmrouterBaseUrl?: string;
    /** Resolve an agent/protocol-specific LLMRouter base URL. */
    getLlmrouterBaseUrl?: (agentId: string, entry: AcpBackendConfig) => string | null | undefined;
    /** Default LLMRouter model for agent CLIs that require an explicit model pin. */
    llmrouterModel?: string;
    /** Resolve a provider's direct third-party key for keySource:"direct". */
    getDirectKey?: (providerId: string) => string | null | undefined;
    /** The host's active text-generation model (deepseek / volcengine / …) to "pass through" to
     *  OpenAI-compatible spawned agents (codex/qwen/opencode) that resolve no key of their own — so
     *  they run on the configured key+baseUrl+model with zero per-agent credentials. */
    passthroughModel?: {
        apiKey: string;
        baseUrl?: string;
        model?: string;
    };
}
/**
 * Resolve the login-free key env for a catalog agent from the unified key sources.
 * "set key once in our system → all agents" — the user never logs into each CLI.
 *   - authMode "oauth" / keySource "none" → {} (no bypass; account required)
 *   - keySource "llmrouter" → gateway sk-qllm + gateway baseUrl (agent calls our gateway)
 *   - keySource "direct"    → the user's provider key (agent calls the provider directly)
 * Only emits env vars the backend actually declares (apiKeyEnvVar / baseUrlEnvVar).
 */
export declare function resolveCatalogKeyEnv(entry: AcpBackendConfig | undefined, sources: CatalogKeySources): Record<string, string>;
export declare class AcpDetector {
    private cache;
    private configStore;
    private keySources;
    /**
     * Provide the config store data so detector can populate `hasConfig` field
     * and include user-registered custom agents.
     */
    setConfigStore(data: AgentConfigStoreData): void;
    /** Wire the unified key sources for login-free catalog injection. */
    setKeySources(sources: CatalogKeySources): void;
    /**
     * Scan for installed ACP agent CLIs.
     * @param force - Clear cache and re-scan.
     */
    scan(force?: boolean): AgentDescriptor[];
    /** Return cached results without IO. */
    list(): AgentDescriptor[];
    /** Clear the detection cache. */
    clearCache(): void;
    private detectBackend;
    private detectCustomAgent;
    private hasAgentConfig;
    /**
     * Descriptor for qlogicagent participating in Solo/Product as a self-hosted ACP agent.
     *
     * qlogicagent's own CLI speaks ACP by default (cli/main.ts: ACP server unless --no-acp), so a
     * participant is just another `node <cli.js>` process. The child reads the SAME owner-profile
     * settings.json (model-registry), so it runs with the configured provider (deepseek / volcengine /
     * llmrouter) — that is how the configured model "passes through" to every qlogicagent instance,
     * with no per-agent key. We forward the owner-profile + llmrouter env so the child resolves its
     * model identically to this (host) process. This lets Solo run N independent qlogicagent sessions
     * in parallel (each its own worktree) — the core "多个 qlogicagent = 多会话并行" use case.
     */
    private buildSelfDescriptor;
    /**
     * Build an ExternalAgentDescriptor suitable for AgentProcessManager.spawn().
     * Returns null if the agent is not available.
     */
    buildExternalDescriptor(agentId: string): import("../../protocol/wire/acp-agent-management.js").ExternalAgentDescriptor | null;
    /**
     * Whether an agent is ready to compete in Solo/Product: installed/available AND configured.
     * qlogicagent self-resolves from the owner profile (always ready). External agents need a usable
     * ACP descriptor (installed) and, for key-auth backends, the key env resolved (configured by the
     * user on the welcome page). Used by the 启动 pre-check so a race never starts with an agent that
     * would fail its turn ("No LLM provider"/auth). Does NOT verify the key is *valid* — that's only
     * known at runtime.
     */
    isAgentReady(agentId: string): boolean;
}
