import type { AgentLocation } from '../agent-location.js';
import type { AutoHandoffSkip, FrameworkEvent } from '../events.js';
/**
 * Persisted orchestration state (#211). The dashboard is a pure projection of the
 * {@link FrameworkEvent} stream, so persisting *is* durably logging that stream:
 * the stack rationale, the loop status, and the decisions ledger are all events
 * that already flow through it. We store the log append-only and rehydrate a
 * restarted dashboard by replaying it into a fresh stream — no separate state
 * model to keep in sync. Per the sync, we do **not** persist the agent's chat
 * transcript (Claude Code owns that); only our own orchestration events.
 */
/**
 * The directory, under the workspace root, that holds the persisted agent (#313):
 * one dir holds both the transient agent state (events.jsonl / agent.json) and the
 * committed agent archive (agents/, #1179); a seeded `.the-framework/.gitignore`
 * keeps the agent state untracked.
 */
export declare const FRAMEWORK_DIR = ".the-framework";
/**
 * Per-run worktrees live under `<repo>/.the-framework/branches/` (#736/#1580), each in a dir
 * named as its branch. Kept out of git by the install-time `.the-framework/.gitignore` (`*` rule,
 * #313), so a worktree's checkout never shows up as dirty in the parent. Declared here beside
 * {@link FRAMEWORK_DIR} rather than in `worktree.ts`, which imports from this module:
 * {@link readLiveMetas} needs it to find the runs living in those worktrees, and the other
 * direction would be an import cycle.
 */
export declare const BRANCHES_DIR = "branches";
/** The append-only event log: one {@link FrameworkEvent} per line (JSONL). */
export declare const EVENTS_FILE = "events.jsonl";
/** A small snapshot for cheap status reads without replaying the whole log. */
export declare const META_FILE = "agent.json";
/**
 * Where finished agents are archived, under both placements that name has: the lasting
 * `agents/<user>/` on the data branch's checkout (#1179/#1582), and the transient
 * `.the-framework/agents/` that an agent with no worktree of its own — or one archiving inside
 * its own throwaway checkout — writes into. {@link archiveDir}/{@link committedArchiveDir} are
 * where a caller picks; both are read when a project's history is listed.
 *
 * The live agent stays at `events.jsonl`/`agent.json` (the daemon tails it); on
 * {@link AgentStore.close} a copy lands here as `<id>.jsonl` + `<id>.json` (#303), giving the
 * history sidebar a per-agent log to replay.
 *
 * The name lives here rather than in `sessions.ts`, which owns the per-user naming: that module
 * reads the store, so the constant travelling the other way would be a cycle.
 */
export declare const ARCHIVE_DIR = "agents";
/** Filesystem-safe, lexicographically-sortable agent id from an ISO start time. */
export declare function agentIdFromStartedAt(startedAt: string): string;
/** An agent id is path-safe: no separators or traversal, only our own charset. */
export declare function isSafeAgentId(id: string): boolean;
/**
 * The inverse of {@link agentIdFromStartedAt}, for a caller that has the id but not the meta
 * (#1251): the CLI's end-of-run handoff needs the start time to tell the agent's own PR from a
 * predecessor's on the same branch name. Undefined for an id that is not one of ours.
 */
export declare function startedAtFromAgentId(id: string): string | undefined;
/** How an agent ended (or that it is still going). */
export type AgentStatus = 'running' | 'done' | 'stopped' | 'failed';
/**
 * A queryable snapshot of the agent, derived entirely from the event log. Lets the
 * dashboard render a header (and a future agent list) without parsing every line.
 */
export interface AgentMeta {
    status: AgentStatus;
    /** Stable, path-safe id for this agent (derived from {@link startedAt}). */
    id: string;
    /** ISO timestamp the store was opened (run start). */
    startedAt: string;
    /** ISO timestamp of the last event written. */
    updatedAt: string;
    /**
     * The OS pid of the process that owns this agent (the one tailing `control.jsonl`), on {@link host}.
     * Persisted so a reader can tell a live agent from one whose process died without writing `end`
     * (#716): a `running` meta whose owning pid is gone is stale and gets flipped to `stopped`.
     */
    pid?: number;
    /** The host the owning {@link pid} lives on, so a pid probe only trusts a match (#716). */
    host?: string;
    /** What this session was asked for (from the `intent` event). */
    intent?: string;
    /** The wrapped agent (from the `session` event). */
    driver?: string;
    /** The workspace the agent builds in (from the `session` event). */
    workspace?: string;
    /** The wrapped agent's real session id, once it reports one. */
    sessionId?: string;
    /** The link shown to jump into the live agent session. */
    sessionLink?: string;
    /** The session name the agent chose (#326), also its `tf-<name>` branch. */
    sessionName?: string;
    /**
     * The branch the agent's work is on: folded from `branch` events as the agent observes it (#1277),
     * and corrected at teardown while the worktree still exists (#799).
     *
     * Not reliably derivable instead of recorded: a clean agent loses its checkout, and the #326
     * prompt lets the agent create its own branch, so neither `tf-<sessionName>` nor
     * the run-id branch is guaranteed to be the one holding the commits.
     */
    branch?: string;
    /**
     * The hand-off anchor a cloud run pushed for its session to clone at (#1601): an empty commit
     * unique to this run, folded from the `cloud-anchor` event. The session works on a `claude/*`
     * branch of the cloud's own naming, and this is the ancestor by which the daemon's adoption
     * pass recognizes which of origin's `claude/*` heads is this run's. Absent on non-web runs
     * and on web runs whose pre-hand-off push failed.
     */
    cloudAnchor?: string;
    /**
     * The ticket this agent is implementing (#1117), repo-relative (`tickets/<file>.md`).
     *
     * Set only when the framework picked the ticket itself, so the Overview can show a ticket that is
     * being coded right now as `implementing` instead of inferring it from the plan/spike it left
     * behind. Absent on every agent nobody linked to a ticket.
     */
    ticket?: string;
    /**
     * The pull request this session's work is on (E6), recorded when one is opened rather than
     * re-derived from branch names and timestamps by every surface that wants it.
     */
    pr?: {
        number: number;
        url: string;
    };
    /** Whether the agent signalled `setReadyForMerge()` (#326): building (false/absent) vs ready (true). */
    readyForMerge?: boolean;
    /**
     * What this session's end-of-session handoff is armed to do (#1102): push its branch, and open
     * a draft PR for it. Both start on.
     *
     * On the meta because the checkboxes that show it live in a different process from the agent that
     * obeys it, and a tab opened after the agent started has no event history to fold — the same
     * reason {@link browserStreamPort} is here. Absent means an older agent, which the reader treats
     * as armed, matching what that agent will actually do.
     *
     * `merge` mirrors the auto-merge arming (#1216, #1382) — display-only, like the rest of this
     * field: the agent merges off its own config, never off the meta. Absent on records from before
     * #1382, which the reader treats as off.
     */
    handoff?: {
        push: boolean;
        pr: boolean;
        merge?: boolean;
    };
    /**
     * How the end-of-session handoff reported back (#1455), folded from the `handoff` event.
     *
     * What lets a list surface — which reads meta, not the event log — tell "ended, still
     * publishing" from "ended, published": between a clean `end` and this field, an armed agent's
     * epilogue is still pushing / opening the PR, exactly the window the session pill calls
     * "publishing…" (#1431). Absent until the event lands, which is what a list reads as "still going".
     */
    handoffReport?: 'done' | 'skipped' | 'failed';
    /**
     * Why a skipped handoff skipped (#1583), folded from the same `handoff` event as
     * {@link handoffReport}. What lets the daemon tell "published elsewhere" from "ended with
     * nothing to hand off": a drain that settles with `no-commits` will never run the PR that
     * lifts its ticket lock, so the sweep releases the claim it minted. On the meta because the
     * sweep reads metas, not event logs. Absent on non-skipped handoffs and on older records.
     */
    handoffSkip?: AutoHandoffSkip;
    /**
     * How the handoff's merge half went (#1418), folded from the `handoff` event's `merge` field.
     *
     * What the daemon's CI watch scans for: `watched` is a PR waiting for green that *this* side
     * must merge (the repo could not arm GitHub auto-merge), `auto-armed` one GitHub will land by
     * itself but whose checks going red is still ours to notice. On the meta because the watch
     * reads metas, not event logs, and must survive both the agent's process and the daemon's.
     * Absent on runs from before this field, and on every agent whose handoff had no merge to report.
     */
    mergeOutcome?: 'auto-armed' | 'merged' | 'watched' | 'withheld' | 'failed';
    /**
     * The choice gate the agent is currently parked on (#636): set when a `choice` event fires and
     * cleared when its `choice-resolved` (or the agent's `end`) arrives. Present means the agent is
     * paused waiting for the user's answer — the second "needs you" source after open PRs (#624).
     */
    pendingChoice?: {
        id: string;
        title: string;
    };
    /**
     * When the agent settled and parked on the user (#785), or absent while the agent is working.
     *
     * Deliberately not a {@link AgentStatus} value: the agent IS still live while it waits (its
     * process is alive, it still takes messages, it still holds the project), and a dozen readers
     * key "live" off `status === 'running'`. This is the orthogonal fact — working, or waiting on
     * you — which `status` cannot carry because it only changes when the agent ends.
     */
    settledAt?: string;
    /**
     * The loopback port the agent's browser preview is listening on (#813), or absent when the agent
     * has no browser. What lets the daemon proxy the pane: the port is allocated per agent and the
     * dashboard is a different process, so meta is the only place it can learn it.
     */
    browserStreamPort?: number;
    /**
     * Where this run executes (#1050/#1053/#610): `actions` for a GitHub Actions run, `web` for a
     * Claude Code cloud session, `remote` when relayed to a connected device (#1067), absent for a
     * local run. Persisted so the agent view can tell a burst-mode Actions run from a stalled live
     * feed, show a cloud agent's session link after a reload, and gate the browser pane off (#1053).
     */
    target?: 'local' | 'actions' | 'remote' | 'web';
    /** The connected device a remote agent (#1067) executes on, for the session list + notice after a reload. */
    remoteLabel?: string;
    /**
     * The flow this agent started under (#1467): `build` for the scope→build orchestration, `prompt`
     * for the direct-prompt path (research and transparent runs record `prompt` too). Persisted so a
     * continuation (#762) can re-enter the flow its first leg ran — the composer's Resume always
     * arrives as a `prompt` start, and without this record a resumed build agent ended as a bare
     * prompt session (no synthesize framing, no backlog offer). Absent on records from before this
     * field, which a reader treats as unknown (the continuation then keeps the prompt path).
     */
    kind?: 'build' | 'prompt';
    /**
     * The model id the current leg's agent was started with (#1438), folded from each leg's
     * `session` event — a continuation (#762) may run a different model than the first leg, so
     * the latest leg wins rather than the first pinning it. Absent when the leg left the agent
     * on its own default (and on records from before this field).
     */
    model?: string;
}
/**
 * The slice of a filesystem {@link AgentStore} needs. Mirrors the `LedgerFs` seam
 * in ai-autopilot's decisions store: the store logic is pure and testable with an
 * in-memory fs, and only {@link nodeStoreFs} touches disk.
 */
export interface StoreFs {
    read(path: string): Promise<string>;
    write(path: string, contents: string): Promise<void>;
    append(path: string, contents: string): Promise<void>;
    exists(path: string): Promise<boolean>;
    mkdir(path: string): Promise<void>;
    /** List a directory's entries (names only). Missing dir yields `[]`. */
    readdir(path: string): Promise<string[]>;
    /**
     * Replace `to` with `from` in one step. Optional: an adapter that has it gets torn-proof meta
     * writes (see {@link writeMetaFile}), and one that does not writes in place, which is right for
     * the in-memory fakes — a `Map.set` cannot be observed half-done.
     */
    rename?(from: string, to: string): Promise<void>;
}
/** Options for {@link AgentStore.open}. */
export interface OpenStoreOptions {
    /** The filesystem adapter. Default {@link nodeStoreFs}. */
    fs?: StoreFs;
    /**
     * Truncate any prior log so this is a clean agent (MVP: one agent per workspace).
     * `false` (the default) opens read-only-ish for {@link AgentStore.loadEvents} —
     * the `--resume` path — and does not clear the log.
     */
    fresh?: boolean;
    /** The wall-clock start, ISO. Injectable so tests are deterministic. */
    now?: string;
    /**
     * Reads the current time for each appended event, so {@link AgentMeta.updatedAt} tracks the last
     * event rather than the agent's start. Injectable so tests can step it deterministically.
     *
     * Separate from {@link now} on purpose: `now` is when the agent *opened*, and a single timestamp
     * cannot answer both questions. Reusing it for appends froze `updatedAt` at `startedAt` for a
     * run's whole life, which every reader that orders by recency (the overview, the activity feed,
     * the interventions queue) silently sorted on.
     */
    clock?: () => string;
    /**
     * The session's intent (its prompt / request) shown in the dashboard's sessions list. Seeded
     * here so the row shows the prompt from the moment the store opens, before the session's own
     * `intent` event lands; refreshed by that event.
     */
    intent?: string;
    /**
     * Who owns this agent (#716). Defaults to the current process on this host — the process opening a
     * fresh store *is* the agent's owner. Injectable so tests can seed a specific (dead) pid.
     */
    owner?: AgentOwner;
    /**
     * The agent's id, overriding the one derived from {@link OpenStoreOptions.now}. The daemon
     * allocates the id before it spawns the agent (it names the agent's worktree with it, #736) and
     * passes it in, so the worktree directory and the agent inside it are one string rather than two
     * timestamps taken a moment apart. Ignored unless path-safe.
     */
    id?: string;
    /**
     * Reopen the agent already at this path instead of starting a new one (#762): keep its event log
     * and its original intent, and flip it back to `running` under this process. What makes a
     * continued run one row in the history rather than two: the follow-up is a second process, but
     * it writes into the same agent.
     *
     * Falls back to a fresh agent when there is nothing to reopen.
     */
    continueAgent?: boolean;
    /** Where this agent executes (#1053/#610): recorded on the meta so the agent view can read it. */
    target?: AgentLocation;
    /** The flow this agent started under (#1467): recorded on the meta so a continuation can re-enter it. */
    kind?: 'build' | 'prompt';
}
/**
 * Fold one event into the running {@link AgentMeta}. Pure, so the same derivation
 * drives both a live append and reconstructing meta from a replayed log.
 */
export declare function applyEventToMeta(meta: AgentMeta, event: FrameworkEvent, at: string): AgentMeta;
/** Who owns a live agent: its OS pid and the host that pid lives on (#716). */
export interface AgentOwner {
    pid: number;
    host: string;
}
/** Rebuild {@link AgentMeta} from a full event log (used when resuming). */
export declare function metaFromEvents(events: readonly FrameworkEvent[], startedAt: string): AgentMeta;
/**
 * Durable, append-only store for a single agent's orchestration events, plus a
 * derived {@link AgentMeta} snapshot. Writes are serialized through one tail
 * promise so an append and its meta rewrite never interleave; {@link close}
 * flushes that queue before the process exits.
 */
export declare class AgentStore {
    private readonly fs;
    readonly dir: string;
    private readonly clock;
    private tail;
    private meta;
    /**
     * The intent a continuation must keep (#762/#1467): a reopened session keeps its original
     * label, but a continuation's own `intent` event carries the resume message and would relabel
     * the row through {@link applyEventToMeta}'s normal refinement. Unset for a fresh session,
     * where that refinement stands.
     */
    private pinnedIntent;
    private constructor();
    /** The event log path. */
    get eventsPath(): string;
    /** The meta snapshot path. */
    get metaPath(): string;
    /**
     * Open (creating `.the-framework/` if needed) under the workspace `cwd`. `fresh`
     * truncates any prior log for a new agent; the default preserves it so a resume
     * can {@link loadEvents}.
     */
    static open(cwd: string, opts?: OpenStoreOptions): Promise<AgentStore>;
    /**
     * Append one event to the log and refresh the meta snapshot. Fire-and-forget at
     * the call site: internally chained so writes stay ordered. A failed write is
     * swallowed (persistence is best-effort — it must never break a live agent).
     */
    append(event: FrameworkEvent): Promise<void>;
    /**
     * Flush any queued writes, then archive this agent into `agents/` so it shows up in
     * the dashboard's history (#303). Both best-effort: persistence must never break
     * an agent, so an archive failure is logged, not thrown.
     */
    close(): Promise<void>;
    /** The current derived snapshot. */
    snapshot(): AgentMeta;
    /**
     * Read and parse the persisted event log. A blank or malformed trailing line
     * (e.g. a crash mid-write) is skipped rather than throwing, so a partial agent
     * still replays everything up to the cut. Missing file yields `[]`.
     */
    loadEvents(): Promise<FrameworkEvent[]>;
    /** Read the persisted meta snapshot, or `undefined` if none/unreadable. */
    readMeta(): Promise<AgentMeta | undefined>;
    private writeMeta;
}
/**
 * Put an archived agent's history back where an agent reads it (#762), so a continued agent picks up its
 * own log rather than starting empty. The inverse of {@link archiveWorktreeAgent}: teardown moved the
 * history to the repo, and continuing needs it in the checkout again.
 *
 * A no-op when the worktree already holds a live agent (nothing to restore, and its log is newer),
 * or when there is no archive. Never throws.
 */
export declare function restoreArchivedAgent(repo: string, worktree: string, agentId: string, fs?: StoreFs): Promise<boolean>;
/** One checkout on disk: where it is, and whose it is. */
export interface WorktreeDirEntry {
    path: string;
    agentId: string;
}
/**
 * Every checkout directory on disk (#1580). Only the run branch spelling counts — the same
 * directory holds the rename links (#1589), which are views, not checkouts. Forgiving: a missing
 * root yields nothing.
 */
export declare function worktreeDirEntries(cwd: string, fs?: StoreFs): Promise<WorktreeDirEntry[]>;
/**
 * The agent ids that have a worktree directory (#737/#1580). Forgiving — a project that never ran
 * concurrently has no such dir and yields `[]`.
 */
export declare function listWorktreeDirs(cwd: string, fs?: StoreFs): Promise<string[]>;
/**
 * Archive a worktree agent's history into the *main repo* (#737), returning the meta it archived.
 *
 * An agent writes its `agent.json` / `events.jsonl` inside its own worktree (#736), so deleting that
 * worktree would delete the agent's history with it. This copies it into the repo, which is the one
 * place the dashboard's history reads from, so teardown becomes safe.
 *
 * `user` files the copy under that user's lasting `agents/<user>/` on the data branch's checkout
 * (#1179/#1582) instead of the transient `agents/`. It is this copy, not the one the agent left in
 * its own worktree, that is meant to last: every agent in a git repo gets a worktree, so this is
 * the only archive of it that outlives the checkout. The caller owns getting it committed — the
 * daemon funnels this through the data branch's writer. The worktree's own copy deliberately
 * stays untracked — it would otherwise be committed onto the agent's branch as well and collide
 * with this one on merge.
 *
 * A meta still marked `running` is flipped to `stopped` first: this runs when the process is
 * already gone, so `running` means it died without closing (crash, kill -9), exactly the case
 * {@link reconcileOrphanedAgents} handles for the project path. Idempotent per id, and forgiving:
 * a worktree with no run, or an unreadable one, yields `undefined` rather than throwing.
 */
export declare function archiveWorktreeAgent(worktree: string, repo: string, fs?: StoreFs, branch?: string, user?: string): Promise<AgentMeta | undefined>;
/**
 * The archived log + meta paths of one agent, wherever it is filed, or `[]` when it is nowhere.
 * Exported so a caller that deletes a session (the dashboard's Remove) does not have to know which
 * user archived it — before #1179 the path was derivable from the id alone, and now it is not.
 */
export declare function archivedAgentPaths(cwd: string, agentId: string, fs?: StoreFs): Promise<string[]>;
/**
 * List a project's archived agents, most-recent first: every user's committed archive plus the
 * transient `agents/`. The id sorts chronologically so no timestamp parse is needed. Missing or
 * unreadable dir/entries are skipped, never thrown.
 *
 * `since` (epoch ms) is for a caller that only wants recent runs — a poll on a cadence, not the
 * history list. It is answered from the filenames, so the records it excludes cost no read at all.
 */
export declare function listAgents(cwd: string, fs?: StoreFs, since?: number): Promise<AgentMeta[]>;
/**
 * Reconcile runs a dead process left marked `running` — the live `agent.json`, an archived
 * `agents/*.json`, or an agent inside a worktree. Such an agent shows as active while nothing is left
 * to read its `control.jsonl`, so its Stop is a no-op. Each is flipped to `stopped`; the live
 * run is archived first (idempotent) so its history is kept. Returns how many were reconciled.
 * Best-effort: a read/write error skips that agent, never throws.
 *
 * An agent whose pid is alive on this host is left alone (#926). This used to flip every `running`
 * meta on the assumption that a fresh dashboard drives no in-flight run, which holds only while
 * exactly one is ever booted: a second one marked genuinely live agents as finished, giving them a
 * no-op Stop in the dashboard. A meta with no `pid` keeps the old behaviour, since there is
 * nothing better to go on.
 */
export declare function reconcileOrphanedAgents(cwd: string, fs?: StoreFs, isAlive?: (pid: number) => boolean): Promise<number>;
/**
 * Whether `pid` is a live process on this host. `process.kill(pid, 0)` sends no signal but
 * throws `ESRCH` once the process is gone; `EPERM` means it exists under another user (still
 * alive). A pid on a *different* host is unknowable here, so callers guard on {@link AgentMeta.host}
 * before trusting a result. A recycled pid (another process reusing a dead agent's number) reads as
 * alive — an accepted, vanishingly rare miss on a single dev box.
 */
export declare function isPidAlive(pid: number): boolean;
/**
 * The live (in-progress) run's meta snapshot from `.the-framework/agent.json`, or
 * `undefined` when none/unreadable. Unlike {@link listAgents} (which reads the
 * archived `agents/` copies written on close), this is the agent the daemon is
 * tailing right now — so the dashboard can list it with a `running` status
 * before it finishes. Missing or torn file yields `undefined`, never throws.
 *
 * Self-heals a stale agent on read (#716): if the meta says `running` but its owning process died
 * without writing `end` (a crash, `kill -9`, or the machine sleeping), nothing is left to consume
 * `control.jsonl` — so Stop is a no-op and the row is stuck. When the owning pid is gone on this
 * host, flip it to `stopped` and archive it, so the dashboard clears the row on the next poll
 * instead of only after a daemon restart's boot-time {@link reconcileOrphanedAgents}. An agent whose
 * meta predates this field (no `pid`) is left untouched — the boot reconcile still catches it.
 */
export declare function readLiveMeta(cwd: string, fs?: StoreFs, isAlive?: (pid: number) => boolean): Promise<AgentMeta | undefined>;
/**
 * A live agent plus the checkout it is running in (#738). Since #736 an agent lives in its own
 * worktree, so a project's live run is no longer a single thing and no longer sits at the
 * project path: `cwd` says which checkout to read that agent's git/file status from.
 */
export interface LiveAgent extends AgentMeta {
    /** The agent's own checkout: a worktree under `.the-framework/branches/`, or the repo root. */
    cwd: string;
}
/**
 * Every live agent of a project (#738): the list variant of {@link readLiveMeta}.
 *
 * An agent started from the dashboard gets its own worktree (#736) and writes its `agent.json`
 * inside it, so the project path alone no longer sees any of them. This looks in both places:
 * each `.the-framework/branches/*` checkout, and the repo root itself, which is where a
 * project that cannot be given a worktree (not a git repo) still runs and where every agent
 * from before #736 lives.
 *
 * Each candidate goes through {@link readLiveMeta}, so a stale agent self-heals exactly as it
 * did. Newest first, by id. Never throws: an unreadable worktree is skipped.
 */
export declare function readLiveMetas(cwd: string, fs?: StoreFs, isAlive?: (pid: number) => boolean): Promise<LiveAgent[]>;
/**
 * Read one archived agent's event log for replay. Returns `undefined` for an
 * unknown or unsafe id; a torn trailing line is dropped (same rule as the live
 * {@link AgentStore.loadEvents}).
 */
export declare function loadAgentEvents(cwd: string, id: string, fs?: StoreFs): Promise<FrameworkEvent[] | undefined>;
/** A {@link StoreFs} backed by `node:fs/promises`. See {@link nodeFs}. */
export declare function nodeStoreFs(): StoreFs;
/**
 * A project's runs: the live ones prepended to the archived history, newest-first. Forgiving —
 * a side that cannot be read simply contributes nothing.
 *
 * Live wins over archived (#768). The dedup used to drop the live copy, which was right while
 * "archived" meant "finished for good": an agent was only ever copied into `agents/` on its way out.
 * Continuing an agent (#762) breaks that — the agent has an archived copy from its first leg AND is
 * live again — and keeping the archive showed a running agent as finished.
 *
 * This composition, not its two halves, is what every caller actually wants; the store exporting
 * only the halves is why three separate modules each grew their own copy of it.
 */
export declare function readAllAgents(cwd: string, fs?: StoreFs): Promise<AgentMeta[]>;
/**
 * One agent's meta by id, live copy winning over archived — {@link readAllAgents}'s rule for a
 * single row. The find-by-id shape the RPCs kept privately rebuilding, for the same reason
 * the list shape did: the store exported only the halves.
 */
export declare function findAgent(cwd: string, agentId: string, fs?: StoreFs): Promise<AgentMeta | undefined>;
/**
 * Read a checkout's live event log (`.the-framework/events.jsonl`). Missing or unreadable
 * yields `[]`, and a torn trailing line is dropped — the same rule as
 * {@link AgentStore.loadEvents}, exported so a reader outside the store (the Discord bot's gate
 * lookup) cannot keep a second parser with a drifted torn-line policy.
 */
export declare function readEventLog(cwd: string, fs?: StoreFs): Promise<FrameworkEvent[]>;
/** The facts a settled run learns after its process is gone: the PR its work is on, the branch it landed on. */
export type ArchivePatch = Partial<Pick<AgentMeta, 'branch' | 'pr'>>;
/**
 * Patch an archived run's record with a fact discovered once the agent's process is gone (E6,
 * #1601): the pull request opened for its work, or the branch a cloud session's work landed
 * on. There is no event stream left to carry it, and every surface reads the record, so this
 * one write is what turns a "nothing committed" row into its real branch and PR.
 *
 * A plain file write: the archive lives on the data branch's checkout, and a fact written there
 * is only durable once committed — {@link patchArchivedAgentOnDataBranch} is the funneled form
 * every caller outside a test uses.
 */
export declare function patchArchivedAgent(cwd: string, agentId: string, patch: ArchivePatch, fs?: StoreFs): Promise<boolean>;
//# sourceMappingURL=agent-store.d.ts.map