/**
 * "Viewing in <app> tab N" for tmux-hosted agent sessions.
 *
 * A tmux-wrapped agent (see src/lib/exec.ts `runInTmux`) runs detached on the
 * shared socket; a terminal only *displays* it while a client is attached. This
 * resolver answers "which app + tab is looking at this session right now" by
 * matching the session to its attached tmux client(s) and reusing the app/tab
 * resolvers we already have:
 *
 *   - app  — the client's terminal PID walked up the process ancestry via the
 *            shared HOST_MATCHERS logic (`hostFromPid`).
 *   - tab  — per app: Ghostty via `assignGhosttyTabs` (cwd + title match), iTerm
 *            via the `t<n>` field of the client's `$ITERM_SESSION_ID`, and
 *            VS Code / Cursor / Codium via the extension-published `tabIndex` in
 *            live-terminals.json (keyed by session id).
 *
 * No client attached => `undefined` (the session is running detached). Every
 * lookup is best-effort; a miss degrades to `{ app }` with no tab, never throws.
 */
import type { TmuxClient } from '../tmux/session.js';
import type { ActiveSession } from './active.js';
import { type GhosttySurface } from './ghostty-tabs.js';
/** Where a tmux-hosted session is currently displayed. */
export interface ViewingIn {
    /** Host app of the attached client — 'ghostty', 'iterm', 'code', 'codium', … */
    app: string;
    /** 1-based tab number within that app, when it can be resolved. */
    tab?: number;
}
/**
 * The one display form of "where is this session being watched" — `'codium tab 3'`
 * when a client is attached, the bare app name when the tab can't be resolved, and
 * `'detached'` when the pane is live but nobody is looking at it (the terminal that
 * displayed it was closed or crashed).
 *
 * `undefined` means **we do not know**, and it covers two different situations that
 * must not be confused with `'detached'`: a session that isn't tmux-hosted (no pane
 * to attach to, so it isn't on this axis at all), and a tmux session whose pane the
 * locator could not resolve (`mapPanesToTargets` returned nothing for this socket,
 * or the row was never enriched). {@link resolveViewingIn} answers `undefined` for
 * BOTH "no client attached" and "could not locate the pane", so the pane's resolved
 * `tmuxTarget` is what separates them: without it there is no evidence of absence,
 * only absence of evidence. Claiming `'detached'` there would invent an orphaned
 * session — and a consumer acts on that claim (the ext's picker pre-ticks every
 * detached row for rescue), so the wrong answer resumes a session nobody asked for.
 *
 * Shared by the `--active` row renderer and the `--json` serializer so a machine
 * consumer reads exactly the string a human sees, instead of re-deriving "detached"
 * from an absent field.
 */
export declare function viewingInLabel(s: Pick<ActiveSession, 'provenance' | 'viewingIn' | 'tmuxTarget'>): string | undefined;
/**
 * Wire form -> internal form for a row arriving from another machine's
 * `--active --json`. The fan-out reaches peers whose CLI may predate
 * {@link viewingInLabel} and still emit the `{app, tab}` object, so this boundary
 * normalizes both shapes into one — the ONLY place either shape is accepted.
 * `'detached'` maps to undefined, which is what "no attached client" means
 * internally; {@link viewingInLabel} regenerates the word from the pane.
 */
export declare function parseViewingIn(raw: unknown): ViewingIn | undefined;
/** Injection seams so `resolveViewingIn` is unit-testable without a live tmux/ps/osascript. */
export interface ViewingInDeps {
    /** Ghostty surfaces (window/tab/cwd/title). Enumerated once by the caller and shared. */
    ghosttySurfaces?: GhosttySurface[];
    /** pane id -> `session:window.pane`, from `mapPanesToTargets`. Used to find the session name. */
    paneToTarget?: Map<string, string>;
    /** client pid -> host app. Defaults to the real `hostFromPid`. */
    resolveApp?: (pid: number) => Promise<string | undefined>;
    /** client pid -> raw env. Defaults to reading /proc (Linux) or `ps eww` (macOS). */
    readClientEnv?: (pid: number) => Promise<Record<string, string> | undefined>;
    /** session id -> VS Code editor-tab index, from live-terminals.json. Defaults to the real read. */
    tabIndexForSession?: (sessionId: string | undefined) => number | undefined;
}
/**
 * Resolve where a single tmux-hosted session is being viewed. Returns undefined
 * when the session isn't tmux-hosted, can't be located, or has no client
 * attached (detached). Pure aside from the injected (defaulted) probes.
 */
export declare function resolveViewingIn(session: ActiveSession, clients: TmuxClient[], deps?: ViewingInDeps): Promise<ViewingIn | undefined>;
/**
 * iTerm tab from the attaching client's `$ITERM_SESSION_ID` (`w<n>t<n>p<n>:UUID`).
 * The `t<n>` field is iTerm2's 0-based tab index; we present it 1-based to match
 * Ghostty's `index of tab`. Exported for the parser test.
 */
export declare function itermTabFromSessionId(value: string | undefined): number | undefined;
