/** * src/agent/guard.ts * * F-206 — `/guard` progress-guarding loop state. * * Exports: * addGuard({ planPath, intervalMs, goal?, slug? }) * listGuards() * getGuard(slug) * removeGuard(slug) * recordGuardCheck(slug, check) * markGuardStopped(slug) * * Persists each guard to `.bizar/guards//state.json` and appends * each check to `.bizar/guards//checks.jsonl`. The directory layout * mirrors `.bizar/cron.json` so a future `bizar migrate` pass can lift * both into `.bizar/state/` without a schema break. * * The guard loop itself is not a persistent daemon. `addGuard` only * records intent; the host-side `/loop` primitive (Claude Code) or an * external scheduler re-invokes `recordGuardCheck` on cadence. */ /** Bumped when the on-disk shape changes in a breaking way. */ export declare const GUARD_SCHEMA_VERSION = "1.0.0"; export type GuardStatus = "pending" | "running" | "stopped" | "done"; export type GuardVerdict = "healthy" | "drift" | "stuck" | "done"; export interface Guard { /** Stable slug; doubles as on-disk directory name. */ slug: string; /** Filesystem path (relative or absolute) to the plan doc. */ planPath: string; /** Check cadence in milliseconds. */ intervalMs: number; /** Optional operator-stated goal of the plan (free text). */ goal?: string; status: GuardStatus; /** ISO timestamp the guard was created. */ startedAt: string; /** ISO timestamp the most recent check completed; undefined if none. */ lastCheckedAt?: string; /** ISO timestamp the guard transitioned out of `pending | running`. */ stoppedAt?: string; /** Most recent verdict recorded by `recordGuardCheck`. */ lastVerdict?: GuardVerdict; /** Schema version for forward-compatible loaders. */ schemaVersion: string; } export interface GuardCheck { /** ISO timestamp the check completed. */ ts: string; /** Computed verdict. */ verdict: GuardVerdict; /** Free-text list of signals that produced the verdict. */ signals: string[]; /** Operator-actionable recommendation. */ recommendation: string; /** True when the guard self-terminated on this check. */ selfTerminated: boolean; } /** * Validate a slug: lowercase letters, digits, and dashes only. * Throws on empty, missing, or malformed input so callers see a clear * error rather than a path-traversal vulnerability. */ export declare function normalizeSlug(slug: string | undefined): string; /** * Add a guard. Returns the persisted record. Re-adding an existing slug * with identical options is allowed (idempotent — operator may have * re-run `bizar guard start` after a host crash), but re-adding with a * different `planPath` or `intervalMs` throws so the existing record * stays authoritative. */ export declare function addGuard(opts: { planPath: string; intervalMs: number; goal?: string; slug?: string; repoRoot?: string; }): Guard; /** List every guard on disk, sorted by `startedAt`. */ export declare function listGuards(repoRoot?: string): Guard[]; /** Fetch a single guard by slug. Returns null if missing or malformed. */ export declare function getGuard(slug: string, repoRoot?: string): Guard | null; /** * Remove a guard and its on-disk directory. * @returns true if the guard existed and was removed */ export declare function removeGuard(slug: string, repoRoot?: string): boolean; /** * Append a check to `/checks.jsonl` and update the parent guard's * `lastCheckedAt` + `lastVerdict`. Returns the persisted guard after * the update so callers can inspect the new status without a second * read. */ export declare function recordGuardCheck(slug: string, check: GuardCheck, repoRoot?: string): Guard; /** * Mark a guard as explicitly stopped by an operator (i.e. `bizar guard * stop`). Distinct from `recordGuardCheck`'s verdict-driven transition. */ export declare function markGuardStopped(slug: string, repoRoot?: string): Guard; /** Read the most recent N checks for a guard (default 5). */ export declare function listGuardChecks(slug: string, limit?: number, repoRoot?: string): GuardCheck[]; //# sourceMappingURL=guard.d.ts.map