/**
 * Runtime detection + picker + credential-script builder for `agents run --lease`.
 *
 * The picker asks which coding-agent runtime(s) to provision on a leased box.
 * The default selection is whatever the user is currently signed into locally
 * (via `getAccountInfo`, the same source `agents view` uses). The chosen runtimes
 * drive both what gets installed on the box and which auth token file is copied
 * over — the token contents ride the uploaded `--script-stdin` body, never argv.
 *
 * SECURITY: copying a runtime's auth token to an ephemeral cloud box is a
 * credential transfer. It is strictly opt-in (a confirm prompt in the command
 * layer), the token never appears in argv/`ps`, and `--lease` one-shot runs tear
 * the box down afterward so the credential's lifetime is bounded by the run.
 */
import type { AgentId } from '../types.js';
/**
 * Credential file locations per runtime. `localCandidates` are read in order
 * (first existing wins); `remote` is where the box's CLI reads it by default
 * (home-level — no per-version shim). Source of truth for these paths is
 * `getAccountInfo` in src/lib/agents.ts; keep them in sync.
 */
interface RuntimeCred {
    id: AgentId;
    label: string;
    localCandidates: string[];
    remote: string;
}
export declare const LEASE_RUNTIMES: RuntimeCred[];
/** True when `id` is a native OAuth / session login that MUST NOT be copied between devices (SING-1b). */
export declare function isNativeOAuthRuntime(id: AgentId): boolean;
/** The fail-loud message naming the forbidden runtimes and the portable path to use instead. */
export declare function nativeOAuthTransferRefusal(nativeRuntimes: AgentId[]): string;
export interface DetectedRuntime {
    id: AgentId;
    label: string;
    email: string | null;
    signedIn: boolean;
    /** Absolute local path of the credential file, if found. */
    credPath: string | null;
}
/** Which lease-capable runtimes the user is signed into on this machine. */
export declare function detectSignedInRuntimes(): Promise<DetectedRuntime[]>;
/**
 * Interactive checkbox: which runtimes to provision on the box. Defaults to the
 * signed-in ones. Runtimes with no local credential are shown disabled.
 * `prompt` is injected so tests don't require a TTY.
 */
export declare function pickRuntimes(detected: DetectedRuntime[], prompt?: (choices: {
    name: string;
    value: AgentId;
    checked: boolean;
    disabled: boolean | string;
}[]) => Promise<AgentId[]>): Promise<AgentId[]>;
/**
 * The lease runtime to provision for a headless run of `agentName`.
 *
 * When the agent is itself a lease-capable runtime (claude/codex/gemini/grok)
 * that IS the runtime to install. Otherwise fall back to the single signed-in
 * lease runtime (preferring claude), or null when none is signed in. This is the
 * non-interactive replacement for the runtime checkbox picker: `--lease` requires
 * a prompt, so it is headless by contract and must never block on a TTY.
 *
 * Profile-dispatch agents (kimi/deepseek) and custom workflow agents that run
 * under a non-obvious runtime are resolved separately — see RUSH-1725.
 */
export declare function inferLeaseRuntime(agentName: string, detected: DetectedRuntime[]): AgentId | null;
/** True when a profile already carries auth for its host runtime via env. */
export declare function profileNeedsBaseRuntimeCredentials(agent: AgentId, env: Record<string, string>, authEnvVar?: string): boolean;
/** Build a quoted heredoc write to a path under the remote user's home. */
export declare function buildHomeFileWriteScript(remote: string, contents: string): string;
/**
 * Where Claude Code reads its OAuth token on the box. `.claude.json` (the file
 * LEASE_RUNTIMES copies) is config/account-metadata ONLY — the actual token
 * lives here, so without it the box boots "Not logged in".
 */
export declare const CLAUDE_TOKEN_REMOTE = ".claude/.credentials.json";
/**
 * The RAW wrapped Claude credential payload (`{"claudeAiOauth":{…}}`) to write to
 * the box's `~/.claude/.credentials.json`, or null if no signed-in token is found.
 *
 * On macOS the token is in the login Keychain, read SILENTLY via
 * `getKeychainToken` (the `/usr/bin/security … -w` path — Claude's item trusts it,
 * no Touch ID). A default native install uses the bare `Claude Code-credentials`
 * service; an agents-cli managed install (where `~/.claude` symlinks into a
 * versioned home) uses a hash-suffixed service, so we try the bare service first,
 * then enumerate installed version homes (preferring the account whose email
 * matches `preferEmail`, so the token matches the `.claude.json` config we copy).
 * Off macOS the local Claude CLI stores the wrapped rotating blob in
 * `.credentials.json` already. Read that file here with a shape check
 * (`claudeAiOauth.accessToken`). Do not reintroduce a shared helper that
 * also serves Rush Cloud dispatch — dispatch is email-only (SING-1b) and
 * the old `readClaudeCredentialsBlob` path was the #1767 TTY-banner leak
 * (RUSH-2359).
 *
 * The reader/service/version helpers are injected so unit tests never touch the
 * real Keychain.
 */
export declare function resolveClaudeCredentialsBlob(opts?: {
    preferEmail?: string | null;
    readItem?: (service: string) => string;
    service?: (home?: string) => string;
    listVersions?: () => string[];
    versionHome?: (version: string) => string;
    accountEmail?: (home: string) => Promise<string | null>;
}): Promise<string | null>;
/**
 * The credential-provisioning snippet for a `--lease` box.
 *
 * Every runtime this could serialize is a native OAuth / session login
 * (`LEASE_RUNTIMES`), and SING-1b forbids copying one to another device —
 * including an ephemeral leased box, whose refresh of a shared rotating token
 * invalidates every other holder. So this no longer writes a login: it REFUSES
 * (throws, steering to the portable `agents accounts` path) whenever a picked
 * runtime actually has a native credential to copy — signed in locally
 * (`credPath`), or a Claude OAuth blob supplied. A picked runtime with nothing to
 * copy is simply skipped, so `buildCredentialScript` returns `''` (a no-op box
 * bootstrap) rather than throwing on a not-signed-in runtime.
 */
/**
 * The native OAuth runtimes among `picked` that actually have a credential to copy
 * — signed in locally (`credPath`) or a Claude OAuth blob supplied — i.e. the ones
 * a transfer would leak. A picked runtime with nothing to copy is not refused.
 */
export declare function refusedNativeOAuthRuntimes(picked: AgentId[], detected: DetectedRuntime[], extras?: {
    claudeCredentialsJson?: string | null;
}): AgentId[];
/**
 * Throw the SING-1b refusal if any picked runtime would transfer a native OAuth
 * login. Callers should invoke this at a FAIL-FAST point — before any expensive or
 * costly side effect (e.g. before `crabboxWarmup` leases a paid box) — so a refused
 * `--lease` never leaks infra, mirroring how `--copy-creds` refuses before it opens
 * an SSH connection.
 */
export declare function assertNoNativeOAuthTransfer(picked: AgentId[], detected: DetectedRuntime[], extras?: {
    claudeCredentialsJson?: string | null;
}): void;
export declare function buildCredentialScript(picked: AgentId[], detected: DetectedRuntime[], extras?: {
    claudeCredentialsJson?: string | null;
}): string;
export {};
