import type { PlanContext } from "../internals/plan.js"; import { type Action } from "../internals/plan.js"; import type { Check } from "../internals/verify.js"; import type { Platform } from "../platform/base.js"; /** * `aih tools` — install the agent shell tools the harness leans on. Mirrors the * harness posture used for certs/npm: pick the right command for the detected * package manager, EMIT it (dry-run shows exactly what will run), execute it as a * LOCAL exec under `--apply`, and when an install fails (blocked registry, no * admin) escalate it as a support ticket rather than pretending it worked. * * Pure data + Runner-seam probes, so tests stay hermetic (no real install). */ export type Tier = "core" | "optional"; /** One package-manager install option: the PM that must be present, and its argv. */ export interface PmOption { pm: string; argv: string[]; } export interface ToolSpec { /** Display name. */ tool: string; /** The binary probed on PATH to decide "installed". */ bin: string; /** `core` (rg/fd/jq — absence is a real gap) vs `optional` (nice-to-have). */ tier: Tier; /** Ordered install options — the first whose PM is available wins. */ options: PmOption[]; /** Human fallback shown when no supported package manager is available. */ manual: string; } /** * The install matrix. Each tool lists package-manager options in preference order * (native PM first, then the cross-platform language toolchains). Only SAFE, * non-interactive commands — no piped `curl | bash`. */ export declare const TOOLS: ToolSpec[]; /** Probe a binary on PATH through the Runner seam (`where`/`which`). */ export declare function onPath(ctx: PlanContext, bin: string): Promise; /** The package managers available on this machine (canonical keys). */ export declare function detectPms(ctx: PlanContext): Promise>; /** Tools (core + optional) whose binary is NOT on PATH. */ export declare function missingTools(ctx: PlanContext): Promise; /** The first install option whose package manager is available, or `undefined`. */ export declare function chooseOption(t: ToolSpec, pms: ReadonlySet): PmOption | undefined; /** * Windows can't `execFile` a `.cmd` shim directly (npm/scoop/pnpm/yarn — and the * npm-installed `claude` CLI), so route those through `cmd /c` — the same fix the * rest of the harness uses for npm/npx. */ export declare const WIN_CMD_SHIMS: Set; export declare function execArgv(platform: Platform, argv: string[]): string[]; /** * The install actions for a set of missing tools, given the available package * managers: one per tool — a LOCAL `exec` when a PM matches (`allowFailure` so one * blocked install doesn't abort the rest), else a `doc` with the manual route. The * single source of truth for "how aih installs a shell tool", reused by `aih tools` * AND `aih ready --apply`. Callers append their own follow-on verify probes, which * carry the `env.tool-install-blocked` escalation when an install stays blocked. */ export declare function installActionsFor(ctx: PlanContext, tools: readonly ToolSpec[], pms: ReadonlySet): Action[]; /** How a tool would be installed, given the available package managers. */ export declare function howToInstall(t: ToolSpec, pms: ReadonlySet): string; /** * Post-install verification: is the tool on PATH now? A CORE tool still missing is * a `fail` (real gap, drives a non-zero exit + an escalation ticket); an OPTIONAL * one is a `skip` (advisory improvement). Both carry `env.tool-install-blocked` so * the support pipeline turns a blocked install into a ready-to-send ticket. Shared * by `aih tools` and `aih ready --apply` so a blocked install escalates identically. */ export declare function verifyTool(ctx: PlanContext, t: ToolSpec, pms: ReadonlySet): Promise;